Katarzyna Kądziołka
Katarzyna KądziołkaJunior Software Developer @ Code Hydra

Jak zaimplementować i18n w Vue 3 Composition API

Sprawdź, jak w prosty sposób zacząć swoją przygodę z i18n na przykładzie implementacji w Vue 3 Composition API.
24.11.20233 min
Jak zaimplementować i18n w Vue 3 Composition API

i18n to skrót oznaczający internationalization, czyli internacjonalizację. Jest to termin określający procesy i techniki służące do dostosowania oprogramowania do różnych języków i kultur, bez konieczności zmiany kodu źródłowego. i18n umożliwia nie tylko tłumaczenie tekstów, ale też formatowanie dat, czasu, walut i liczb. 

Istnieje wiele narzędzi i bibliotek, ułatwiających implementację założeń i18n. W przypadku środowiska Vue 3 najpopularniejszą biblioteką jest vue-i18n. W tym artykule pokażę Ci, jak w prosty sposób zacząć swoją przygodę z i18n.

Instalacja

NPM:

npm install vue-i18n@9

Yarn:

yarn add vue-i18n@9


Pełną dokumentację znajdziesz tutaj.

Przygotowanie plików

W katalogu src załóż nowy folder o nazwie locales. To tutaj będziesz przechowywał wszystkie pliki z tłumaczeniami. Stwórz nowy plik - en.json. Możesz wybrać inny format (np. YAML), ale ze względu na to, że json jest w tym wypadku bardziej popularny, to on posłuży nam za wzorzec.

"common": {
 "next": "Next",
 "cancel": "Cancel"
},
"home": {
 "logOut": {
   "logIn": "Log in",
   "register": "Register"
 },
  "logIn": {
   "welcome": "Welcome!",
 }
}


Klucze muszą być jednakowe we wszystkich plikach z tłumaczeniami. Jeśli chcesz dodać kolejny język musisz stworzyć nowy plik i dla istniejących kluczy przypisać odpowiednie wartości. Np. dla języka polskiego byłby to plik pl.json.

"common": {
 "next": "Dalej",
 "cancel": "Anuluj"
},
"home": {
 "logOut": {
   "logIn": "Zaloguj się",
   "register": "Załóż konto"
 },
  "logIn": {
   "welcome": "Witaj!",
 }
}

Konfiguracja

Przejdź do pliku main.ts. Zaimportuj utworzone przed chwilą pliki z tłumaczeniami. Następnie musisz skonfigurować i18n.

import pl from "./locales/pl.json" 
import en from "./locales/en.json" 

const i18n = createI18n({ 
  locale: navigator.language, 
  fallbackLocale: "en", 
  messages: { pl, en }, 
  legacy: false 
})


Locale umożliwia określenie jaki ma być język startowy aplikacji. Możesz podać tu konkretny plik, np. “en” albo użyć właściwości navigator.language, który odpowiada językowi przeglądarki użytkownika.

FallbackLocale wskazuje na plik z tłumaczeniami, który zostanie użyty w sytuacji, gdy przeglądarka użytkownika jest w języku, którego Twoja aplikacja nie wspiera lub gdy zabrakło odpowiedniego klucza w innym pliku json.

We właściwości messages deklarujesz pliki z tłumaczeniami. Pole legacy musisz ustawić na false, jeśli używasz Composition API.

Po utworzeniu instancji aplikacji konieczne jest zarejestrowanie pluginu i18n.

const app = createApp(App) 
app.use(i18n) 
app.mount('#app')

Użycie w komponencie

Aby użyć i18n w danym komponencie musisz go zaimportować, a następnie dokonać destrukturyzacji, żeby uzyskać dostęp do funkcji t. Posłuży ona do wykonywania tłumaczeń.

<script setup lang='ts'>
  import {useI18n} from 'vue-i18n' 

  const {t} = useI18n();
</script>


W części HTML zamiast stringów, używaj odpowiednich kluczy, z pomocą funkcji t.

<span>{{t('home.logIn.welcome')}</span> 

Language switcher

Warto dać użytkownikowi możliwość dopasowania języka do swoich preferencji. W tym celu możesz użyć właściwości locale.

<script setup lang="ts">
import {useI18n} from 'vue-i18n'

const {locale} = useI18n();
const currentLanguage = locale.value;

</script>


Aby zmienić aktywny język wystarczy przypisać do locale.value nową wartość, np. “pl”.

Poniżej zaprezentuję moją implementację language switcher’a.

Najpierw dodałam interfejs SelectOption. Label będzie odpowiadał tekstowi wyświetlanemu w Select, a value będzie wskazywał na nazwę pliku z odpowiednim tłumaczeniem.

export interface SelectOption {
   label: string,
   value: string
}


Następnie stworzyłam komponent LanguageSwitcher. Przechowuje on informacje o dostępnych językach, obsługuje ich zmianę oraz komunikuje się z komponentem-dzieckiem BaseSelect. Przyjmuje on właściwość options typu tablica SecetOption oraz obsługuje modelValue typu string.

<script setup lang="ts">
import {useI18n} from 'vue-i18n'
import BaseSelect from "@/components/common/baseSelect/BaseSelect.vue";
import type {SelectOption} from "@/components/common/baseSelect/selectOption";
import {ref, watchEffect} from "vue";

const {locale} = useI18n();


const options: SelectOption[] = [
 {
   label: 'English',
   value: 'en'
 },
 {
   label: 'Polski',
   value: 'pl'
 }
];
const currentLanguage = options.find((x) => x.value === locale.value)?.label ?? "English";
const selectedOption = ref(currentLanguage);

watchEffect(() => {
 locale.value = options.find((x) => x.label === selectedOption.value)!.value;
})

</script>

<template>
 <BaseSelect v-model="selectedOption" :options="options"/>
</template> 


CurrentLanguage sprawdza jaki język jest obecnie ustawiony jako wiodący. Jeśli użytkownik używa języka nieobsługiwanego przez aplikację, zostanie wybrany angielski.

WatchEffect na podstawie zmiany wartości w BaseSelect wyszukuje odpowiednie value i przypisuje do locale.value. 

Dalsze kroki

Vue-i18n daje ogromne możliwości. Warto zapoznać się z kompletną dokumentacją.

<p>Loading...</p>