Guides / Prompting and shipping
How to Add Multiple Languages to Your App or Website
Make your app multilingual: translation files, a language switcher, URLs per language, hreflang, dates and currencies, right-to-left layouts and content.
Mythex Team · · 6 min read
To add multiple languages to an app, move every piece of interface text into translation files (one per language), load them with an i18n library, and add a language switcher that remembers the choice. For public pages you want found in search, give each language its own URL such as /fr/ and link the versions with hreflang tags. Then handle the parts people forget: dates, numbers and currencies, longer text in some languages, right-to-left scripts, and content stored in your database.
Words you'll hear
- Internationalisation (i18n): preparing the code to support any language — no hard-coded strings, locale-aware formatting, flexible layouts. The "18" is the number of letters between the i and the n.
- Localisation (l10n): adapting the app for a specific language or market, mostly translation, sometimes also currency, imagery and legal text.
- Locale: a language plus, optionally, a region, like
en-GBorpt-BR.
Do i18n once, and adding each new language becomes mostly translation work.
Options and trade-offs
| Approach | How it works | Good for | Trade-off |
|---|---|---|---|
| i18n library + translation files (e.g. react-i18next, next-intl, vue-i18n) | Text lives in JSON files per locale; components look up keys | Most apps | Initial refactor; translations to maintain |
| Translation management system (e.g. Crowdin, Lokalise, Phrase) | Hosted editor for translators, synced with your files | Many languages, several translators | Paid; another tool to set up |
| Machine or AI translation at build time | Generate draft translations with an API, then review | Getting to many languages quickly | Quality needs checking; API costs |
| Browser or widget auto-translate | Visitor's browser translates the page on the fly | Nothing you control | No quality control; translated pages aren't indexed as yours |
| Separate sites per language | Duplicate site per market | Very different markets | Everything maintained twice |
For most apps, a standard i18n library with translation files is the right base. Draft translations with machine or AI translation if you like, then have fluent speakers review what customers see most.
The parts of a multilingual app
Translation files
Instead of <h1>Welcome back</h1>, the code says t('dashboard.welcome'), and each locale has a file with the text:
{
"dashboard": {
"welcome": "Welcome back, {{name}}",
"items_one": "{{count}} item",
"items_other": "{{count}} items"
}
}
Use placeholders for variables rather than joining sentence fragments — word order differs between languages. And use the library's plural rules: English has two forms (1 item, 2 items), but some languages have three, four or more.
Formatting dates, numbers and money
Don't format these by hand. The browser's built-in Intl API formats for any locale: 1,234.5 in English is 1.234,5 in German; dates switch between day-first and month-first; currency symbols move. Store dates in UTC and money as numbers with a currency code, and format only for display.
Layout that stretches
Translated text is often longer than English — German and Finnish words in particular. Avoid fixed-width buttons and truncated labels, and test with your longest language.
Right-to-left languages
Arabic, Hebrew, Persian and Urdu read right to left. Set dir="rtl" on the page for those locales and use CSS logical properties (margin-inline-start instead of margin-left; in Tailwind, ms-4 instead of ml-4) so the layout mirrors itself. Icons that imply direction, like arrows, need flipping too.
Language switcher and detection
Show a switcher on every page, labelled with each language's own name ("Deutsch", "Français", "العربية") rather than flags — flags represent countries, not languages. Detect the browser's preferred language on the first visit to suggest a version, but let the visitor's explicit choice win and remember it.
URLs and SEO
For pages you want in search results, each language needs its own URL. As of September 2026, Google's guidance for multilingual sites is:
- Separate URLs per language — subdirectories (
example.com/fr/) are the simplest; subdomains and country domains also work. URL parameters (?lang=fr) are not recommended. - Don't switch language by cookie or browser setting alone; Google's crawler may never see the other versions.
- Don't auto-redirect by language; link between versions instead.
- Use hreflang to tell Google which pages are translations of each other. Each version must list itself and all the others, or the annotations may be ignored. Add
x-defaultfor the fallback page. - Google detects a page's language from its visible content, not from
langor hreflang — so translate the whole page, not just the menu.
Still set <html lang="fr"> on each version: screen readers use it to pick the right pronunciation, which is an accessibility requirement.
Logged-in app screens don't need to be indexed, so for those, storing the language in the user's profile is fine. See SEO for AI-built websites for getting public pages crawled in the first place.
Content in your database
Interface text lives in files; content like product names, blog posts and categories lives in the database. Two common patterns:
- A translations table:
product_translations (product_id, locale, name, description). Clean and scales to many languages. - A JSON column per field:
name: {"en": "...", "fr": "..."}. Simpler for a few languages.
Decide what happens when a translation is missing — usually fall back to the default language rather than showing blank space.
Emails and notifications
Store each user's language and use it for emails, notifications and PDFs too. It's easy to translate the app and forget that the welcome email still arrives in English.
Prompts that work
Add internationalisation with react-i18next. Move every user-visible string into locales/en.json with namespaced keys, use interpolation and plural rules instead of string concatenation, and format dates, numbers and prices with Intl using the current locale. Don't change any wording yet.
Add French and German. Public marketing pages get /fr/ and /de/ URL prefixes with English at the root, hreflang links on every page (including self-reference and x-default), and html lang set per page. Add a language switcher showing each language's native name. For logged-in pages, store the language on the user's profile.
Add Arabic with right-to-left support: set dir="rtl" for Arabic, replace left/right margins and paddings with logical properties, mirror directional icons, and check that forms and tables still read correctly.
Step by step
- Pick your first extra language based on real demand — where your visitors or customers are.
- Internationalise the code: move strings to files, add plurals and
Intlformatting. Ship this with English only and check nothing changed. - Decide the URL structure for public pages and add hreflang.
- Translate: draft with machine or AI translation, then review with a fluent speaker. Give translators context — a word like "Book" is a noun on one screen and a verb on another.
- Translate database content and set fallbacks.
- Localise the rest: emails, error messages, legal pages, images with text in them.
- Test each language at phone width, and with right-to-left if relevant.
- Set up a process so new features ship with translations, not months later.
Common mistakes
- Concatenating sentences (
"You have " + n + " messages"), which breaks in other languages. - Hard-coded text left in components, error messages and validation strings.
- Formatting dates and prices manually.
- Flags for languages, and auto-redirects that trap people in the wrong version.
- One URL for all languages on pages you want indexed.
- Missing hreflang return links, so Google ignores the annotations.
- Translating the interface but not the content, or the other way round.
- Unreviewed machine translation on pricing, legal and checkout pages.
Multilingual checklist
- No hard-coded user-visible strings; plural rules and placeholders used
- Dates, numbers and currencies formatted with
Intl - Language switcher with native names on every page; choice remembered
- Separate URLs per language for public pages; no forced redirects
- hreflang on every version, including self and x-default
-
html lang(anddir="rtl"where needed) set per page - Database content translated with sensible fallbacks
- Emails and notifications sent in the user's language
- Customer-facing text reviewed by a fluent speaker
Multiple languages on Mythex
On Mythex, you add languages by asking in chat — there is no separate translation panel — so the prompts above work as written. Do the internationalisation step first and check it in Preview before adding languages; it is a large refactor, and a chat checkpoint gives you a point to roll back to if something breaks (chat and checkpoints). If you want the app to translate content automatically with an AI or translation API, that uses your own API key, stored in project settings (environment variables and secrets); how to use LLM APIs explains the costs. Publish again once the new languages are ready.
Questions
What is the difference between i18n and localisation?
Internationalisation (i18n) is preparing the code so it can support many languages: no hard-coded text, locale-aware dates and numbers, layouts that handle longer words and right-to-left scripts. Localisation (l10n) is the work of adapting it for one language or market, mainly translation.
Can I just use machine translation or AI to translate my app?
For a first draft, yes — modern machine and AI translation is good at interface text. Have a fluent speaker review anything customer-facing, especially legal text, pricing and marketing copy, because tone and small errors matter there.
Should each language have its own URL?
For public pages you want in search results, yes. Google recommends separate URLs per language, such as /fr/ and /de/, rather than switching language by cookie or browser setting, because its crawler may otherwise only ever see one version.
Should I redirect visitors based on their browser language?
Suggest, don't force. Google advises against automatic language redirects because they can stop people and crawlers from reaching other versions. Show a small prompt offering the matching language and a visible switcher on every page.