Skip to content

devlog/model-bench/glm-53-in-the-editor-bilingual-ui-string-mistakes-1074.md

GLM-5.3 in the Editor: Bilingual UI String Mistakes

Pasting both languages into one prompt and expecting line-for-line symmetry

When you send GLM-5.3 a bilingual task, the shape of the request decides whether the answer is diffable. The most common failure is a single paragraph where English copy sits next to a loose translation request. The result reads beautifully and maps to nothing. The model reorders strings, merges two button labels into one phrase, and quietly drops a line it considers redundant. You end up reviewing prose instead of verifying a patch.

The fix is boring and effective. Give every string an explicit identifier before it leaves your editor, keep source and target in clearly labeled fields, and ask for those identifiers back in the same order. Name the target language per block rather than assuming the preference carries across a long response. Instructions belong at the top, data in the middle, and the requested output shape at the bottom, because GLM-5.3 follows structure it can point at.

  • Label every string with a stable key before you submit it.
  • Ask for output in the same order as the input blocks.
  • State the target language explicitly for every block you send.
  • Separate translation instructions from the copy data itself.

Splitting work into paired calls also beats one giant batch. A short request per language pair yields small diffs, makes retries cheap, and stops one ambiguous string from poisoning an entire response that you now have to read line by line.

Letting GLM-5.3 invent keys, merge strings, or mangle placeholders

Placeholders, plural syntax, and inline markup are where bilingual jobs quietly break. GLM-5.3 will translate a variable name if it looks like a word, smooth a plural template into a single sentence, and reorder tags inside a phrase. The copy sounds fine in the review pane and then your locale file fails to parse at build time.

Protect tokens explicitly in every request and list them again if the batch is long. Tell the model that placeholders, tags, numbers, and product names must appear unchanged in the target. Then validate mechanically instead of trusting the eye. A small terminal script that extracts placeholders from source and target and compares sets catches most damage before anything reaches your repository. When the counts differ, fail the command and request a repair for only that string.

  • Give the model an explicit list of protected placeholders and tags.
  • Ask for plain text output with no formatting and no code fences.
  • Validate every response with a placeholder comparison script before merging.
  • Reject any string whose placeholder count differs from the source.

Proper nouns deserve the same treatment as variables. Brand names, feature names, and plan tiers should sit in a do-not-translate list, because a model that localizes your product name is doing the one thing no reviewer can fix without a second pass.

Skipping context notes so short UI strings come back wrong

Short strings are the hardest ones you will ever send. A label like Book can be a verb or a noun, and the correct French or German form depends on which one it is. Tooltip copy needs one tone, an error message needs another, and a settings toggle label sits somewhere between them. Without context, GLM-5.3 guesses, and it guesses consistently enough that the wrong choice survives review.

Attach a context line to each string: where it appears, who sees it, what happens on click, and whether the tone is formal or casual. Decide person and sentence case once, then repeat those rules in every batch so they stay stable across locales. If a string is genuinely ambiguous, ask the model to translate it and add a short note about which reading it chose, so the decision surfaces in review instead of in production.

  • Describe where each string appears, such as a modal or a tooltip.
  • Declare tone and person once and repeat them in every batch.
  • Give character limits per language whenever the layout is constrained.
  • Flag ambiguous strings and ask the model to state its reading.

Gender agreement is another trap. Nouns that modify a noun in one language need agreement in another, and only context tells the model which noun is in play. One extra sentence per string is cheaper than a full localization review.

Waiting until the build fails to check length budgets

Length is a runtime property of UI copy, not a cosmetic detail. German expands, Japanese contracts, and a button that fits English will clip in two other locales. Waiting for a visual regression test to catch this means another round trip, and each round trip is another chance for someone to rewrite copy that was already correct.

Ask for variants up front. When a control has a hard width, request a short version and a standard version of the same string, both preserving the same meaning and the same protected tokens. Measure with a script in your terminal rather than by eye, because character count is a poor proxy for rendered width when scripts mix. Feed the measured length back into the next request instead of describing the problem vaguely.

  • Request a short variant and a standard variant for constrained controls.
  • Measure rendered width instead of counting characters alone.
  • Include a hard character budget for every constrained string you send.
  • Return measured results to the model when asking for a rewrite.

This habit also improves your source copy. Strings that need three variants usually need a clearer message, and fixing that in English saves translation work in every locale downstream.

Rerunning whole batches when only three strings changed

Copy work is iterative, and iteration is where token spend leaks. The expensive pattern is regenerating an entire locale file after changing one error message. The cheaper pattern is a stable system block that carries your glossary and tone rules, followed by small payloads containing only the strings that changed. That structure also keeps your cache warm, since the long instructions stay byte-identical between calls.

This is one reason I route bilingual work through Fluxo. One key and one base URL at https://api.fluxorelay.com cover Claude, GPT, Gemini, DeepSeek, Kimi, GLM, Qwen, Grok and more, so a prompt can move between models without a rewrite. Billing is per real token including cache reads and writes, with no monthly fee, which makes those small targeted reruns genuinely cheap. It works inside Claude Code, Codex, Gemini CLI and any OpenAI SDK, so the same request works from a script or straight from the terminal.

  • Keep system instructions byte-identical so cache reads stay high.
  • Send only the strings that changed since the previous run.
  • Group locales together when their instructions are exactly the same.
  • Track cache writes separately from cache reads when estimating cost.

Friends you invite also earn you a referral share when they pay, which is a quiet way to offset the tokens your localization pipeline consumes every week.

Reaching for GLM-5.3 on every bilingual task

GLM-5.3 is a strong choice for bilingual product copy and UI strings, but it is not the only lever. A quick second opinion from Gemini 3.8 Flash can confirm a tense choice in seconds, and a heavier pass from Qwen3.8 Max helps when a legal or marketing string keeps coming back unstable. With one base URL and one key, switching models is a one-line change instead of a migration.

A practical pattern is to translate once, then have a second model flag only suspected errors rather than rewrite everything. Disagreements get reviewed by a human, agreements get merged, and the review queue stays short. Record the decisions in a glossary file that lives next to your locale files, so the next batch starts from what you already settled.

  • Use a second model to flag suspected errors rather than rewrite.
  • Record every settled term in a glossary beside your locale files.
  • Keep human review focused on strings where models disagree.

If you want to try this workflow from your own editor, you are welcome to create a Fluxo account and point a single base URL at it. If anything here is unclear, leave a note on the contact page after signing in and we will pick it up from there.

Next in the buffer