Skip to main content
string
required
A BCP 47 tag such as "en", "es" or "pt-BR". Plugins look up their own phrasebooks by this id.
Grammar
required
Word mechanics for this language.
CorePhrases
required
Every phrase the TypeScript engine can produce.
Record<string, unknown>
Phrasebooks for plugins that don’t ship this locale, keyed by plugin name. They can be partial: each phrase here takes priority over the plugin’s own translation, and anything missing falls back to it and then to the plugin’s English. Entries for plugins registered in PluginPhrases are type-checked against that plugin’s phrasebook type. See Typed overrides.

extendLocale

Builds a locale on top of another. phrases and each plugin’s phrasebook are merged into the base key by key, so anything you leave out keeps the base’s wording. grammar helpers replace the base’s one by one. This is the recommended way to start a translation.

mergePhrases

The merge extendLocale and the engine use: later phrasebooks win, nested groups are merged rather than replaced, and anything they leave out comes from the earlier ones.

Grammar

All of these receive strings that may contain markup. There is no hook for grammatical gender, because the engine doesn’t know a noun’s gender. article receives the noun it goes with, so a locale can look the gender up itself. See Grammar, gender and number.

CorePhrases

CorePhrases groups phrases by area. Each phrase is a function from already-rendered pieces to a string, or a plain string for fixed words. The complete, commented type ships with @usenarrator/core. The English implementation is on GitHub in packages/locale-en/src/phrases, one file per area.

Example

See Translating Narrator for a full walkthrough.