Internationalizing a React Native app is more than translating visible strings. This guide provides a repeatable workflow for estimating localization effort, organizing translation keys, handling RTL layouts and locale-aware formatting, configuring fallback behavior, and deciding when an app is ready for another language or region.
Overview
React Native internationalization, often called i18n, is the engineering work that makes an app ready for multiple languages and regional conventions. Localization, or l10n, is the process of adapting that prepared app for a specific locale. A locale may describe language, region, numbering rules, calendar preferences, and writing direction. For example, language selection and regional formatting are related, but they are not always the same decision.
A durable implementation separates four concerns:
- Translation resources: the text shown to users, organized by locale and key.
- Locale selection: how the app chooses a language from device settings, account preferences, or an in-app setting.
- Formatting: dates, times, numbers, percentages, units, and currencies presented according to locale.
- Layout and assets: right-to-left support, text expansion, fonts, icons, images, and navigation behavior.
For a React Native app, the safest approach is to establish these boundaries before adding a second language. Keep user-facing text out of components, use stable translation keys, and make formatting explicit rather than assembling strings manually. A localization library can manage resources and interpolation, while the JavaScript internationalization APIs or a compatible formatting layer can handle locale-aware values. Expo and bare React Native projects can follow the same application architecture, but native configuration and build testing should be checked for each target platform.
The objective is not to translate every screen immediately. It is to create a system in which adding a locale is a controlled change with measurable inputs, predictable review, and a repeatable release checklist.
How to estimate
Estimate localization as a set of work units rather than as a single translation task. A practical estimate can use this formula:
Total localization effort = content preparation + translation review + engineering adaptation + device and visual QA + release coordination.
Start with a locale coverage matrix. List every supported locale, its writing direction, translation status, formatting requirements, font needs, and QA status.
| Locale | Direction | Strings | Formatting | Font or asset review | QA status |
|---|---|---|---|---|---|
| en-US | LTR | Complete | US dates, numbers, currency | Complete | Baseline |
| fr-FR | LTR | In review | French dates, numbers, currency | Check text expansion | Pending |
| ar | RTL | Not started | Arabic dates, numbers, currency | Check Arabic font and icons | Pending |
Count translation keys, not only screens. A screen may contain headings, empty states, validation messages, accessibility labels, notification text, settings labels, and pluralized messages. Also identify dynamic content: names, quantities, dates, and values inserted into translated sentences need interpolation rules and test cases.
Use a simple readiness score for each locale:
Locale readiness = completed translation keys + formatting coverage + RTL or layout coverage + device QA coverage.
This is not a percentage of product quality; it is a project control. Mark each category as complete, in progress, or blocked. A locale should not be considered release-ready merely because its translation file is full.
Inputs and assumptions
Before estimating, record the inputs that will affect the work. These assumptions should be visible in the project issue or release plan.
Translation inventory
Export or inspect all user-facing strings, including strings in validation logic, permission explanations, push notification templates, native configuration screens, and error states. Decide whether server-provided content is translated by the app, supplied by an API, or managed separately.
Key structure
Use semantic keys that describe purpose rather than English wording. A template such as checkout.payment.title, checkout.payment.cardNumberLabel, and checkout.payment.invalidCardMessage is easier to maintain than keys based on the original sentence. Keep keys stable when wording changes, and avoid using translated text as a key.
Pluralization and interpolation
Do not create strings by concatenating a number with a noun. Languages can require different plural categories and word order. Store a plural-aware message and pass named values such as count. Test zero, one, and larger values where the product displays quantities. Interpolated user data should be escaped or handled according to the translation library’s rules.
Dates, numbers, and currencies
Define whether dates represent an instant in time, a calendar date, or a time range. Format them at the presentation boundary using the selected locale and the intended time zone. Format decimal separators, grouping, percentages, units, and currencies with locale-aware APIs rather than hard-coded punctuation. Store monetary values in a precise application format and decide which currency is authoritative before rendering it.
RTL and visual assumptions
RTL support requires more than reversing text alignment. Review row direction, padding, margins, icon direction, swipe gestures, drawers, progress indicators, and navigation arrows. Avoid using left and right as semantic layout names when start and end are intended. Check whether an icon communicates direction and needs mirroring; do not mirror icons that represent a fixed object or universal symbol.
Allow for translated text to expand or contract. Fixed-height labels, clipped buttons, single-line assumptions, and narrow tab bars are common sources of localization defects. Verify fonts for every script you support, including fallback behavior when a character is missing.
Worked examples
Example 1: adding a second LTR locale
Suppose a React Native app has 12 screens, 180 translation keys, and one existing locale. The team plans to add a second left-to-right language. The estimate should include an inventory check, translation preparation, implementation of locale selection, locale-aware formatting, review of longer labels, and device testing on both platforms. Because the writing direction stays the same, RTL-specific layout work is not part of this change, but text expansion and pluralization still are.
The team can divide the work into a checklist: 180 keys inventoried, dynamic messages identified, date and currency examples added to tests, translated resources reviewed, long-label screens inspected, and release builds tested with the new locale selected. If any category is incomplete, the locale remains in review regardless of translation completion.
Example 2: adding an RTL locale
Now assume the app adds an RTL locale after the LTR workflow is established. The new estimate includes all normal translation and formatting work plus a layout audit. Review shared components first: stacks, list rows, cards, form fields, headers, bottom navigation, modal actions, and directional icons. Then inspect screens with custom absolute positioning or platform-specific native modules.
A useful test matrix combines locale and state rather than testing only the home screen. For example: LTR with short text, LTR with long text, RTL with short text, RTL with long text, plural count zero, plural count one, plural count greater than one, missing translation, and a device whose system locale differs from the in-app selection. Capture screenshots or run visual checks for each high-risk screen.
Example 3: fallback behavior
Assume a translation key is missing in a newly added locale. Define the expected fallback before release. A common policy is to fall back to the default app language, while logging the missing key in development or QA builds. Avoid silently displaying a raw key to users unless that behavior is an intentional diagnostic mode. Test missing keys, malformed interpolation values, unavailable fonts, and locale changes during an active session.
When to recalculate
Recalculate the localization estimate whenever the inputs change, not only when a new language is requested. Revisit it when the app adds a major feature, introduces a new navigation pattern, changes its date or currency model, adds push notifications, adopts a new design system, or replaces its translation tooling.
Also recalculate before a release when translators return updated resources, when supported React Native, Expo, iOS, or Android versions change, or when a locale exposes a formatting or layout regression. Native configuration and device behavior can change across platform upgrades, so test locale selection, RTL layout, permissions, notifications, and date formatting in release-like builds rather than relying only on a development simulator.
Use this final release checklist:
- Every user-facing string has a semantic key and a defined fallback.
- Plural messages and interpolated values have locale-specific tests.
- Dates, times, numbers, percentages, units, and currencies are formatted deliberately.
- Locale selection is persistent and behaves consistently after relaunch.
- LTR and RTL screens have been checked for alignment, gestures, icons, and navigation.
- Long translations, missing translations, and unsupported characters have been tested.
- Fonts, accessibility labels, push notification text, and native screens are included in review.
- QA results are recorded in the locale coverage matrix before release.
Internationalization becomes easier to maintain when every new locale follows the same inputs, workflow, and acceptance criteria. Keep the matrix with the project, update it as the interface changes, and treat localization regressions as ordinary product defects rather than last-minute translation problems.