Localization and Text
Localized text, formatted text with inserted values, and the shop banner in a Real-time Catalog response.
How the text fields in your GetCatalog response are localized and formatted, and the optional shop banner.
Localization
All user-facing text supports localization. Each text field is a LocalizableText. Send defaultText in every one, since it is the fallback, and add at most one of:
localizationKey: Stash-side lookup in our localization system (requires sharing localization keys with Stash up front).localizedText: Pre-resolved text in the player's language, computed by your backend.
Pick whichever fits your localization pipeline; you can mix the two across different fields in the same response.
Stash shows localizedText when you send it. For a localizationKey, it shows the translation for the player's language, or defaultText when the key has no translation. With neither, it shows defaultText. When a localizationKey on your webshop page falls back to defaultText, a shop with catalog diagnostics on receives a CATALOG_TEXT_FALLBACK webhook naming the key, and whether the key is unknown or only lacks a translation in that language.
Formatted text
A LocalizableText can carry values to insert into its text, so one translated sentence serves every player and each language places the values where its grammar needs them.
| Field | Meaning |
|---|---|
formatArguments | Optional. The values to insert, as a map of keys to strings, for example {"count": "1"}. |
formatSyntax | How the text writes its placeholders: TEXT_FORMAT_SYNTAX_ICU_MESSAGE_FORMAT for {count} or {0}, or TEXT_FORMAT_SYNTAX_PRINTF for %s or %1$s. |
Stash picks the text for the player's language as described in Localization, inserts the values, and shows the result.
Example. A localization entry shared with Stash:
| Key | English | Japanese |
|---|---|---|
TOOLTIP.PACK_GUARANTEE | At least {count} card of {rarity} stars or more | {rarity}つ星以上のカードが{count}枚以上 |
A content item that uses it as its info tooltip:
{
"name": { "defaultText": "Card pack" },
"quantity": "1",
"infoButton": {
"tooltip": {
"text": {
"defaultText": "Contains guaranteed cards",
"localizationKey": "TOOLTIP.PACK_GUARANTEE",
"formatArguments": { "count": "1", "rarity": "3" },
"formatSyntax": "TEXT_FORMAT_SYNTAX_ICU_MESSAGE_FORMAT"
}
}
}
}The tooltip text is At least 1 card of 3 stars or more in English and 3つ星以上のカードが1枚以上 in Japanese.
For printf-style text such as At least %1$s card of %2$s stars or more, send "formatArguments": {"1": "1", "2": "3"} with "formatSyntax": "TEXT_FORMAT_SYNTAX_PRINTF".
- Values are literal. Stash inserts each value as sent, with no number, date or plural formatting, so send values already formatted for the player's language.
- Limits. At most 32 entries. Keys match
^[A-Za-z0-9_]{1,64}$and values are at most 512 bytes. The text before composing is at most 4096 bytes, and the composed text at most 8192 bytes. - Fallback. If the text cannot be composed, for example because a value it reads is missing, Stash composes
defaultTextwith the same syntax and values instead. If that fails too, the text is left out. WritedefaultTextwithout placeholders so the fallback renders, and with printf-style write a literal percent sign as%%. - Optional. A text with neither field shows as is.
formatArgumentswithout aformatSyntaxleaves the text out.
For ICU-style quoting, %d, and the other edge cases, see the GetCatalog API Reference.
Shop banner
catalog.banner is an optional banner shown once, above the first section of the shop, for example a message about a bonus for buying on the web. It has three optional fields, title, subtitle and description, and the shop may display each one differently. Each is a LocalizableText, and because the catalog is requested per player, each can differ per player and use formatted text:
{
"catalog": {
"banner": {
"title": {
"defaultText": "Web shop bonus",
"localizationKey": "BANNER.WEB_BONUS_TITLE"
},
"subtitle": {
"defaultText": "Extra rewards on every pack",
"localizationKey": "BANNER.WEB_BONUS_SUBTITLE",
"formatArguments": { "percent": "10" },
"formatSyntax": "TEXT_FORMAT_SYNTAX_ICU_MESSAGE_FORMAT"
},
"description": {
"defaultText": "Only when you buy on the web.",
"localizationKey": "BANNER.WEB_BONUS_DESCRIPTION"
}
}
}
}With the entry +{percent}% on every pack for BANNER.WEB_BONUS_SUBTITLE, the subtitle reads +10% on every pack. Send only the fields you need: a field that is absent or resolves to blank is left out. The banner is display only: it never changes what is granted or charged. Omit it, or send fields that all resolve to blank, for no banner.
How is this guide?