Proposal
Ship first-class multi-language support. Today src/i18n/request.ts already selects a locale from NEXT_PUBLIC_APP_LOCALE and falls back to English, but (a) only messages/en.json exists and (b) a number of screens bypass next-intl with hardcoded English, so they can't be localized at all.
This proposes:
- Add
messages/pt.json (Brazilian Portuguese) and messages/es.json (Latin American Spanish), key-for-key identical to en.json.
- Internationalize ~250 hardcoded strings across ~30 files (Notifications, AI agent, Signup, Forgot password, Join, Flows header, interactive message builder, flow/automation template galleries, theme picker, scattered toasts/placeholders/aria-labels) so the whole UI follows the selected locale.
- Fix a few pre-existing i18n bugs that render raw keys even in English:
- missing
Settings.sections.quick-replies label,
- Overview role chip using
useTranslations('roles') instead of 'Settings.roles',
- the API-key
scopesHint message embedding <code className> (next-intl rich tags must be attribute-less),
- Base UI
<SelectValue /> triggers showing the raw enum value instead of the translated option label.
It stays additive: locale is still one global value, English remains the default and fallback, and data-definition files keep their English seed copy.
I understand the template is intentionally English-only and single-locale, and that translations may be considered fork territory — opening this first per CONTRIBUTING to check alignment. The bug fixes in point 3 are worth landing regardless of the translation decision; happy to split them into a separate English-only PR if you'd prefer to take just those.
Proposal
Ship first-class multi-language support. Today
src/i18n/request.tsalready selects a locale fromNEXT_PUBLIC_APP_LOCALEand falls back to English, but (a) onlymessages/en.jsonexists and (b) a number of screens bypass next-intl with hardcoded English, so they can't be localized at all.This proposes:
messages/pt.json(Brazilian Portuguese) andmessages/es.json(Latin American Spanish), key-for-key identical toen.json.Settings.sections.quick-replieslabel,useTranslations('roles')instead of'Settings.roles',scopesHintmessage embedding<code className>(next-intl rich tags must be attribute-less),<SelectValue />triggers showing the raw enum value instead of the translated option label.It stays additive: locale is still one global value, English remains the default and fallback, and data-definition files keep their English seed copy.
I understand the template is intentionally English-only and single-locale, and that translations may be considered fork territory — opening this first per CONTRIBUTING to check alignment. The bug fixes in point 3 are worth landing regardless of the translation decision; happy to split them into a separate English-only PR if you'd prefer to take just those.