Search Documentation
Search for a documentation page...
Localization
Serve translated catalog content and per-currency prices through the API.
A YNS store can sell in more than one language and price in more than one currency. Both are driven by the Localization module, and both surface through the API as request parameters rather than separate endpoints — the same product, asked for differently.
Discover what's enabled
Start with GET /api/v1/me. Its settings block tells you what the merchant has switched on:
| Field | What it drives |
|---|---|
store.currency | The base currency — always available |
store.locale | The store's own locale |
settings.defaultLanguage | The language content falls back to |
settings.enabledLanguages | Which extra languages to offer in a switcher |
settings.enabledCurrencies | Which currencies have prices set |
Build your language and currency switchers from these two lists rather than hard-coding them, and the storefront follows whatever the merchant enables later.
Translated content
Pass lang with a locale code to overlay translated fields onto the response.
Supported on:
| Endpoint | Translated fields |
|---|---|
| Products | name, slug, summary, content, seo.title, seo.description |
| Collections | Name, slug, description, SEO fields |
| Categories | Name, slug, description, SEO fields |
| Brands | Name, slug, description, SEO fields |
| Posts | title, slug, content, seo.title, seo.description |
Fields with no translation keep their default-language value, so a partially translated catalog never returns blanks. Locale codes are the full form — en-US, pl-PL, es-ES, de-DE.
Translated slugs are returned too. If you route by slug, resolve the incoming slug in the same language you rendered the links in.
Per-currency prices
Pass currency with a three-letter code to price a response in one of the store's enabled currencies.
Supported on Products, Variants, Carts, Events, Coupons, Promotions, Shipping, Orders, and Analytics.
Prices are set per currency by the merchant rather than converted at request time, so the number you get back is the exact price they chose for that market. Product responses only include prices for currencies the store has enabled.
When writing products you can supply the extra prices directly:
Writing translations
Use the translation PUT endpoints to create, update, or delete translated content for products, collections, and categories. Each call targets one entity and one locale. Requires the catalog:write scope.
The entity can be identified by UUID or slug. The locale must be a supported locale code (e.g. pl-PL, de-DE) and cannot be the store's base locale — base content is edited via the entity's own PATCH endpoint.
Behaviour
- Upsert: if a translation row exists for this entity + locale, it is updated. Otherwise a new row is created.
- Delete: sending an empty body (all fields omitted or blank) deletes the translation row entirely, so the entity falls back to its base-language content.
- The locale does not have to be enabled in
settings.enabledLanguages— you can stage translations before flipping the language on.
Product translation fields
| Field | Type | Description |
|---|---|---|
name | string | Translated product name |
slug | string | Translated URL slug |
summary | string | Translated short summary |
content | object | Translated description (TipTap JSONContent) |
badgeContent | string | Translated badge text |
seoTitle | string | Translated SEO title |
seoDescription | string | Translated SEO description |
All fields are optional. The schema is strict — unknown fields are rejected.
Post translation fields
| Field | Type | Description |
|---|---|---|
title | string | Translated post title |
slug | string | Translated URL slug |
content | object | Translated body (TipTap JSONContent) |
seoTitle | string | Translated SEO title |
seoDescription | string | Translated SEO description |
Collection and category translation fields
Collections and categories share the same field set:
| Field | Type | Description |
|---|---|---|
name | string | Translated name |
slug | string | Translated URL slug |
description | object | Translated description (TipTap JSONContent) |
longDescription | object | Translated long description (TipTap JSONContent) |
seoTitle | string | Translated SEO title |
seoDescription | string | Translated SEO description |
Response
The response includes productId, collectionId, categoryId, or postId depending on the entity type, plus the locale and a deleted flag indicating whether the translation was removed (all fields were empty).
Errors
| Status | Meaning |
|---|---|
400 | Unsupported locale, or the locale is the store's base locale |
404 | No entity matches the identifier |
409 | A translation with this slug already exists for the same locale |
Putting it together
- Call
GET /api/v1/meonce and cache it. - Render switchers from
enabledLanguagesandenabledCurrencies. - Thread the visitor's choice through every catalog call as
langandcurrency. - Fall back to
defaultLanguageandstore.currencywhen the visitor hasn't chosen.
Related
- Store API — what's enabled for this store
- Products API — the main consumer of both parameters
- Merchant-facing setup: Sell in multiple languages