← All tests

Khmer localization — nix-cafe STAGING

Phase-2 i18n wiring for the last & hardest app (the live-POS Next.js App Router on a Cloudflare Worker). Verified on demo.staging 6/6 + staging smoke 5/5.

next-intl v4, without i18n routing. The locale is driven by a nix_cafe_lang cookie (EN / ខ្មែរ), not a /[locale] URL segment — so the /cafe basePath, the auth middleware, and the POS-lockdown middleware are all untouched. 1,926 strings across 97 files were converted to t(...) calls; messages are generated from the flat localization export into nested messages/{en,km}.json by a re-runnable script. The km bundle is English-until-translated — every key resolves to English until Narong fills the Khmer column, then km.json regenerates with one command (no code change). A language switcher sits in the authed top bar.
Because the Khmer column isn't filled yet, KM currently renders English (validated: all 1,926 keys resolve, zero key-path leaks). What's proven here is the plumbing: the switcher flips the locale, <html lang> updates, and every authed surface renders cleanly in both locales.

Language switcher — EN active → ខ្មែរ active

Englishdashboard, EN active
Top-bar switcher: EN highlighted, <html lang="en">.
ភាសាខ្មែរdashboard, KM active
After clicking ខ្មែរ: cookie set, full reload, <html lang="km">, KM highlighted (text falls back to English until translated).

Authed surfaces render cleanly (no 5xx, no unresolved-key leaks)

POS landing
POS landing
Settings
Settings
Products
Products
Orders
Orders
Team
Team
Reports
Reports

Checks (demo.staging, Pro)

SSO login → /cafe/dashboardpass
Switcher present; EN active; <html lang="en">pass
EN: 13 authed surfaces — no 5xx / pageerror / key-leakpass
Switch to KM → cookie set, <html lang="km">, KM activepass
KM: 13 authed surfaces — no 5xx / pageerror / key-leak (English fallback)pass
Login page honors KM cookie (public route)pass
Staging smoke (demo Pro + lumiere Starter + guards)5/5

Known / deferred

Pre-existing tz hydration warning on POS landing (formatTime lacks a timeZone → UTC vs local). NOT i18n-caused — now FIXED (APP_TIME_ZONE pinned).fixed
Polish pass when Khmer returns: dine-type 3 labels, 4 adapter throw-strings, flat-plural English ("1 orders") — consistent with the other 4 apps.deferred

nix-cafe staging 8a225fc (Worker nix-cafe-staging 59ca459f). Parked for the scheduled prod promote — never ad-hoc (live get-coffee POS path).