Q28 of 38 · TypeScript
What are template literal types in TypeScript, and what can they express?
Short answer
Short answer: Template literal types combine string literal types using backtick syntax: `` `get${Capitalize<string & K>}` ``. They enable typed event names, route patterns, CSS property names, getter/setter method names, and any string-structured type — all enforced at compile time.
Detail
Template literal types (TypeScript 4.1) apply template literal string syntax to types, producing new string literal types from combinations.
Basic syntax: ``type EventName = on${string}``` — matches any string starting with "on". Combined with a literal union: ```on${Capitalize<"click" | "focus">}``` produces "onClick" | "onFocus"`.
Built-in string manipulation types: TypeScript ships Capitalize, Uncapitalize, Uppercase, Lowercase for use in template literal types.
Key remapping in mapped types: The most powerful use — generate method names from property names in a mapped type:
{ [K in keyof T as get${Capitalize<string & K>}]: () => T[K] }
In test automation:
- Typed event names:
page-event:${PageName} - Typed CSS custom properties:
--${string} - Typed API endpoints:
/api/${Resource}/${number}(limited but useful) - Typed fixture names in Playwright config: ensures fixture keys follow a naming convention
// EXAMPLE
// Basic template literal type
type EventName = `on${"Click" | "Focus" | "Blur"}`;
// "onClick" | "onFocus" | "onBlur"
// Generate getter/setter pairs from a model
interface User { name: string; email: string; age: number; }
type Getters<T> = {
[K in keyof T as `get${Capitalize<string & K>}`]: () => T[K];
};
type Setters<T> = {
[K in keyof T as `set${Capitalize<string & K>}`]: (val: T[K]) => void;
};
type UserAccessors = Getters<User> & Setters<User>;
// { getName: () => string; setName: (val: string) => void; ... }
// Typed CSS custom properties
type CSSCustomProp = `--${string}`;
function setCssProp(el: HTMLElement, prop: CSSCustomProp, val: string) {
el.style.setProperty(prop, val);
}
setCssProp(el, "--color-primary", "#0D9668"); // ok
// setCssProp(el, "color", "red"); // Error: must start with --