android-localisation 1.1.3__tar.gz → 1.5.0__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {android_localisation-1.1.3/android_localisation.egg-info → android_localisation-1.5.0}/PKG-INFO +210 -16
- {android_localisation-1.1.3 → android_localisation-1.5.0}/README.md +208 -14
- android_localisation-1.5.0/android_localisation/__init__.py +5 -0
- {android_localisation-1.1.3 → android_localisation-1.5.0}/android_localisation/cli.py +40 -5
- android_localisation-1.5.0/android_localisation/locales.py +72 -0
- android_localisation-1.5.0/android_localisation/store_listing.py +255 -0
- {android_localisation-1.1.3 → android_localisation-1.5.0}/android_localisation/translate.py +78 -24
- {android_localisation-1.1.3 → android_localisation-1.5.0/android_localisation.egg-info}/PKG-INFO +210 -16
- {android_localisation-1.1.3 → android_localisation-1.5.0}/android_localisation.egg-info/SOURCES.txt +2 -0
- {android_localisation-1.1.3 → android_localisation-1.5.0}/pyproject.toml +2 -2
- android_localisation-1.1.3/android_localisation/__init__.py +0 -5
- {android_localisation-1.1.3 → android_localisation-1.5.0}/LICENSE +0 -0
- {android_localisation-1.1.3 → android_localisation-1.5.0}/MANIFEST.in +0 -0
- {android_localisation-1.1.3 → android_localisation-1.5.0}/android_localisation/__main__.py +0 -0
- {android_localisation-1.1.3 → android_localisation-1.5.0}/android_localisation/fix.py +0 -0
- {android_localisation-1.1.3 → android_localisation-1.5.0}/android_localisation/java/VerifyStrings.java +0 -0
- {android_localisation-1.1.3 → android_localisation-1.5.0}/android_localisation/resources.py +0 -0
- {android_localisation-1.1.3 → android_localisation-1.5.0}/android_localisation/setup_path.py +0 -0
- {android_localisation-1.1.3 → android_localisation-1.5.0}/android_localisation/updates.py +0 -0
- {android_localisation-1.1.3 → android_localisation-1.5.0}/android_localisation/verify.py +0 -0
- {android_localisation-1.1.3 → android_localisation-1.5.0}/android_localisation.egg-info/dependency_links.txt +0 -0
- {android_localisation-1.1.3 → android_localisation-1.5.0}/android_localisation.egg-info/entry_points.txt +0 -0
- {android_localisation-1.1.3 → android_localisation-1.5.0}/android_localisation.egg-info/top_level.txt +0 -0
- {android_localisation-1.1.3 → android_localisation-1.5.0}/setup.cfg +0 -0
{android_localisation-1.1.3/android_localisation.egg-info → android_localisation-1.5.0}/PKG-INFO
RENAMED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: android-localisation
|
|
3
|
-
Version: 1.
|
|
4
|
-
Summary: Zero-dependency Android strings.xml
|
|
3
|
+
Version: 1.5.0
|
|
4
|
+
Summary: Zero-dependency Android strings.xml and Google Play store listing translation using LLMs (Gemini, OpenAI, Anthropic, Ollama).
|
|
5
5
|
License: MIT
|
|
6
6
|
Project-URL: Homepage, https://github.com/BharathKmalviya/android-llm-localization
|
|
7
7
|
Project-URL: Repository, https://github.com/BharathKmalviya/android-llm-localization
|
|
@@ -34,7 +34,7 @@ Dynamic: license-file
|
|
|
34
34
|
|
|
35
35
|
**PyPI:** [`android-localisation`](https://pypi.org/project/android-localisation/) · **CLI:** `android-localise` · **Repo:** [android-llm-localization](https://github.com/BharathKmalviya/android-llm-localization)
|
|
36
36
|
|
|
37
|
-
Translate your Android `strings.xml` into multiple languages using AI — Gemini, OpenAI, Anthropic, or a local model via Ollama.
|
|
37
|
+
Translate your Android `strings.xml` and Google Play store listing into multiple languages using AI — Gemini, OpenAI, Anthropic, or a local model via Ollama.
|
|
38
38
|
|
|
39
39
|
---
|
|
40
40
|
|
|
@@ -121,10 +121,10 @@ That's the full workflow. Run these three commands after every time you update y
|
|
|
121
121
|
|
|
122
122
|
When you run `android-localise translate --api-key YOUR_KEY`, here's exactly what it does:
|
|
123
123
|
|
|
124
|
-
1.
|
|
125
|
-
2.
|
|
126
|
-
3. Sends
|
|
127
|
-
4. Parses the response and checks duplicate/unexpected/missing resources, attributes, inline markup, item structure, control escapes and format arguments. A valid result replaces the file atomically; new folders are created only when saving. `--dry-run` shows a diff without writing any files or creating folders
|
|
124
|
+
1. Reads `app/src/main/res/values/strings.xml` by default, or the XML file supplied with `--source`. `--source-language` identifies its language (default `en-US`)
|
|
125
|
+
2. Combines `--languages` and `--languages-file`, expands `all`, removes duplicates and applies `--exclude-languages`. Android qualifiers and conventional language tags are accepted. Without an explicit list, scans existing locale folders in the destination directory, skipping configuration-only folders such as `values-night`, `values-land`, `values-car`, and `values-sw600dp`. The destination defaults to `--res-dir`, or can be set with `--output-dir`
|
|
126
|
+
3. Sends the source XML to the LLM with its language, app context and instructions to preserve resource structure, protected values, namespaces and format specifiers. With `--missing-only`, requests only resources absent from the target file; existing resources remain untouched, and complete locales make no API request
|
|
127
|
+
4. Parses the response and checks duplicate/unexpected/missing resources, attributes, inline markup, item structure, control escapes and format arguments. A valid result replaces the file atomically; new folders are created only when saving. `--skip-existing` validates existing files and skips them without API calls. `--dry-run` shows a diff without writing any files or creating folders
|
|
128
128
|
5. Waits 5 seconds between each language request to avoid hitting API rate limits
|
|
129
129
|
|
|
130
130
|
**Defaults used when you don't specify anything:**
|
|
@@ -145,7 +145,8 @@ Normal translation still replaces the whole locale file. Use `--missing-only` to
|
|
|
145
145
|
|
|
146
146
|
## Setup
|
|
147
147
|
|
|
148
|
-
|
|
148
|
+
Provide source XML at `app/src/main/res/values/strings.xml` by default, or supply
|
|
149
|
+
another file with `--source` and its language with `--source-language`.
|
|
149
150
|
|
|
150
151
|
For target languages, you have two options:
|
|
151
152
|
|
|
@@ -155,6 +156,26 @@ android-localise translate --api-key YOUR_KEY --languages hi,es,fr,de
|
|
|
155
156
|
```
|
|
156
157
|
This translates into Hindi, Spanish, French and German, creating each folder and `strings.xml` when its translation passes validation.
|
|
157
158
|
|
|
159
|
+
To translate into the same 86-locale catalog used for store listings:
|
|
160
|
+
|
|
161
|
+
```bash
|
|
162
|
+
android-localise translate --api-key YOUR_KEY --languages all
|
|
163
|
+
```
|
|
164
|
+
|
|
165
|
+
`all` is case-insensitive and can be combined with extra languages. The bundled catalog is shared
|
|
166
|
+
with `store-listing` and mapped to [Android resource qualifiers](https://developer.android.com/guide/topics/resources/providing-resources#AlternativeResources):
|
|
167
|
+
`hi-IN` becomes `values-hi-rIN`, `pt-BR` becomes `values-pt-rBR`, `es-419`
|
|
168
|
+
becomes `values-b+es+419`, and `fil` becomes `values-b+fil`. Regional variants,
|
|
169
|
+
including English ones, remain separate; `values/strings.xml` remains the source.
|
|
170
|
+
This is the bundled Play locale set, not every possible Android locale.
|
|
171
|
+
|
|
172
|
+
The same XML validation, atomic saves, delay, `--missing-only` and `--dry-run`
|
|
173
|
+
behavior applies to each locale. Normal translation refreshes existing files;
|
|
174
|
+
use `--languages all --missing-only` to keep reviewed resources. Generating or
|
|
175
|
+
previewing all locales can use 86 translation requests plus provider retries;
|
|
176
|
+
complete locales in missing-only mode skip API calls. No folders are created
|
|
177
|
+
during previews or before their translation passes validation.
|
|
178
|
+
|
|
158
179
|
**Option B — pre-create folders yourself:**
|
|
159
180
|
```
|
|
160
181
|
app/src/main/res/
|
|
@@ -164,7 +185,7 @@ app/src/main/res/
|
|
|
164
185
|
├── values-es/
|
|
165
186
|
└── values-fr/
|
|
166
187
|
```
|
|
167
|
-
Run `android-localise translate --api-key YOUR_KEY` and it picks up locale folders, creating `strings.xml` inside each one after successful translation. Locale examples include `values-hi`, `values-es-rES`, `values-b+zh+Hans`, and `values-en-night`; qualifier-only folders are skipped. `--languages` accepts the same forms without the optional `values-` prefix and rejects path separators or non-locale names.
|
|
188
|
+
Run `android-localise translate --api-key YOUR_KEY` and it picks up locale folders, creating `strings.xml` inside each one after successful translation. Locale examples include `values-hi`, `values-es-rES`, `values-b+zh+Hans`, and `values-en-night`; qualifier-only folders are skipped. `--languages` accepts the same forms without the optional `values-` prefix, plus conventional tags such as `es-ES` or `zh-Hant-TW`, and rejects path separators or non-locale names.
|
|
168
189
|
|
|
169
190
|
**Get a free API key:** [Google Gemini AI Studio](https://aistudio.google.com/) → Get API Key. The free tier handles most apps without hitting limits.
|
|
170
191
|
|
|
@@ -177,6 +198,7 @@ typical workflow. Each command has detailed help with its options and examples:
|
|
|
177
198
|
|
|
178
199
|
```bash
|
|
179
200
|
android-localise translate --help
|
|
201
|
+
android-localise store-listing --help
|
|
180
202
|
android-localise fix --help
|
|
181
203
|
android-localise verify --help
|
|
182
204
|
android-localise models --help
|
|
@@ -207,7 +229,13 @@ android-localise translate \
|
|
|
207
229
|
| `--api-key` | Your API key | reads from env var |
|
|
208
230
|
| `--provider` | Which AI to use: `gemini` `openai` `anthropic` `custom` | `gemini` |
|
|
209
231
|
| `--model` | Specific model to use | see [Providers](#providers) |
|
|
210
|
-
| `--languages` | Comma-separated
|
|
232
|
+
| `--languages` | Comma-separated Android/conventional codes and/or `all`, e.g. `all,zu` or `hi,es-ES,b+es+419` | scan existing destination locale folders |
|
|
233
|
+
| `--languages-file` | UTF-8 comma/newline language list; combines with `--languages` | none |
|
|
234
|
+
| `--exclude-languages` | Remove exact normalized locales after selection/discovery | none |
|
|
235
|
+
| `--source` | Read a custom XML source file | `RES_DIR/values/strings.xml` |
|
|
236
|
+
| `--source-language` | Language tag for source XML | `en-US` |
|
|
237
|
+
| `--output-dir` | Save translated XML into this Android res/ directory | `--res-dir` |
|
|
238
|
+
| `--skip-existing` | Validate and skip existing XML files without API calls | off; incompatible with `--missing-only` |
|
|
211
239
|
| `--app-context` | One-line description of your app | — |
|
|
212
240
|
| `--res-dir` | Path to your `res/` folder | `app/src/main/res` |
|
|
213
241
|
| `--base-url` | API endpoint for local/custom providers | — |
|
|
@@ -229,6 +257,172 @@ Validation permits positional placeholder reordering such as `%s %d` becoming `%
|
|
|
229
257
|
|
|
230
258
|
---
|
|
231
259
|
|
|
260
|
+
### `store-listing`
|
|
261
|
+
|
|
262
|
+
Translate an existing Google Play listing's **app name**, **short description**
|
|
263
|
+
and **full description**, using the same providers, keys, model defaults,
|
|
264
|
+
model-not-found fallbacks and timeout handling as `translate`.
|
|
265
|
+
|
|
266
|
+
Create a UTF-8 `listing.json` containing exactly these three nonempty strings:
|
|
267
|
+
|
|
268
|
+
```json
|
|
269
|
+
{
|
|
270
|
+
"app_name": "Pocket Notes",
|
|
271
|
+
"short_description": "Write and organize your notes",
|
|
272
|
+
"full_description": "Write notes and organize them in folders.\n\nFind saved notes with search."
|
|
273
|
+
}
|
|
274
|
+
```
|
|
275
|
+
|
|
276
|
+
Use your actual app details. JSON represents paragraph breaks as `\n`; this
|
|
277
|
+
command translates supplied copy and does not infer features from Android XML.
|
|
278
|
+
|
|
279
|
+
```bash
|
|
280
|
+
# Translate every bundled Google Play listing locale
|
|
281
|
+
android-localise store-listing --source listing.json --languages all
|
|
282
|
+
# Or select languages manually
|
|
283
|
+
android-localise store-listing --source listing.json --languages hi,es-ES,pt-BR
|
|
284
|
+
# Keep the original brand/app name and preview translations
|
|
285
|
+
android-localise store-listing --source listing.json --languages ja,zh-TW --keep-app-name --dry-run
|
|
286
|
+
# Explicitly refresh reviewed files when the source changes
|
|
287
|
+
android-localise store-listing --source listing.json --languages hi --overwrite
|
|
288
|
+
```
|
|
289
|
+
|
|
290
|
+
Outputs are readable UTF-8 `store-listings/hi.json`, `store-listings/es-ES.json`,
|
|
291
|
+
etc., with the same three keys. Review the text and copy each field into its
|
|
292
|
+
language's Play Console listing; JSON is a local output format, not a Play
|
|
293
|
+
Console import file. The CLI does not upload or publish a listing.
|
|
294
|
+
|
|
295
|
+
| Flag | Description | Default |
|
|
296
|
+
|---|---|---|
|
|
297
|
+
| `--source` | UTF-8 JSON source listing | required |
|
|
298
|
+
| `--languages` | Play tags and/or `all`, e.g. `all,zu` or `hi-IN,es-ES` | required unless `--languages-file` supplies a list |
|
|
299
|
+
| `--languages-file` | UTF-8 comma/newline language list; combines with `--languages` | none |
|
|
300
|
+
| `--exclude-languages` | Remove exact normalized Play tags after selection | none |
|
|
301
|
+
| `--source-language` | Source listing language tag | `en-US` |
|
|
302
|
+
| `--output-dir` | Directory for `LOCALE.json` output | `store-listings` |
|
|
303
|
+
| `--keep-app-name` | Preserve the source app name exactly | off; name is localized with brand-preservation instructions |
|
|
304
|
+
| `--overwrite` | Replace existing locale files after validation | off; existing valid files are skipped |
|
|
305
|
+
| `--dry-run` | Generate, validate and display diffs without files/directories being written | off; API usage applies |
|
|
306
|
+
| `--provider` | `gemini`, `openai`, `anthropic`, `custom` | `gemini` |
|
|
307
|
+
| `--model` | Pin any supported model and disable fallbacks | provider default |
|
|
308
|
+
| `--api-key` | Key, or provider-specific environment variable / `API_KEY` | environment |
|
|
309
|
+
| `--base-url` | OpenAI-compatible endpoint; required for `custom` | provider endpoint |
|
|
310
|
+
| `--app-context` | Terminology context; source copy remains the source of facts | none |
|
|
311
|
+
| `--sleep` | Delay between requests, including correction/fallback requests | `5.0` seconds |
|
|
312
|
+
| `--timeout` | Per-response timeout; up to three attempts on timeout | `180` seconds |
|
|
313
|
+
|
|
314
|
+
**Validation:** source and translated fields must fit **30 / 80 / 4,000 characters**
|
|
315
|
+
respectively, as specified in [Google Play's product details guidance](https://support.google.com/googleplay/android-developer/answer/9859152).
|
|
316
|
+
Counts use Python Unicode code points, including spaces, punctuation, newlines
|
|
317
|
+
and any HTML markup, rather than UTF-8 bytes or visual glyphs. Check final counts
|
|
318
|
+
in Play Console too. Names and short descriptions must be single-line text.
|
|
319
|
+
Missing/extra/duplicate keys, blank fields, invalid JSON, unsupported controls
|
|
320
|
+
and unpaired surrogates are rejected. Overlong or otherwise invalid model output
|
|
321
|
+
gets up to **two correction requests**, with validation feedback; this can incur
|
|
322
|
+
additional API usage. Text is never blindly truncated. After validation the
|
|
323
|
+
complete listing is saved atomically. Rejected output preserves existing files;
|
|
324
|
+
other languages continue and any failure produces exit code 1.
|
|
325
|
+
|
|
326
|
+
Existing files are validated and skipped without translation API calls unless
|
|
327
|
+
`--overwrite` is set, including during a dry run. An invalid existing file fails
|
|
328
|
+
instead of being silently replaced; `--overwrite` explicitly regenerates it.
|
|
329
|
+
`--dry-run --overwrite` previews changes to existing files. Source/output path
|
|
330
|
+
collisions are rejected. Locale tags are syntax-checked and normalized (for
|
|
331
|
+
example `pt-br` becomes `pt-BR`); duplicate tags run once. This does not check
|
|
332
|
+
manual codes against Google Play's supported-language catalog. Choose tags available in your Console;
|
|
333
|
+
Android forms such as `values-hi`, `es-rES` and `b+zh+Hans` are not accepted here.
|
|
334
|
+
|
|
335
|
+
`--languages all` expands to the **86 store-listing locales** in
|
|
336
|
+
[Google Play's available-language list](https://support.google.com/googleplay/android-developer/answer/9844778?hl=en),
|
|
337
|
+
verified on **2026-10-02** and bundled with this release. It includes regional
|
|
338
|
+
variants and the source locale if present in the list. It does not fetch or
|
|
339
|
+
change the catalog at runtime. `all` is case-insensitive and can be combined with
|
|
340
|
+
manual additions. Use `--languages`, `--languages-file`, or both. Manual selection retains normalization and
|
|
341
|
+
duplicate removal. Each locale uses its own request, subject to existing-file
|
|
342
|
+
skips, correction/fallback requests and the configured delay. API usage applies
|
|
343
|
+
to all generated locales, including previews. Existing valid files still skip
|
|
344
|
+
unless `--overwrite` is set.
|
|
345
|
+
|
|
346
|
+
**Translation prompt:** includes the supplied [metadata policy](https://play.google.com/about/storelisting-promotional/metadata),
|
|
347
|
+
[Help Centre guidance](https://support.google.com/googleplay/android-developer/answer/9866151),
|
|
348
|
+
[programme policies](https://play.google.com/about/developer-content-policy) and
|
|
349
|
+
[advance-notice guidance](https://support.google.com/googleplay/android-developer/answer/6320428)
|
|
350
|
+
as publishing references, alongside text guidance reviewed on **2026-10-02**.
|
|
351
|
+
It asks for accurate, natural descriptions without invented claims, keyword
|
|
352
|
+
stuffing, misleading affiliations or anonymous testimonials. App names and
|
|
353
|
+
short descriptions avoid ranking/promotion language and decorative emoji;
|
|
354
|
+
short descriptions also avoid calls to action. Existing factual limitations,
|
|
355
|
+
URLs, brand names, required disclosures and full-description markup should be
|
|
356
|
+
preserved. Unsupported promotional wording should become factual copy.
|
|
357
|
+
These semantic rules are prompt instructions, not automated policy checks.
|
|
358
|
+
No policy pages are fetched by the CLI at runtime, so review the current linked
|
|
359
|
+
policies and translated claims before submitting. Advance notice remains a
|
|
360
|
+
separate developer step if eligible; no notice, permission or approval is implied.
|
|
361
|
+
|
|
362
|
+
**Manual check:** translate two languages, review all three fields with a native
|
|
363
|
+
speaker and check their counts in Play Console. Rerun to confirm existing files
|
|
364
|
+
skip, then use `--overwrite --dry-run` to review refreshes without saving.
|
|
365
|
+
Try a source name longer than 30 characters to confirm rejection before any
|
|
366
|
+
translation request.
|
|
367
|
+
For all-locale coverage, run `--languages all` into a separate output directory,
|
|
368
|
+
confirm 86 successful JSON outputs, then rerun and confirm 86 skips. Use a manual
|
|
369
|
+
list such as `hi-IN,es-ES` to confirm only those two outputs are generated.
|
|
370
|
+
|
|
371
|
+
---
|
|
372
|
+
|
|
373
|
+
### Composing translation commands
|
|
374
|
+
|
|
375
|
+
Both commands accept languages from the CLI, a UTF-8 file, or both. File entries
|
|
376
|
+
can be comma-separated or one per line, with blank lines and `#` comments.
|
|
377
|
+
For example, `languages.txt` can contain:
|
|
378
|
+
|
|
379
|
+
```text
|
|
380
|
+
# Shared targets; conventional tags work in both commands
|
|
381
|
+
hi-IN
|
|
382
|
+
es-ES,pt-BR
|
|
383
|
+
zh-Hant-TW
|
|
384
|
+
```
|
|
385
|
+
|
|
386
|
+
```bash
|
|
387
|
+
# All bundled locales plus an extra, excluding exact regional variants
|
|
388
|
+
android-localise translate --languages all,zu --exclude-languages en-US,en-GB
|
|
389
|
+
android-localise store-listing --source listing.json --languages all,zu --exclude-languages en-US,en-GB
|
|
390
|
+
# Reuse a language file and add more targets
|
|
391
|
+
android-localise translate --languages-file languages.txt --languages de-DE --dry-run
|
|
392
|
+
android-localise store-listing --source listing.json --languages-file languages.txt --languages de-DE --dry-run
|
|
393
|
+
# Translate another source language into a separate Android resource directory
|
|
394
|
+
android-localise translate --source source/strings.xml --source-language fr-FR --output-dir translated/res --languages hi-IN,es-ES --skip-existing
|
|
395
|
+
```
|
|
396
|
+
|
|
397
|
+
Ordering is CLI entries first, then file entries. `all` expands wherever it
|
|
398
|
+
appears; duplicates run once. XML equivalent qualifiers such as `es-ES`,
|
|
399
|
+
`es-rES` and `b+es+ES` run once, preserving the first selected folder spelling.
|
|
400
|
+
Exclusions apply after expansion and use exact locale identity: excluding `en`
|
|
401
|
+
does not exclude `en-US` or every English region. You can pass Android forms to
|
|
402
|
+
XML exclusions, and conventional tags to both commands. Listing language files
|
|
403
|
+
accept Play tags only. Manual tags are syntax-checked, not restricted to the
|
|
404
|
+
bundled Play catalog; verify Play Console supports any additional listing locale.
|
|
405
|
+
An empty final selection or invalid language/file fails before API calls or
|
|
406
|
+
folder creation. Source/output collisions, including linked source files, are
|
|
407
|
+
rejected. Provider, model, custom endpoint, context, delays, timeout and previews
|
|
408
|
+
remain independently configurable.
|
|
409
|
+
|
|
410
|
+
XML preservation choices are whole-file refresh (default), `--missing-only`
|
|
411
|
+
(fill missing resources) or `--skip-existing` (skip complete valid files).
|
|
412
|
+
The two preservation flags cannot be combined. Listing preservation remains
|
|
413
|
+
skip-by-default with explicit `--overwrite`. Preview flags can combine with any
|
|
414
|
+
valid mode and still use the provider for newly generated translations.
|
|
415
|
+
No setup, config file or language file is mandatory for existing commands.
|
|
416
|
+
`fix` and `verify` still use `--res-dir`; point them at a separate XML output
|
|
417
|
+
directory after placing the intended default source at `values/strings.xml` there.
|
|
418
|
+
|
|
419
|
+
Manual check: reuse one language file with both commands, combine `all` with an
|
|
420
|
+
extra locale and exclusions, preview before saving, and confirm existing files
|
|
421
|
+
are retained under the chosen preservation mode. Build the app and review the
|
|
422
|
+
actual translations; local validation does not prove linguistic quality.
|
|
423
|
+
|
|
424
|
+
---
|
|
425
|
+
|
|
232
426
|
### `fix`
|
|
233
427
|
|
|
234
428
|
```bash
|
|
@@ -415,13 +609,13 @@ PRs with cross-platform fixes and test notes are especially appreciated.
|
|
|
415
609
|
| Topic | Detail |
|
|
416
610
|
|---|---|
|
|
417
611
|
| **Platform testing** | I test on **Windows only** — macOS and Linux need community verification (see [Platform support](#platform-support)) |
|
|
418
|
-
| **Scope** |
|
|
612
|
+
| **Scope** | `translate` reads one XML source, defaulting to `values/strings.xml`; `--source` can select another file. Output remains `strings.xml` per locale, with no automatic scan of other XML files. `store-listing` translates a separate three-field JSON listing |
|
|
419
613
|
| **Plurals** | Preserves source quantities and item structure; does not generate target-language plural categories. Review plural completeness for each language |
|
|
420
|
-
| **Overwrite** |
|
|
614
|
+
| **Overwrite** | `translate` refreshes whole files; `--missing-only` retains existing resources but does not detect source changes. `store-listing` skips existing files unless `--overwrite` is set |
|
|
421
615
|
| **Folder scan** | Recognizes language-first and Android `b+` locale forms, with optional trailing qualifiers. MCC/MNC-prefixed resource folders are not scanned |
|
|
422
|
-
| **Validation** |
|
|
423
|
-
| **Large files** |
|
|
424
|
-
| **Network** | `translate`
|
|
616
|
+
| **Validation** | XML checks require source attributes, inline element order and formatting options to match; DTD/entity declarations are unsupported. Listing checks cover structure and field limits. Checks do not replace Android compilation, language review or policy review |
|
|
617
|
+
| **Large files** | `translate` sends one XML document per locale; no automatic batching or resume cache. Listings have bounded field lengths and may use correction requests. Incomplete provider output is rejected |
|
|
618
|
+
| **Network** | `translate` and `store-listing` require access to the LLM API (local `custom` providers can work offline; disable update checks for fully offline use) |
|
|
425
619
|
| **JDK** | `verify` requires `javac` on your PATH |
|
|
426
620
|
|
|
427
621
|
---
|
|
@@ -430,7 +624,7 @@ PRs with cross-platform fixes and test notes are especially appreciated.
|
|
|
430
624
|
|
|
431
625
|
| Problem | What to try |
|
|
432
626
|
|---|---|
|
|
433
|
-
| `Could not find
|
|
627
|
+
| `Could not find source XML` | Check `--source`, or ensure `--res-dir` contains `values/strings.xml` |
|
|
434
628
|
| `No locale directories found` | Add `--languages hi,es,fr` or create `values-<lang>/` folders manually |
|
|
435
629
|
| API auth errors | Confirm your key env var or `--api-key` matches the `--provider` |
|
|
436
630
|
| Resource validation fails | Read the named resource error; check source/target keys, attributes, placeholders and markup. Existing files are retained |
|
|
@@ -6,7 +6,7 @@
|
|
|
6
6
|
|
|
7
7
|
**PyPI:** [`android-localisation`](https://pypi.org/project/android-localisation/) · **CLI:** `android-localise` · **Repo:** [android-llm-localization](https://github.com/BharathKmalviya/android-llm-localization)
|
|
8
8
|
|
|
9
|
-
Translate your Android `strings.xml` into multiple languages using AI — Gemini, OpenAI, Anthropic, or a local model via Ollama.
|
|
9
|
+
Translate your Android `strings.xml` and Google Play store listing into multiple languages using AI — Gemini, OpenAI, Anthropic, or a local model via Ollama.
|
|
10
10
|
|
|
11
11
|
---
|
|
12
12
|
|
|
@@ -93,10 +93,10 @@ That's the full workflow. Run these three commands after every time you update y
|
|
|
93
93
|
|
|
94
94
|
When you run `android-localise translate --api-key YOUR_KEY`, here's exactly what it does:
|
|
95
95
|
|
|
96
|
-
1.
|
|
97
|
-
2.
|
|
98
|
-
3. Sends
|
|
99
|
-
4. Parses the response and checks duplicate/unexpected/missing resources, attributes, inline markup, item structure, control escapes and format arguments. A valid result replaces the file atomically; new folders are created only when saving. `--dry-run` shows a diff without writing any files or creating folders
|
|
96
|
+
1. Reads `app/src/main/res/values/strings.xml` by default, or the XML file supplied with `--source`. `--source-language` identifies its language (default `en-US`)
|
|
97
|
+
2. Combines `--languages` and `--languages-file`, expands `all`, removes duplicates and applies `--exclude-languages`. Android qualifiers and conventional language tags are accepted. Without an explicit list, scans existing locale folders in the destination directory, skipping configuration-only folders such as `values-night`, `values-land`, `values-car`, and `values-sw600dp`. The destination defaults to `--res-dir`, or can be set with `--output-dir`
|
|
98
|
+
3. Sends the source XML to the LLM with its language, app context and instructions to preserve resource structure, protected values, namespaces and format specifiers. With `--missing-only`, requests only resources absent from the target file; existing resources remain untouched, and complete locales make no API request
|
|
99
|
+
4. Parses the response and checks duplicate/unexpected/missing resources, attributes, inline markup, item structure, control escapes and format arguments. A valid result replaces the file atomically; new folders are created only when saving. `--skip-existing` validates existing files and skips them without API calls. `--dry-run` shows a diff without writing any files or creating folders
|
|
100
100
|
5. Waits 5 seconds between each language request to avoid hitting API rate limits
|
|
101
101
|
|
|
102
102
|
**Defaults used when you don't specify anything:**
|
|
@@ -117,7 +117,8 @@ Normal translation still replaces the whole locale file. Use `--missing-only` to
|
|
|
117
117
|
|
|
118
118
|
## Setup
|
|
119
119
|
|
|
120
|
-
|
|
120
|
+
Provide source XML at `app/src/main/res/values/strings.xml` by default, or supply
|
|
121
|
+
another file with `--source` and its language with `--source-language`.
|
|
121
122
|
|
|
122
123
|
For target languages, you have two options:
|
|
123
124
|
|
|
@@ -127,6 +128,26 @@ android-localise translate --api-key YOUR_KEY --languages hi,es,fr,de
|
|
|
127
128
|
```
|
|
128
129
|
This translates into Hindi, Spanish, French and German, creating each folder and `strings.xml` when its translation passes validation.
|
|
129
130
|
|
|
131
|
+
To translate into the same 86-locale catalog used for store listings:
|
|
132
|
+
|
|
133
|
+
```bash
|
|
134
|
+
android-localise translate --api-key YOUR_KEY --languages all
|
|
135
|
+
```
|
|
136
|
+
|
|
137
|
+
`all` is case-insensitive and can be combined with extra languages. The bundled catalog is shared
|
|
138
|
+
with `store-listing` and mapped to [Android resource qualifiers](https://developer.android.com/guide/topics/resources/providing-resources#AlternativeResources):
|
|
139
|
+
`hi-IN` becomes `values-hi-rIN`, `pt-BR` becomes `values-pt-rBR`, `es-419`
|
|
140
|
+
becomes `values-b+es+419`, and `fil` becomes `values-b+fil`. Regional variants,
|
|
141
|
+
including English ones, remain separate; `values/strings.xml` remains the source.
|
|
142
|
+
This is the bundled Play locale set, not every possible Android locale.
|
|
143
|
+
|
|
144
|
+
The same XML validation, atomic saves, delay, `--missing-only` and `--dry-run`
|
|
145
|
+
behavior applies to each locale. Normal translation refreshes existing files;
|
|
146
|
+
use `--languages all --missing-only` to keep reviewed resources. Generating or
|
|
147
|
+
previewing all locales can use 86 translation requests plus provider retries;
|
|
148
|
+
complete locales in missing-only mode skip API calls. No folders are created
|
|
149
|
+
during previews or before their translation passes validation.
|
|
150
|
+
|
|
130
151
|
**Option B — pre-create folders yourself:**
|
|
131
152
|
```
|
|
132
153
|
app/src/main/res/
|
|
@@ -136,7 +157,7 @@ app/src/main/res/
|
|
|
136
157
|
├── values-es/
|
|
137
158
|
└── values-fr/
|
|
138
159
|
```
|
|
139
|
-
Run `android-localise translate --api-key YOUR_KEY` and it picks up locale folders, creating `strings.xml` inside each one after successful translation. Locale examples include `values-hi`, `values-es-rES`, `values-b+zh+Hans`, and `values-en-night`; qualifier-only folders are skipped. `--languages` accepts the same forms without the optional `values-` prefix and rejects path separators or non-locale names.
|
|
160
|
+
Run `android-localise translate --api-key YOUR_KEY` and it picks up locale folders, creating `strings.xml` inside each one after successful translation. Locale examples include `values-hi`, `values-es-rES`, `values-b+zh+Hans`, and `values-en-night`; qualifier-only folders are skipped. `--languages` accepts the same forms without the optional `values-` prefix, plus conventional tags such as `es-ES` or `zh-Hant-TW`, and rejects path separators or non-locale names.
|
|
140
161
|
|
|
141
162
|
**Get a free API key:** [Google Gemini AI Studio](https://aistudio.google.com/) → Get API Key. The free tier handles most apps without hitting limits.
|
|
142
163
|
|
|
@@ -149,6 +170,7 @@ typical workflow. Each command has detailed help with its options and examples:
|
|
|
149
170
|
|
|
150
171
|
```bash
|
|
151
172
|
android-localise translate --help
|
|
173
|
+
android-localise store-listing --help
|
|
152
174
|
android-localise fix --help
|
|
153
175
|
android-localise verify --help
|
|
154
176
|
android-localise models --help
|
|
@@ -179,7 +201,13 @@ android-localise translate \
|
|
|
179
201
|
| `--api-key` | Your API key | reads from env var |
|
|
180
202
|
| `--provider` | Which AI to use: `gemini` `openai` `anthropic` `custom` | `gemini` |
|
|
181
203
|
| `--model` | Specific model to use | see [Providers](#providers) |
|
|
182
|
-
| `--languages` | Comma-separated
|
|
204
|
+
| `--languages` | Comma-separated Android/conventional codes and/or `all`, e.g. `all,zu` or `hi,es-ES,b+es+419` | scan existing destination locale folders |
|
|
205
|
+
| `--languages-file` | UTF-8 comma/newline language list; combines with `--languages` | none |
|
|
206
|
+
| `--exclude-languages` | Remove exact normalized locales after selection/discovery | none |
|
|
207
|
+
| `--source` | Read a custom XML source file | `RES_DIR/values/strings.xml` |
|
|
208
|
+
| `--source-language` | Language tag for source XML | `en-US` |
|
|
209
|
+
| `--output-dir` | Save translated XML into this Android res/ directory | `--res-dir` |
|
|
210
|
+
| `--skip-existing` | Validate and skip existing XML files without API calls | off; incompatible with `--missing-only` |
|
|
183
211
|
| `--app-context` | One-line description of your app | — |
|
|
184
212
|
| `--res-dir` | Path to your `res/` folder | `app/src/main/res` |
|
|
185
213
|
| `--base-url` | API endpoint for local/custom providers | — |
|
|
@@ -201,6 +229,172 @@ Validation permits positional placeholder reordering such as `%s %d` becoming `%
|
|
|
201
229
|
|
|
202
230
|
---
|
|
203
231
|
|
|
232
|
+
### `store-listing`
|
|
233
|
+
|
|
234
|
+
Translate an existing Google Play listing's **app name**, **short description**
|
|
235
|
+
and **full description**, using the same providers, keys, model defaults,
|
|
236
|
+
model-not-found fallbacks and timeout handling as `translate`.
|
|
237
|
+
|
|
238
|
+
Create a UTF-8 `listing.json` containing exactly these three nonempty strings:
|
|
239
|
+
|
|
240
|
+
```json
|
|
241
|
+
{
|
|
242
|
+
"app_name": "Pocket Notes",
|
|
243
|
+
"short_description": "Write and organize your notes",
|
|
244
|
+
"full_description": "Write notes and organize them in folders.\n\nFind saved notes with search."
|
|
245
|
+
}
|
|
246
|
+
```
|
|
247
|
+
|
|
248
|
+
Use your actual app details. JSON represents paragraph breaks as `\n`; this
|
|
249
|
+
command translates supplied copy and does not infer features from Android XML.
|
|
250
|
+
|
|
251
|
+
```bash
|
|
252
|
+
# Translate every bundled Google Play listing locale
|
|
253
|
+
android-localise store-listing --source listing.json --languages all
|
|
254
|
+
# Or select languages manually
|
|
255
|
+
android-localise store-listing --source listing.json --languages hi,es-ES,pt-BR
|
|
256
|
+
# Keep the original brand/app name and preview translations
|
|
257
|
+
android-localise store-listing --source listing.json --languages ja,zh-TW --keep-app-name --dry-run
|
|
258
|
+
# Explicitly refresh reviewed files when the source changes
|
|
259
|
+
android-localise store-listing --source listing.json --languages hi --overwrite
|
|
260
|
+
```
|
|
261
|
+
|
|
262
|
+
Outputs are readable UTF-8 `store-listings/hi.json`, `store-listings/es-ES.json`,
|
|
263
|
+
etc., with the same three keys. Review the text and copy each field into its
|
|
264
|
+
language's Play Console listing; JSON is a local output format, not a Play
|
|
265
|
+
Console import file. The CLI does not upload or publish a listing.
|
|
266
|
+
|
|
267
|
+
| Flag | Description | Default |
|
|
268
|
+
|---|---|---|
|
|
269
|
+
| `--source` | UTF-8 JSON source listing | required |
|
|
270
|
+
| `--languages` | Play tags and/or `all`, e.g. `all,zu` or `hi-IN,es-ES` | required unless `--languages-file` supplies a list |
|
|
271
|
+
| `--languages-file` | UTF-8 comma/newline language list; combines with `--languages` | none |
|
|
272
|
+
| `--exclude-languages` | Remove exact normalized Play tags after selection | none |
|
|
273
|
+
| `--source-language` | Source listing language tag | `en-US` |
|
|
274
|
+
| `--output-dir` | Directory for `LOCALE.json` output | `store-listings` |
|
|
275
|
+
| `--keep-app-name` | Preserve the source app name exactly | off; name is localized with brand-preservation instructions |
|
|
276
|
+
| `--overwrite` | Replace existing locale files after validation | off; existing valid files are skipped |
|
|
277
|
+
| `--dry-run` | Generate, validate and display diffs without files/directories being written | off; API usage applies |
|
|
278
|
+
| `--provider` | `gemini`, `openai`, `anthropic`, `custom` | `gemini` |
|
|
279
|
+
| `--model` | Pin any supported model and disable fallbacks | provider default |
|
|
280
|
+
| `--api-key` | Key, or provider-specific environment variable / `API_KEY` | environment |
|
|
281
|
+
| `--base-url` | OpenAI-compatible endpoint; required for `custom` | provider endpoint |
|
|
282
|
+
| `--app-context` | Terminology context; source copy remains the source of facts | none |
|
|
283
|
+
| `--sleep` | Delay between requests, including correction/fallback requests | `5.0` seconds |
|
|
284
|
+
| `--timeout` | Per-response timeout; up to three attempts on timeout | `180` seconds |
|
|
285
|
+
|
|
286
|
+
**Validation:** source and translated fields must fit **30 / 80 / 4,000 characters**
|
|
287
|
+
respectively, as specified in [Google Play's product details guidance](https://support.google.com/googleplay/android-developer/answer/9859152).
|
|
288
|
+
Counts use Python Unicode code points, including spaces, punctuation, newlines
|
|
289
|
+
and any HTML markup, rather than UTF-8 bytes or visual glyphs. Check final counts
|
|
290
|
+
in Play Console too. Names and short descriptions must be single-line text.
|
|
291
|
+
Missing/extra/duplicate keys, blank fields, invalid JSON, unsupported controls
|
|
292
|
+
and unpaired surrogates are rejected. Overlong or otherwise invalid model output
|
|
293
|
+
gets up to **two correction requests**, with validation feedback; this can incur
|
|
294
|
+
additional API usage. Text is never blindly truncated. After validation the
|
|
295
|
+
complete listing is saved atomically. Rejected output preserves existing files;
|
|
296
|
+
other languages continue and any failure produces exit code 1.
|
|
297
|
+
|
|
298
|
+
Existing files are validated and skipped without translation API calls unless
|
|
299
|
+
`--overwrite` is set, including during a dry run. An invalid existing file fails
|
|
300
|
+
instead of being silently replaced; `--overwrite` explicitly regenerates it.
|
|
301
|
+
`--dry-run --overwrite` previews changes to existing files. Source/output path
|
|
302
|
+
collisions are rejected. Locale tags are syntax-checked and normalized (for
|
|
303
|
+
example `pt-br` becomes `pt-BR`); duplicate tags run once. This does not check
|
|
304
|
+
manual codes against Google Play's supported-language catalog. Choose tags available in your Console;
|
|
305
|
+
Android forms such as `values-hi`, `es-rES` and `b+zh+Hans` are not accepted here.
|
|
306
|
+
|
|
307
|
+
`--languages all` expands to the **86 store-listing locales** in
|
|
308
|
+
[Google Play's available-language list](https://support.google.com/googleplay/android-developer/answer/9844778?hl=en),
|
|
309
|
+
verified on **2026-10-02** and bundled with this release. It includes regional
|
|
310
|
+
variants and the source locale if present in the list. It does not fetch or
|
|
311
|
+
change the catalog at runtime. `all` is case-insensitive and can be combined with
|
|
312
|
+
manual additions. Use `--languages`, `--languages-file`, or both. Manual selection retains normalization and
|
|
313
|
+
duplicate removal. Each locale uses its own request, subject to existing-file
|
|
314
|
+
skips, correction/fallback requests and the configured delay. API usage applies
|
|
315
|
+
to all generated locales, including previews. Existing valid files still skip
|
|
316
|
+
unless `--overwrite` is set.
|
|
317
|
+
|
|
318
|
+
**Translation prompt:** includes the supplied [metadata policy](https://play.google.com/about/storelisting-promotional/metadata),
|
|
319
|
+
[Help Centre guidance](https://support.google.com/googleplay/android-developer/answer/9866151),
|
|
320
|
+
[programme policies](https://play.google.com/about/developer-content-policy) and
|
|
321
|
+
[advance-notice guidance](https://support.google.com/googleplay/android-developer/answer/6320428)
|
|
322
|
+
as publishing references, alongside text guidance reviewed on **2026-10-02**.
|
|
323
|
+
It asks for accurate, natural descriptions without invented claims, keyword
|
|
324
|
+
stuffing, misleading affiliations or anonymous testimonials. App names and
|
|
325
|
+
short descriptions avoid ranking/promotion language and decorative emoji;
|
|
326
|
+
short descriptions also avoid calls to action. Existing factual limitations,
|
|
327
|
+
URLs, brand names, required disclosures and full-description markup should be
|
|
328
|
+
preserved. Unsupported promotional wording should become factual copy.
|
|
329
|
+
These semantic rules are prompt instructions, not automated policy checks.
|
|
330
|
+
No policy pages are fetched by the CLI at runtime, so review the current linked
|
|
331
|
+
policies and translated claims before submitting. Advance notice remains a
|
|
332
|
+
separate developer step if eligible; no notice, permission or approval is implied.
|
|
333
|
+
|
|
334
|
+
**Manual check:** translate two languages, review all three fields with a native
|
|
335
|
+
speaker and check their counts in Play Console. Rerun to confirm existing files
|
|
336
|
+
skip, then use `--overwrite --dry-run` to review refreshes without saving.
|
|
337
|
+
Try a source name longer than 30 characters to confirm rejection before any
|
|
338
|
+
translation request.
|
|
339
|
+
For all-locale coverage, run `--languages all` into a separate output directory,
|
|
340
|
+
confirm 86 successful JSON outputs, then rerun and confirm 86 skips. Use a manual
|
|
341
|
+
list such as `hi-IN,es-ES` to confirm only those two outputs are generated.
|
|
342
|
+
|
|
343
|
+
---
|
|
344
|
+
|
|
345
|
+
### Composing translation commands
|
|
346
|
+
|
|
347
|
+
Both commands accept languages from the CLI, a UTF-8 file, or both. File entries
|
|
348
|
+
can be comma-separated or one per line, with blank lines and `#` comments.
|
|
349
|
+
For example, `languages.txt` can contain:
|
|
350
|
+
|
|
351
|
+
```text
|
|
352
|
+
# Shared targets; conventional tags work in both commands
|
|
353
|
+
hi-IN
|
|
354
|
+
es-ES,pt-BR
|
|
355
|
+
zh-Hant-TW
|
|
356
|
+
```
|
|
357
|
+
|
|
358
|
+
```bash
|
|
359
|
+
# All bundled locales plus an extra, excluding exact regional variants
|
|
360
|
+
android-localise translate --languages all,zu --exclude-languages en-US,en-GB
|
|
361
|
+
android-localise store-listing --source listing.json --languages all,zu --exclude-languages en-US,en-GB
|
|
362
|
+
# Reuse a language file and add more targets
|
|
363
|
+
android-localise translate --languages-file languages.txt --languages de-DE --dry-run
|
|
364
|
+
android-localise store-listing --source listing.json --languages-file languages.txt --languages de-DE --dry-run
|
|
365
|
+
# Translate another source language into a separate Android resource directory
|
|
366
|
+
android-localise translate --source source/strings.xml --source-language fr-FR --output-dir translated/res --languages hi-IN,es-ES --skip-existing
|
|
367
|
+
```
|
|
368
|
+
|
|
369
|
+
Ordering is CLI entries first, then file entries. `all` expands wherever it
|
|
370
|
+
appears; duplicates run once. XML equivalent qualifiers such as `es-ES`,
|
|
371
|
+
`es-rES` and `b+es+ES` run once, preserving the first selected folder spelling.
|
|
372
|
+
Exclusions apply after expansion and use exact locale identity: excluding `en`
|
|
373
|
+
does not exclude `en-US` or every English region. You can pass Android forms to
|
|
374
|
+
XML exclusions, and conventional tags to both commands. Listing language files
|
|
375
|
+
accept Play tags only. Manual tags are syntax-checked, not restricted to the
|
|
376
|
+
bundled Play catalog; verify Play Console supports any additional listing locale.
|
|
377
|
+
An empty final selection or invalid language/file fails before API calls or
|
|
378
|
+
folder creation. Source/output collisions, including linked source files, are
|
|
379
|
+
rejected. Provider, model, custom endpoint, context, delays, timeout and previews
|
|
380
|
+
remain independently configurable.
|
|
381
|
+
|
|
382
|
+
XML preservation choices are whole-file refresh (default), `--missing-only`
|
|
383
|
+
(fill missing resources) or `--skip-existing` (skip complete valid files).
|
|
384
|
+
The two preservation flags cannot be combined. Listing preservation remains
|
|
385
|
+
skip-by-default with explicit `--overwrite`. Preview flags can combine with any
|
|
386
|
+
valid mode and still use the provider for newly generated translations.
|
|
387
|
+
No setup, config file or language file is mandatory for existing commands.
|
|
388
|
+
`fix` and `verify` still use `--res-dir`; point them at a separate XML output
|
|
389
|
+
directory after placing the intended default source at `values/strings.xml` there.
|
|
390
|
+
|
|
391
|
+
Manual check: reuse one language file with both commands, combine `all` with an
|
|
392
|
+
extra locale and exclusions, preview before saving, and confirm existing files
|
|
393
|
+
are retained under the chosen preservation mode. Build the app and review the
|
|
394
|
+
actual translations; local validation does not prove linguistic quality.
|
|
395
|
+
|
|
396
|
+
---
|
|
397
|
+
|
|
204
398
|
### `fix`
|
|
205
399
|
|
|
206
400
|
```bash
|
|
@@ -387,13 +581,13 @@ PRs with cross-platform fixes and test notes are especially appreciated.
|
|
|
387
581
|
| Topic | Detail |
|
|
388
582
|
|---|---|
|
|
389
583
|
| **Platform testing** | I test on **Windows only** — macOS and Linux need community verification (see [Platform support](#platform-support)) |
|
|
390
|
-
| **Scope** |
|
|
584
|
+
| **Scope** | `translate` reads one XML source, defaulting to `values/strings.xml`; `--source` can select another file. Output remains `strings.xml` per locale, with no automatic scan of other XML files. `store-listing` translates a separate three-field JSON listing |
|
|
391
585
|
| **Plurals** | Preserves source quantities and item structure; does not generate target-language plural categories. Review plural completeness for each language |
|
|
392
|
-
| **Overwrite** |
|
|
586
|
+
| **Overwrite** | `translate` refreshes whole files; `--missing-only` retains existing resources but does not detect source changes. `store-listing` skips existing files unless `--overwrite` is set |
|
|
393
587
|
| **Folder scan** | Recognizes language-first and Android `b+` locale forms, with optional trailing qualifiers. MCC/MNC-prefixed resource folders are not scanned |
|
|
394
|
-
| **Validation** |
|
|
395
|
-
| **Large files** |
|
|
396
|
-
| **Network** | `translate`
|
|
588
|
+
| **Validation** | XML checks require source attributes, inline element order and formatting options to match; DTD/entity declarations are unsupported. Listing checks cover structure and field limits. Checks do not replace Android compilation, language review or policy review |
|
|
589
|
+
| **Large files** | `translate` sends one XML document per locale; no automatic batching or resume cache. Listings have bounded field lengths and may use correction requests. Incomplete provider output is rejected |
|
|
590
|
+
| **Network** | `translate` and `store-listing` require access to the LLM API (local `custom` providers can work offline; disable update checks for fully offline use) |
|
|
397
591
|
| **JDK** | `verify` requires `javac` on your PATH |
|
|
398
592
|
|
|
399
593
|
---
|
|
@@ -402,7 +596,7 @@ PRs with cross-platform fixes and test notes are especially appreciated.
|
|
|
402
596
|
|
|
403
597
|
| Problem | What to try |
|
|
404
598
|
|---|---|
|
|
405
|
-
| `Could not find
|
|
599
|
+
| `Could not find source XML` | Check `--source`, or ensure `--res-dir` contains `values/strings.xml` |
|
|
406
600
|
| `No locale directories found` | Add `--languages hi,es,fr` or create `values-<lang>/` folders manually |
|
|
407
601
|
| API auth errors | Confirm your key env var or `--api-key` matches the `--provider` |
|
|
408
602
|
| Resource validation fails | Read the named resource error; check source/target keys, attributes, placeholders and markup. Existing files are retained |
|