Languages
The languages your players read, who chooses a player's language, and how translated rules are shown
The embed shows its interface and its events in your players' languages. You choose which languages your operator offers; each launch then has exactly one owner of the player's language: your site, or the embed.
Your Languages
Your operator offers an ordered list of languages. The first one is your default: a player whose language you do not offer reads your default, and a text with no translation in the player's language falls back to it.
| Code | Language | Shown to players as | Embed interface |
|---|---|---|---|
en | English | English | English |
fr | French | Français | French |
sw | Swahili | Kiswahili | Swahili |
Your list and the country your numbers and dates are formatted for (for example KE for Kenya) are operator settings, shared by sandbox and production. Your team's Admin can change them in the back office, or Phoenix sets them during onboarding. Every code must be one Phoenix offers, and each may appear once.
Who Owns the Player's Language
Whoever sends the language owns it, so your site and the embed can never disagree.
Your site has its own language switcher. Put the player's language in the launch token's language claim:
{
"iss": "acme",
"env": "prod",
"sub": "operator-player-123",
"currency": "KES",
"name": "Player Name",
"avatar": { "kind": "none" },
"language": "fr",
"iat": 1779100000,
"exp": 1779100600
}- The embed opens in that language if you offer it, else in your default language. A code you do not offer never refuses the launch.
- The embed shows no language picker of its own.
- When the player switches language on your site, switch the embed with the Host SDK, without a new token or a reload:
embed.setLanguage('en')In React, pass the language prop to PmmEmbedFrame or usePmmEmbed; a change is pushed to the running embed. The switch lasts for this session and survives a setToken.
The embed refuses a switch it cannot make and tells your page with an error event: code language_not_enabled for a language your operator does not offer, language_not_host_owned when the launch token has no language claim (the embed owns the language then), and session_not_live while the session has stopped and waits for a fresh token.
A switch reconnects the embed, so a switch after the launch token has expired ends the session: the player sees "Your session ended" and your page receives session.expired (see Sessions and Token Refresh).
Your site has no language switcher, or you prefer the embed's. Leave language out of the launch token:
- The embed shows a language picker in its header when you offer two or more languages, listing each language in its own name.
- The choice is kept in the player's browser, and a signed-in player's choice is also saved with their account, so their next launch on another device opens in it too. On a device that has its own saved choice, that choice wins.
- A player who never chose reads your default language.
setLanguagefrom your page is refused withlanguage_not_host_owned.
Switching language reloads the embed's live data in the new language within a moment; the player stays signed in. Your page hears every switch, whoever made it: the embed sends language.changed ({ language }) once the session reads in the new language. ready carries the language the session started in. An embed without the language.changed capability (see embed.info.capabilities) never sends it.
What Players Read
Every event text a player sees is shown in their language when it has an approved translation, else in your default language when that has an approved translation, else as the event was written.
- A draft is never shown. A translation drafted by the AI reaches players only after a person who reads the language approves it. Until then players read the text as written.
- Phoenix's events are written in English. Phoenix translates them into the languages operators offer, and approves those translations. Events made from Phoenix's templates (for example football fixtures from the data feed) carry their translations with them.
- Your own events are written in the language your staff choose, and translations are optional. Your staff translate and approve them in the back office. An event without an approved translation is shown as written; nothing blocks publishing.
- A translation made from text that was later changed is not shown until someone updates or keeps it, so players never read an out-of-date translation.
- Player comments are never translated.
Your staff see each text's status (Missing, Out of date, Waiting for approval or Approved) in the back office. Players never see a status. See Languages and Translations.
Numbers and dates follow the embed's interface language and your formatting country, for example 21/10/2026 for English with KE.
Translated Rules
The rules as written decide every result. A translation is for reading only.
When a market's rules are shown translated, the rules panel says so, for example "Translated from English. If they differ, the English rules apply.", with a Show the original link that switches to the rules as written (and Show the translation to switch back).
Checklist
- Tell Phoenix your languages, default first, and your formatting country, or have your Admin set them in the back office.
- Decide who owns the language. If your site has a switcher, send
languagein every launch token and callsetLanguagewhen the player switches. Otherwise leavelanguageout. - In sandbox, launch once in each of your languages and open a market's rules to check the translation notice.