Skip to content

feat(i18n): extract sandbox + all remaining UI areas to the i18n dictionaries#4971

Merged
rafavalls merged 1 commit into
mainfrom
viktormarinho/i18n-extract-sandbox
Jul 22, 2026
Merged

feat(i18n): extract sandbox + all remaining UI areas to the i18n dictionaries#4971
rafavalls merged 1 commit into
mainfrom
viktormarinho/i18n-extract-sandbox

Conversation

@viktormarinho

@viktormarinho viktormarinho commented Jul 21, 2026

Copy link
Copy Markdown
Contributor

Summary

Final extraction PR of the i18n effort (mechanism: #4959, settings area: #4964). Covers everything that was left: sandbox, chat, registry, orgs (connections/members/monitoring), sections-editor, task-board, library, reports, virtual-mcp, home, admin, onboarding, and remaining components/layouts/routes.

3,941 keys now live in 32 per-domain dictionary files (en + pt-BR), each pt-BR file type-checked complete via satisfiesbun run check remains the translation-completeness proof. English UI copy is unchanged (values extracted verbatim).

How it was produced

  • Two extraction fleets (39 + 142 haiku agents, one per file / small-file group, per-file key namespaces → zero collisions), followed by a deterministic dictionary merge.
  • A 46-cluster repair fleet (sonnet) + manual pass for the 131 type errors the extraction left (missing useT, labelKey fields typed as string, undefined-unsafe interpolation vars, labellabelKey call sites).
  • APPROVAL_LEVEL_OPTIONS now carries labelKey/shortKey translation keys and chat surfaces render via t() — closes the known seam from feat(i18n): zero-dep i18n module with pt-BR support and language preference #4959.
  • TranslationKey re-exported from use-t.ts; TFunction threaded through helpers receiving t.

Verification (deterministic, not vibes)

  • tsc --noEmit (apps/mesh): 0 errors — every t() key literal-checked against the union.
  • Key↔usage cross-check: 0 keys used but missing; 79 orphan keys removed from both dictionaries.
  • en↔pt placeholder parity: identical {var} sets for all keys (4 benign en-only {plural} vars where pt uses parenthetical forms).
  • ICU-syntax grep: 0 (invented {count, plural, ...} forms replaced with plain {var} in 14 keys).
  • Web unit suite: zero regressions vs origin/main (verified by diffing failing-test sets against a clean main worktree; 18 order-dependent failures pre-exist on both).

Collateral hardening

  • useLocalStorage guards a missing localStorage (non-browser render contexts get defaults) — components that now resolve copy via useT no longer explode in polluted test environments.
  • Component tests for tier-trigger / assistant / blocks-tab wrap renders in a QueryClientProvider; the pure-logic test for mobile tab labels passes a real t built from the en dictionary (no mocks).
  • Two files corrupted by smart-quote-writing agents were restored byte-exact (em-dashes/arrows included).

Known deferrals (TODO(i18n), per AGENTS.md convention)

Module-scope Zod validation messages and JSX-interleaved rich-text sentences (~30 spots) are marked for a manual pass. Server-originated error messages and transactional emails remain deliberately out of scope.

Testing

  • bunx tsc --noEmit (apps/mesh) ✅ 0 errors
  • bun test apps/mesh/src/web ✅ no regressions vs main
  • bun run lint ✅ 0 errors · bun run fmt ✅ · knip clean

🤖 Generated with Claude Code


Summary by cubic

Finished extracting sandbox and all remaining UI into i18n with full pt-BR coverage, locale‑aware time, and a one‑time auto‑switch heads‑up for Portuguese‑browser users; merged latest main.

  • ~3,900 keys across 33 per‑domain dictionaries (en, pt-BR), literal UTF‑8; type‑checked complete via bun run check.

  • New Features

    • Localized remaining UI (incl. sandbox): automations, chat (tool calls, input/editor, banners), connections/details, file/GitHub pickers, header/org switcher, home/tiles, deck toolbar, monitoring, prompts, collections, import, org create/invite, errors/shortcuts. Includes aria labels, toasts, dialogs.
    • Added language-announcement-dialog with auto‑switch for Portuguese browsers and quick revert; commerce‑onboarding language switcher is now a dropdown (EN, PT-BR).
    • SDK/dev: approval levels and model/tier/context labels use labelKey/shortKey; threaded t through helpers (model selectors, uploader, tools popover); relative time respects the selected locale.
  • Bug Fixes

    • Preserved Portuguese‑first surfaces by restoring original Portuguese copy in en where intended.
    • Hoisted useT out of conditional branches to fix hook‑order crashes; adjusted helpers that receive t.
    • CI/tests: wrapped components using useT in QueryClientProvider (assistant, tier‑trigger, tiptap input, propose‑plan); fixed date-fns pt-BR locale imports and ensured dictionaries are literal UTF‑8.

Written for commit 4c6b896. Summary will update on new commits.

Review in cubic

@rafavalls
rafavalls force-pushed the viktormarinho/i18n-extract-sandbox branch from f21eff1 to 0a84270 Compare July 22, 2026 13:21
@rafavalls
rafavalls enabled auto-merge (squash) July 22, 2026 13:47
…ionaries

Completes the i18n extraction phase across the whole web UI: ~3,900 keys
in 33 per-domain dictionary files (en + pt-BR), covering sandbox, chat,
registry, orgs, sections-editor, monitoring, task-board, library,
reports, virtual-mcp, home, admin, onboarding and misc components,
layouts and routes. pt-BR completeness is enforced by satisfies checks,
so bun run check proves translation coverage.

Beyond the mechanical extraction:
- APPROVAL_LEVEL_OPTIONS carries labelKey/shortKey translation keys;
  chat surfaces render them via t()
- TFunction/TranslationKey exported from use-t.ts and threaded through
  helpers that receive t as a parameter
- pt-first surfaces (commerce onboarding, reports, related banners)
  keep their original Portuguese copy as the en value — their audience
  and e2e contract are Portuguese by design
- conditional useT() declarations hoisted to component tops (they
  crashed the tree with hook-order violations when branches flipped)
- useLocalStorage tolerates missing localStorage; component tests wrap
  renders in QueryClientProvider where components now resolve copy via
  useT; the mobile tab-label unit test passes a real t built from the
  en dictionary

History note: this squashes the branch (fleet extraction, repair passes
and four main merges) into one commit on top of main; the tree is
byte-identical to the CI-green merged state.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
@viktormarinho
viktormarinho force-pushed the viktormarinho/i18n-extract-sandbox branch from 82af4a5 to 4c6b896 Compare July 22, 2026 15:57
@rafavalls
rafavalls merged commit bbb8246 into main Jul 22, 2026
14 checks passed
@rafavalls
rafavalls deleted the viktormarinho/i18n-extract-sandbox branch July 22, 2026 16:04
decocms Bot pushed a commit that referenced this pull request Jul 22, 2026
PR: #4971 feat(i18n): extract sandbox + all remaining UI areas to the i18n dictionaries
Bump type: minor

- decocms (apps/mesh/package.json): 4.96.0 -> 4.97.0
- @decocms/mesh-sdk (packages/mesh-sdk/package.json): 1.28.0 -> 1.29.0
- @deco/ui (packages/ui/package.json): 1.4.0 -> 1.5.0

Deploy-Scope: web
pedrofrxncx added a commit that referenced this pull request Jul 22, 2026
The fetch-error state added in #5029 hardcoded its two strings in English, missed by the same-day i18n sweep in #4971 that translated the rest of this file. Adds registry.monitorConnectionsPanel.loadFailed / .unknownError keys (en + pt-br) and routes them through t().
rafavalls added a commit that referenced this pull request Jul 22, 2026
Resolve conflicts between the top-bar redesign and main:

- Tasks/Library/runtime-switcher toggles: keep the redesign that folds the
  agent-independent overlays into the main-panel tab bar; drop the now-orphaned
  library-toggle / tasks-toggle / runtime-switcher files.
- Port main's features into the redesign: reports-only hides the Library
  overlay (#4711), task board graduated out of its org flag (#4883, dropped
  useTaskBoardEnabled), i18n strings (#4971), and the new Connect-to-Claude
  footer action (#2765).
- sidebar footer: keep the redesign's unified account row (Settings tucked into
  a bottom-right icon) but restore the reports-only trimmed extra-actions
  variant.
- preview: keep the redesign's header-portal structure over main's inline
  toolbar; main's a11y/focus/reload fixes auto-merged and are preserved.

Verified: tsc --noEmit, oxlint (0 errors), knip (clean).
pedrofrxncx added a commit that referenced this pull request Jul 23, 2026
… dialog (#5099)

The delete dialog in the sandbox file explorer (title, description, unsaved-
changes warning, and buttons) was hardcoded in English, missed by the sandbox
i18n sweep (#4971). pt-br users see raw English strings when deleting a file
or folder. Wires it through useT() following the existing
FileExplorerNameDialog / DeleteConnectionDialogs pattern (translated prefix +
untranslated inline filename span).
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants