Menguasai Internationalization (i18n) di Aplikasi React: Panduan Praktis dengan react-i18next dan Strategi Lanjutannya
Halo para developer! Pernahkah Anda membayangkan aplikasi web Anda digunakan oleh orang-orang dari berbagai belahan dunia, masing-masing dengan bahasanya sendiri? Atau mungkin Anda bekerja di sebuah perusahaan yang ingin menjangkau pasar global? Di sinilah Internationalization (i18n), atau sering disebut globalisasi, memainkan peran krusial.
i18n bukan hanya sekadar menerjemahkan teks dari satu bahasa ke bahasa lain. Lebih dari itu, i18n mencakup penyesuaian format angka, tanggal, mata uang, pluralisasi, hingga arah teks (kiri-ke-kanan atau kanan-ke-kiri) agar aplikasi terasa native bagi setiap pengguna. Mengabaikan i18n berarti membatasi potensi aplikasi Anda dan memberikan pengalaman pengguna yang kurang optimal.
Di blog ini, kita sudah pernah membahas panduan umum tentang i18n. Kali ini, kita akan menyelam lebih dalam ke implementasi praktis i18n, khususnya di ekosistem React, menggunakan salah satu library paling populer dan tangguh: react-i18next. Kita akan membahas mulai dari setup dasar hingga strategi lanjutan untuk aplikasi skala besar. Mari kita mulai! 🚀
1. Pendahuluan: Mengapa react-i18next?
Anda mungkin bertanya, mengapa perlu library khusus untuk i18n? Bukankah hanya if (lang === 'en') { ... } sudah cukup? Tentu saja tidak! Pendekatan manual akan menjadi mimpi buruk seiring bertambahnya teks dan bahasa.
react-i18next adalah jembatan antara library i18n inti, i18next, dan React. Library ini menyediakan Hooks dan Components yang memudahkan Anda mengintegrasikan terjemahan ke dalam komponen React Anda dengan cara yang declarative dan efisien.
Keunggulan react-i18next:
- Mudah digunakan: Dengan Hooks seperti
useTranslation, Anda bisa mengakses terjemahan dengan cepat. - Fitur Lengkap: Mendukung pluralisasi, interpolasi, konteks, fallback bahasa, deteksi bahasa otomatis, dan banyak lagi.
- Fleksibel: Dapat dikonfigurasi untuk memuat terjemahan dari berbagai sumber (JSON, API, dll.) dan mendukung lazy loading.
- Komunitas Besar: Dokumentasi yang lengkap dan dukungan komunitas yang aktif.
Mari kita siapkan proyek React baru dan mulai mengimplementasikannya.
2. Memulai dengan react-i18next: Setup Dasar
Pertama, instal dependency yang diperlukan:
npm install i18next react-i18next i18next-browser-languagedetector --save
# atau
yarn add i18next react-i18next i18next-browser-languagedetector
i18next: Core i18n library.react-i18next: Integrasi untuk React.i18next-browser-languagedetector: Plugin untuk mendeteksi bahasa dari browser pengguna.
Selanjutnya, buat file konfigurasi i18n di root proyek Anda, misalnya src/i18n.js:
// src/i18n.js
import i18n from 'i18next';
import { initReactI18next } from 'react-i18next';
import LanguageDetector from 'i18next-browser-languagedetector';
// Import terjemahan Anda
import translationEN from './locales/en/translation.json';
import translationID from './locales/id/translation.json';
// Objek resource untuk terjemahan
const resources = {
en: {
translation: translationEN
},
id: {
translation: translationID
}
};
i18n
.use(LanguageDetector) // Mendeteksi bahasa pengguna dari browser
.use(initReactI18next) // Menghubungkan i18next ke React
.init({
resources,
fallbackLng: 'en', // Bahasa default jika bahasa terdeteksi tidak tersedia
debug: true, // Aktifkan untuk debugging
interpolation: {
escapeValue: false, // React sudah melakukan escaping, jadi tidak perlu lagi
}
});
export default i18n;
Buat juga folder src/locales/ dengan subfolder untuk setiap bahasa, misalnya en dan id, dan file translation.json di dalamnya:
// src/locales/en/translation.json
{
"welcome": "Welcome to our application!",
"greeting": "Hello, {{name}}!",
"pluralKey_one": "You have {{count}} new message.",
"pluralKey_other": "You have {{count}} new messages.",
"dateExample": "Today is {{date, DATE_HUGE}}.",
"settings": {
"title": "Settings",
"language": "Language"
}
}
// src/locales/id/translation.json
{
"welcome": "Selamat datang di aplikasi kami!",
"greeting": "Halo, {{name}}!",
"pluralKey_one": "Anda punya {{count}} pesan baru.",
"pluralKey_other": "Anda punya {{count}} pesan baru.",
"dateExample": "Hari ini adalah {{date, DATE_HUGE}}.",
"settings": {
"title": "Pengaturan",
"language": "Bahasa"
}
}
Terakhir, impor file i18n.js ini di file index.js atau main.jsx aplikasi React Anda:
// src/index.js atau src/main.jsx
import React from 'react';
import ReactDOM from 'react-dom/client';
import './i18n'; // Penting: Import konfigurasi i18n Anda
import App from './App';
ReactDOM.createRoot(document.getElementById('root')).render(
<React.StrictMode>
<App />
</React.StrictMode>
);
✅ Dengan setup ini, i18next akan otomatis mendeteksi bahasa browser pengguna dan memuat terjemahan yang sesuai.
3. Menggunakan Terjemahan dalam Komponen React
Sekarang, mari kita gunakan terjemahan di komponen App.js kita:
// src/App.js
import React from 'react';
import { useTranslation, Trans } from 'react-i18next';
function App() {
const { t, i18n } = useTranslation();
const changeLanguage = (lng) => {
i18n.changeLanguage(lng);
};
const today = new Date();
return (
<div style={{ padding: '20px', maxWidth: '600px', margin: '0 auto' }}>
<h1>{t('welcome')}</h1>
<p>{t('greeting', { name: 'Dunia' })}</p>
<h2>{t('settings.title')}</h2>
<p>{t('settings.language')}:</p>
<button onClick={() => changeLanguage('en')} style={{ marginRight: '10px' }}>English</button>
<button onClick={() => changeLanguage('id')}>Bahasa Indonesia</button>
<h3>Pluralisasi</h3>
<p>{t('pluralKey', { count: 1 })}</p> {/* Output: Anda punya 1 pesan baru. */}
<p>{t('pluralKey', { count: 5 })}</p> {/* Output: Anda punya 5 pesan baru. */}
<p>{t('pluralKey', { count: 0 })}</p> {/* Output: Anda punya 0 pesan baru. */}
<h3>Format Tanggal</h3>
<p>{t('dateExample', { date: today })}</p>
<h3>Interpolasi dengan Komponen React (`Trans`)</h3>
<p>
<Trans i18nKey="complexText">
Silakan kunjungi <a href="https://blog.example.com">blog kami</a> untuk informasi lebih lanjut.
</Trans>
</p>
{/* Untuk ini, Anda perlu menambahkan "complexText" di translation.json */}
{/* "complexText": "Silakan kunjungi <1>blog kami</1> untuk informasi lebih lanjut." */}
</div>
);
}
export default App;
Tambahkan complexText ke file translation.json Anda:
// src/locales/en/translation.json
{
// ...
"complexText": "Please visit <1>our blog</1> for more information."
}
// src/locales/id/translation.json
{
// ...
"complexText": "Silakan kunjungi <1>blog kami</1> untuk informasi lebih lanjut."
}
📌 Penting:
useTranslation()Hook mengembalikan fungsit(translate) dan objeki18n.- Fungsi
t(key, options)digunakan untuk menerjemahkan string berdasarkankey. - Interpolasi variabel dilakukan dengan
{{variabel}}di string terjemahan dan diteruskan melaluioptionsobjek. Transcomponent sangat berguna untuk menerjemahkan blok teks yang mengandung elemen React lainnya (misalnya, link, bold text).
4. Manajemen Terjemahan yang Efisien: Namespaces dan Lazy Loading
Untuk aplikasi skala besar, menempatkan semua terjemahan dalam satu file translation.json akan membuatnya sulit dikelola dan memperlambat loading. i18next mendukung namespaces dan lazy loading untuk mengatasi ini.
Namespaces
Anda bisa membagi terjemahan berdasarkan fitur atau bagian aplikasi (misalnya common, dashboard, auth).
-
Buat folder
locales/en/danlocales/id/menjadi seperti ini:src/locales/ ├── en/ │ ├── common.json │ └── dashboard.json └── id/ ├── common.json └── dashboard.json -
Isi
common.json:// src/locales/en/common.json { "welcome": "Welcome to our app!", "greeting": "Hello, {{name}}!" } // src/locales/id/common.json { "welcome": "Selamat datang di aplikasi kami!", "greeting": "Halo, {{name}}!" }Isi
dashboard.json:// src/locales/en/dashboard.json { "title": "Dashboard Overview", "userCount": "Total users: {{count}}" } // src/locales/id/dashboard.json { "title": "Ikhtisar Dashboard", "userCount": "Total pengguna: {{count}}" } -
Update konfigurasi
i18n.jsAnda:// src/i18n.js // ... i18n // ... .init({ // ... ns: ['common', 'dashboard'], // Daftarkan semua namespaces yang akan digunakan defaultNS: 'common', // Namespace default jika tidak disebutkan // ... }); // ... -
Saat menggunakan
useTranslation, Anda bisa menentukan namespace:import React from 'react'; import { useTranslation } from 'react-i18next'; function DashboardHeader() { // Menggunakan namespace 'dashboard' const { t } = useTranslation('dashboard'); return ( <h2>{t('title')}</h2> ); } function WelcomeMessage() { // Menggunakan namespace default (common) const { t } = useTranslation(); return ( <p>{t('welcome')}</p> ); }
Lazy Loading Terjemahan
Untuk memuat terjemahan hanya saat dibutuhkan (misalnya, saat pengguna mengganti bahasa atau menavigasi ke halaman tertentu), Anda bisa menggunakan i18next-http-backend dan React Suspense.
-
Instal
i18next-http-backend:npm install i18next-http-backend --save -
Update
i18n.js:// src/i18n.js import i18n from 'i18next'; import { initReactI18next } from 'react-i18next'; import LanguageDetector from 'i18next-browser-languagedetector'; import HttpBackend from 'i