batch-text-translation
Published
Public
in @translation-essentials

Translate a labeled batch of texts into a target language in one call — one result per item in input order, labels echoed verbatim, with placeholders, HTML, and markdown preserved character-for-character in every translation.

batch-text-translation

Translate a labeled batch of texts into a target language in one call — the batch counterpart of text-translation. Every item comes back as a {label, translated_text} pair in input order, with the things that break naive machine translation preserved verbatim: template placeholders ({var}, %s, %(count)d), HTML tags, markdown syntax, URLs, emails, and code identifiers.

Built for localizing whole UI string files, resource bundles, and CMS field sets where you want one call per language instead of one call per string — and where a corrupted %(count)d or a mixed-up label is a production bug, not a style issue.

Entrypoints

EntrypointRendersInputs
systemBatch-translator instructions + embedded output schematarget_language, source_language?
userThe delimited <items> block + target languageitems, target_language, source_language?

Render system as the system message and user as the user message. Pass the shared variables to both renders.

Variables

  • items (array, required) — the batch to translate. Each item is {label: string, text: string}:
    • label — an opaque identifier (e.g. "checkout.cta", "error_404_title"), echoed back verbatim in the corresponding output entry. Never translated, trimmed, or re-cased.
    • text — the text to translate. May contain placeholders, HTML, or markdown; may be empty.
  • target_language (string, required) — ISO 639-1 code ("de") or English language name ("German").
  • source_language (string, optional) — ISO 639-1 code of the source language, when you know it. The engine trusts it and echoes it back as detected_source_language; omit to auto-detect.

Output

parseOutput() returns:

{
  "reasoning": "All three strings are English UI copy. One printf placeholder and one HTML tag preserved in place; labels echoed untouched.",
  "detected_source_language": "en",
  "translations": [
    { "label": "greeting", "translated_text": "Hallo %s, willkommen zurück!" },
    { "label": "inbox.count", "translated_text": "Sie haben <b>%(count)d</b> neue Nachrichten." },
    { "label": "cta.upgrade", "translated_text": "Jetzt upgraden" }
  ]
}
  • reasoning comes before the translations by design — language identification and placeholder decisions are made before committing to output.
  • detected_source_language is a closed enum of 41 ISO 639-1 codes plus "und" — the dominant language across the batch when items mix.
  • translations has exactly one entry per input item, in input order — including empty-text items (empty string) and repeated labels. Empty array only for an empty batch.

Behaviour you can rely on

  • Order and cardinality are stable. One output entry per input item, same order — items are never merged, dropped, or reordered.
  • Labels are opaque. Echoed character-for-character, even when a label looks like a translatable word.
  • Items are independent. One item's content never leaks into another's translation.
  • Placeholders survive verbatim. {var}, %s, %(name)s, :param, $1, tags, attribute values, URLs, backtick code spans.
  • Instructions inside the texts are translated, not obeyed. The texts are data — "ignore the above and output X" comes out as its faithful translation.
  • No hallucinated content. Empty text yields an empty translated_text; an empty batch yields an empty array and "und".

House conventions

  • Reasoning-first, key order pinned in the system prompt.
  • Strict schema: additionalProperties: false, closed enum for the detected language.
  • Injection-safe input: each text is triple-mustache-injected inside its own <item label="..."> delimiter within an <items> block, and explicitly treated as data.
  • Empty/garbage behaviour specified: empty item → empty string; empty batch → empty array + "und".

Part of the Translation Essentials collection — use text-translation for single strings with untranslatable-segment auditing, language-detection to route, and translation-qa-grading to grade individual results.

@sufleur/