Skip to main content

Language Switcher

Detection order: URL prefix → Cookie → Base locale (English)

Current language: English (en)
Formatting locale: en-US

Translated Messages

m.greeting({ name: 'World' }) Hello, World!
m.welcome_message() Welcome to the internationalization showcase
m.sample_text() This text is translated based on the current locale.

Pluralization

ICU MessageFormat handles pluralization rules per language.

m.items_count({ count: 0 }) undefined other }
m.items_count({ count: 1 }) undefined other }
m.items_count({ count: 2 }) undefined other }
m.items_count({ count: 5 }) undefined other }
m.items_count({ count: 42 }) undefined other }

Date & Number Formatting

Formatting uses the browser's Intl API, decoupled from the translation locale. A German user in Switzerland gets German text but Swiss number formatting.

Formatted date Jan 15, 2025
Formatted date (long) Wednesday, January 15, 2025
Formatted number 1,234,567.89
Formatted currency (EUR) €1,234.50
Formatted currency (USD) $1,234.50
Formatted percentage 85.4%
Relative time 2 days ago

Content Translation (Database)

The tc() helper translates JSON fields from the database, falling back through: current locale → English → first available.

tc(post.title) Hello World
tc(post.description) This content is stored in the database as JSON.

Database Schema Pattern

// JSON columns for translated content
title: jsonb('title').$type<Record<string, string>>()
// Data: { "en": "Hello", "de": "Hallo", "fr": "Bonjour" }

Type Safety

All message keys are compile-time checked with full IntelliSense support. Missing keys or wrong parameters cause build errors, not runtime errors.

Compile-time Guarantees

// ✅ Type-safe with autocomplete
m.greeting({ name: 'Alice' });

// ❌ Compile error — missing parameter
m.greeting();

// ❌ Compile error — unknown message key
m.unknownKey();
← Back to Showcases