Formats
.stringsdict
Plural forms for a .strings table. Written next to its singulars by the same sync, with one entry per CLDR category the locale has.
What you get
Everything the editor does, through the files you already ship.
Every plural form a language has
Each locale gets exactly the CLDR categories it uses, Arabic six and Japanese one, written in the format's own plural shape.
Five checks on every save
Placeholders, length, terminology, consistency and missing translations are flagged on the row they concern, not in production.
Scriptable from the CLI
Push, pull and sync from a terminal, a build phase or a coding agent's shell, with a token in the environment.
The CLIEverything is an HTTP call
Project tokens carry read, push and manage scopes, so a CI token that pushes files cannot delete keys.
The HTTP API
Set it up
From nothing to every language.
Step 1: Format the count through the dictionary
Foundation picks the category for the count at runtime. The key holds a format string whose
%#@name@refers to the plural rule, andlocalizedStringWithFormatfills it in.CartViewController.swiftlet format = NSLocalizedString("cart.items", comment: "Items in the cart") countLabel.text = String.localizedStringWithFormat(format, cart.count)Step 2: Install the CLI and log in
Homebrew or the one-line installer, then a token issued per project under Settings, Integrations. The read scope pulls; push writes source files and values; manage creates and deletes keys.
shellbrew install anylocale/tap/anylocale anylocale login --project my-appStep 3: Sync, and the .stringsdict comes along
A table with at least one plural key gets a .stringsdict beside its .strings file, with one entry per category the locale uses and the value type the source declared.
shellanylocale sync --project my-app --out-dir Sources/Resourcesde.lproj/Localizable.stringsdict<?xml version="1.0" encoding="UTF-8"?> <plist version="1.0"> <dict> <key>cart.items</key> <dict> <key>NSStringLocalizedFormatKey</key> <string>%#@count@</string> <key>count</key> <dict> <key>NSStringFormatSpecTypeKey</key> <string>NSStringPluralRuleType</string> <key>NSStringFormatValueTypeKey</key> <string>d</string> <key>one</key> <string>1 Artikel</string> <key>other</key> <string>%d Artikel</string> </dict> </dict> </dict> </plist>Step 4: Write plural values from a script
Every category the locale has must be supplied at once; a partial set is refused and nothing is written.
shellanylocale values set --project my-app --name cart.items \ --value de.one="1 Artikel" \ --value de.other="%d Artikel"
Good to know
- Which categories exist is decided per locale: German has one and other, Polish adds few and many, Japanese has other only.
- Keys with several named variables are edited in the app, not through values set.
Questions
- Which plural categories does each language get?
- Exactly the ones CLDR defines for it: German has one and other, Polish adds few and many, Arabic has six and Japanese only other. The editor shows one field per category, so nothing is guessed.
- Can plurals be written from a script?
- Yes, with values set, one value per category. Every category the locale has must be supplied in the same call; a partial set is refused and nothing is written.
- What about keys with several counted variables?
- A key with more than one named variable is edited in the app, where each combination has its own field. The CLI and the device files leave those keys alone.
- Which other formats can the same project be pulled in?
- .xcstrings, .strings with .stringsdict, strings.xml, JSON, next-intl messages and CSV. A project is not tied to the format it was pushed in, which is how an iOS app and an Android app share one catalog..xcstrings.stringsstrings.xmlJSONnext-intlCSV
Start with the file your app already ships.
After checkout, import one strings file and read the first drafts within minutes.
Nothing to connect and nothing to install. The CLI is optional.