Working with locales across platforms
Loco expresses locales with standard codes, or language tags as you might know them. This page explains how developers interact with these codes when using the API. General information about managing custom project locales is available here.
Standard language tags
To open with an example, here are the two most common ways "Greek" might be represented:
"el"(language code only)
"el-GR"(+region code, indicates the country of Greece)
In accordance with RFC 5646, the following variations are also supported by Loco:
"el-Latn"(script code indicates transliteration to the Latin alphabet)
"el-polyton"(variant code indicates Polytonic Greek)
"el-x-custom"(private use extension for whatever else you need)
All Loco project locales follow this syntax, but if your platform uses something different (such as
"gre" instead of
"el") we have ways to ensure compatibility.
Custom language tags
If you need to use different codes from those Loco provides, you can specify a custom language tag for each of your project locales.
This is useful in a number of cases:
- to use an underscore instead of a hyphen, such as
- to use grandfathered tags, such as
- to use alternative ISO standards, such
"iw"for Hebrew, or
- to use completely non-standard references, like
Once a custom language tag is defined it will be used across your project whenever Loco would normally use the standard form. This doesn't affect the functionality of Loco at all. A custom tag is just a label for your own purposes.
The custom language tag is effectively an alias for the tag that Loco would normally use. In addition to this alias, Loco lets you define multiple aliases for targeting different platforms.
For example: You could export Simplified Chinese as
"zh-Hans" for iOS, but
"zh-rCN" for Android.
Platform aliases are used by the Export API in two situations:
- When file paths are generated for Zip archives;
- When the file itself contains language tag references.
Language tags in file paths
For generating Zip archives, Loco defines a default path for each exportable file format. For example:
The language tag that appears in these paths can be customized by setting a platform alias. The following aliases are available for their respective export formats:
"android", "chrome", "codeigniter", "gettext", "ios", "java", "qt", "rails", "symfony".
The Export API also provides a custom file path parameter. This means you don't have to stick to the formats above, you can define any named alias you like and pass it to the Zip exporter. See documentation on custom file paths.
Language tags in file contents
Not all file formats contain language tag references. For those that do, the following aliases affect how they will be written to the relevant export:
"gettext"(defines the contents of the Language header in PO files)
"symfony"(defines the language attributes exported into Symfony XLIFF files)
"rails"(defines the hash keys used in Ruby on Rails YAML files)
"ios"(defines the language attributes exported into Xcode XLIFF files)
"icu"(defines the table key used in ICU resource bundle source files)
"qt"(defines the language attributes exported into Qt Framework TS files)
Note that Loco does not validate your custom language tags against the file format's syntax.
For example: always use a valid
xml:lang attribute when exporting XML files.
Built-in platform formatting
Loco performs some platform-specific formatting automatically unless you override it with your own platform alias.
This is limited to platforms that tend to use underscores instead of hyphens, plus
"android" (which places the letter
"r" before the region). All other platforms use the standard form by default.
For example, if you have locale
"el-GR" and export to Android, the language tag
"el-rGR" will be used unless you've overridden this with an alias called
Similarly this would be exported as
"el_GR" into PO files unless you specified your own
Note that this formatting is also applied if you've specified a custom language tag but not a platform alias.
For example, if you have locale
"zh-Hans" but set your custom tag to "
zh_CN" your Android export will use
"zh-rCN". This is your custom tag, but in the Android style to avoid errors in your application.
If your custom tag is a non-standard format, it will just be used as it is. For example the tag "english" would not be parsed as a language tag so it would be exported without any formatting.
Language tag matching
In many cases it won't matter if your own codes don't exactly match the ones in Loco. However, if you're doing any of the following things it's recommended you keep them the same, or as close as possible:
- presenting language tags to the Loco API.
- exporting files that reference language tags.
- exporting archives containing multiple files.
- extracting specific languages from multi-language files.
Referencing project locales
When using the API you will often need to specify a language, such as when you export a file.
In these cases Loco has to match the parameter you specify to no more than one of your project locales. Care should be taken to avoid ambiguous or incorrect matches, so it's always a good idea to use the exact code and not an alias.
Example 1: (loose match)
"en-GB"(effectively as a wildcard) so if your project contained
["en-GB","fr-FR","de"]you would get a match.
Example 2: (ambiguous)
"en-US"equally. So if your project contained both of these, you would get a 404 error - no match.
Example 3: (reverse match)
"en-GB"does not technically match
"en"(it's more specific), but amongst
["en","fr","de"]it will be matched in reverse as no other tag contradicts.
Matching on aliases
Custom languages tags as described above are only consulted if there is no match for the standard language tag. We don't recommend you rely on this, but it is supported if you find you have to.
"english" matches nothing in
["en","fr","de"] but if you assigned the custom language tag
"en" it would be matched as a final fallback.
Alias matching is case-insensitive and your custom tag is NOT parsed; Hence
"English" would be matched by
"english", but NOT
Platform aliases are only consulted during certain platform-specific import processes and shouldn't generally be used to present a
locale parameter to the API.
Extracting locales from files
Most file formats have a single target language which can't be mistaken, but when importing from multi-language files there exists a case where the locale you specify means two things:
- The project locale you're importing into;
- The locale in the file you're extracting out.
If the locale you specify in this situation is not an exact match for both of these things, then knowing the priority order can be critical. For examples of matching languages in files, see importing XLIFF files.
If you're using custom language tags beware of ambiguity when specifying the language you want to extract.
locale parameter you present to the import API will always be consulted first. If there is no match in the file, then the canonical tag of the matching project locale will be used. Only when these both fail will aliases be consulted.
Notes on the standards
BCP47 and RFC 5646
If you're familiar with these standards, please note a few of Loco's storage limitations:
- Only one variant subtag up to 8 characters is supported per locale.
- Only one extension OR private use subtag up to 12 characters is supported per locale.
- All project locales must have a language. If no language applies, you can specify
- Loco only uses one code per language (e.g. Greek is
"el", and not
- Loco doesn't recognize extended language or grandfathered subtags.
These restrictions only affect how Loco stores locales internally. You can always specify an alias if you need to use unsupported codes.
Regarding the matching of language tags: Loco only very loosely follows some of the principles in RFC 4647.
For example: Loco allows
"el" to match
"el-Latn" as a wildcard, but this is technically wrong.
"el" expands to
"el-Grek" by default and so
"Latn" is a mismatch on the script subtag.
We hope you'll forgive our pragmatic approach!
When Loco first launched it only supported the
"xx_YY" style of locale codes.
This legacy style became optional on November 8th 2015. If your project is old you can upgrade it to use standard language tags in your project settings.