Как добавить поддержку нескольких языков в ReactJS
В этом руководстве мы узнаем, как добавить поддержку нескольких языков с помощью react-i18next
библиотеки в проект React.
react-i18next — это мощная интернационализация React/React Native, основанная на i18next.
Содержание
- Создать новый проект
- Разработка
- Добавление переводов
- Переключатель языков
- Оптимизация перевода
- Конечный результат
Создать новый проект
Шаг 1. Запустите приведенный ниже код, чтобы создать новый проект React.
npx create-react-app react-lang-support
После создания проекта проверьте, работает ли он, запустив этот код
cd react-lang-support
npm start
Проект успешно открыт
Шаг 2. Установите зависимости.
Запустите приведенный ниже код, чтобы установить две библиотеки react-i18next
и i18next
npm install react-i18next i18next
react-i18next
- это интернационализация-фреймворк для React и React Native, основанный на i18next
i18next
- интернационализация-фреймворк, написанный на JavaScript и для него
Разработка
Шаг 1. Сначала нам нужно создать новый файл с именем i18n.js
в нашем проекте
Шаг 2. Добавьте следующий код внутрь i18n.js
файла
import i18n from "i18next";
import { initReactI18next } from "react-i18next";
i18n
.use(initReactI18next) // passes i18n down to react-i18next
.init({
// the translations
// (tip move them in a JSON file and import them,
// or even better, manage them via a UI: https://react.i18next.com/guides/multiple-translation-files#manage-your-translations-with-a-management-gui)
resources: {
en: {
translation: {
"Welcome to React": "Welcome to React and react-i18next"
}
}
},
lng: "en", // if you're using a language detector, do not define the lng option
fallbackLng: "en",
interpolation: {
escapeValue: false // react already safes from xss => https://www.i18next.com/translation-function/interpolation#unescape
}
});
Теперь наш файл выглядит так
Шаг 3. Теперь нам нужно сделать наш файл перевода доступным для всего нашего проекта. Вот почему нам нужно импортировать i18n.js
файл внутри index.js
Добавьте код ниже внутри index.js
import "./i18n"
Проверьте, правильно ли вы следуете руководству, посмотрев на этот снимок экрана ниже.
Внутри i18n.js
файла находится объект перевода, состоящий из ключей и значений. Отсюда мы будем использовать эти ключи внутри нашего JSX-файла.
Шаг 4. Внутренний App.js файл позволяет импорировать скобки useTranslation
import { useTranslation } from 'react-i18next';
function App() {
return (
...
)
}
useTranslation
- получает t
функцию i18n
экземпляр внутри вашего функционального компонента.
Шаг 5. Как было сказано выше, мы получим t
функцию из скобок useTranslation
внутри App
компонента.
function App() {
const { t } = useTranslation()
return (
...
)
}
Шаг 6. Теперь мы можем использовать t
функцию внутри нашего JSX. t
функция ищет ключ t('key')
из i18n.js
файла. Наши ключи расположены внутри объекта перевода.
В целом наши App.js выглядят так
import logo from './logo.svg';
import './App.css';
import { useTranslation } from 'react-i18next';
function App() {
const { t } = useTranslation()
return (
<div className="App">
<header className="App-header">
<img src={logo} className="App-logo" alt="logo" />
<p>
Edit <code>src/App.js</code> and save to reload.
</p>
<a
className="App-link"
href="https://reactjs.org"
target="_blank"
rel="noopener noreferrer"
>
{t('Welcome to React')}
</a>
</header>
</div>
);
}
export default App;
Проверьте, что мы сделали до этой части
npm start
Результат
Как видите, мы получили текст «Welcome to React and react-i18next» из нашего i18n.js
файла. Это означает, что мы успешно настроили react-i18next
и теперь готовы к добавлению переводов.
Добавление переводов
В этом проекте будут использоваться три языка. Это узбекский, русский и английский.
Шаг 1. В целях демонстрации добавьте следующие переводы внутрь i18n
файла.
resources: {
uz: {
translation: {
welcome: "Xush kelibsiz",
goodbye: "Xayr"
}
},
ru: {
translation: {
welcome: "Добро пожаловать",
goodbye: "До свидания"
}
},
en: {
translation: {
welcome: "Welcome",
goodbye: "Goodbye"
}
}
}
Теперь наш i18n
файл выглядит так
import i18n from "i18next";
import { initReactI18next } from "react-i18next";
i18n
.use(initReactI18next) // passes i18n down to react-i18next
.init({
// the translations
// (tip move them in a JSON file and import them,
// or even better, manage them via a UI: https://react.i18next.com/guides/multiple-translation-files#manage-your-translations-with-a-management-gui)
resources: {
uz: {
translation: {
welcome: "Xush kelibsiz",
goodbye: "Xayr"
}
},
ru: {
translation: {
welcome: "Добро пожаловать",
goodbye: "До свидания"
}
},
en: {
translation: {
welcome: "Welcome",
goodbye: "Goodbye"
}
}
},
lng: "en", // if you're using a language detector, do not define the lng option
fallbackLng: "en",
interpolation: {
escapeValue: false // react already safes from xss => https://www.i18next.com/translation-function/interpolation#unescape
}
});
Теперь посмотрим результат в браузере.
Как видите, он показывает слова из нашего i18n
файла. Но показывает только английскую версию.
Пусть перейдет на русский язык. Для этого сделаем изменение lng
ключа ru
внутри i18n
файла
import i18n from "i18next";
import { initReactI18next } from "react-i18next";
i18n
.use(initReactI18next) // passes i18n down to react-i18next
.init({
// the translations
// (tip move them in a JSON file and import them,
// or even better, manage them via a UI: https://react.i18next.com/guides/multiple-translation-files#manage-your-translations-with-a-management-gui)
resources: {
uz: {
translation: {
welcome: "Xush kelibsiz",
goodbye: "Xayr"
}
},
ru: {
translation: {
welcome: "Добро пожаловать",
goodbye: "До свидания"
}
},
en: {
translation: {
welcome: "Welcome",
goodbye: "Goodbye"
}
}
},
lng: "ru", // change here
fallbackLng: "en",
interpolation: {
escapeValue: false // react already safes from xss => https://www.i18next.com/translation-function/interpolation#unescape
}
});
Дайте увидим результат
Как видите, на экране отображается русский перевод. Если вам нужен узбекский перевод, просто измените lng
его на uz
. Но возникает вопрос, будет ли каждый раз менять язык вот таким жестко закодированным способом?
Ответ - нет . Мы внедрим переключатель в наш проект.
Переключатель языков
Шаг 1. Внутри App.js
добавьте тег <select>
, чтобы предоставить пользователю возможность выбора языка.
import logo from './logo.svg';
import './App.css';
import { useTranslation } from 'react-i18next';
function App() {
const { t } = useTranslation()
return (
<div className="App">
<header className="App-header">
<img src={logo} className="App-logo" alt="logo" />
<p>
Edit <code>src/App.js</code> and save to reload.
</p>
<select>
<option>Choose language</option>
<option value="uz">Uzbek</option>
<option value="ru">Russian</option>
<option value="en">English</option>
</select>
<a
className="App-link"
href="https://reactjs.org"
target="_blank"
rel="noopener noreferrer"
>
{t('welcome')}
<br />
{t('goodbye')}
</a>
</header>
</div>
);
}
export default App;
Теперь пользователь сможет выбрать язык из <select>
выпадающего списка. Но это не изменит язык, так как мы не реализовали функцию смены языка. Чтобы изменить язык, мы получим экземпляр i18n
из скобок useTranslation
.
Базовый синтаксис смены языка с помощью i18n
i18n.changeLanguage('en-US');
Шаг 2. Нам нужно получить экземпляр i18n
из «useTranslation»
function App() {
const { t, i18n } = useTranslation()
return (
...
)
}
Теперь внутри метода <select>
добавления тега onChange
мы получаем значения из предоставленных опций и передаем их i18n
для изменения языка.
<select onChange={(e) => i18n.changeLanguage(e.target.value)}>
<option>Choose language</option>
<option value="uz">Uzbek</option>
<option value="ru">Russian</option>
<option value="en">English</option>
</select>
Финал App.js
import logo from './logo.svg';
import './App.css';
import { useTranslation } from 'react-i18next';
function App() {
const { t, i18n } = useTranslation()
return (
<div className="App">
<header className="App-header">
<img src={logo} className="App-logo" alt="logo" />
<p>
Edit <code>src/App.js</code> and save to reload.
</p>
<select onChange={(e) => i18n.changeLanguage(e.target.value)}>
<option>Choose language</option>
<option value="uz">Uzbek</option>
<option value="ru">Russian</option>
<option value="en">English</option>
</select>
<a
className="App-link"
href="https://reactjs.org"
target="_blank"
rel="noopener noreferrer"
>
{t('welcome')}
<br />
{t('goodbye')}
</a>
</header>
</div>
);
}
export default App;
Результат: видео1109257644
Оптимизация перевода
Шаг 1. Вы заметили, что наши переводы находятся внутри i18n.js
файла. Мы еще не начали разбивать переводы на несколько файлов (что настоятельно рекомендуется для больших проектов), но мы уже видим, что добавление большего количества языков приведет к объединению ненужных переводов в приложение.
Чтобы отделить наш перевод, мы будем использовать пакет именно i18next-http-backend
, который поможет нам загружать наши переводы асинхронно.
Установите i18next-http-backend
, запустив этот код на терминале
npm install i18next-http-backend
Теперь нам нужно подключить i18next-http-backend к нашему i18n.js
файлу.
mport i18n from "i18next";
import { initReactI18next } from "react-i18next";
import backend from "i18next-http-backend"; // <--- import here
i18n
.use(initReactI18next) // passes i18n down to react-i18next
.use(backend) // <--- wire up here
.init({
// the translations
// (tip move them in a JSON file and import them,
// or even better, manage them via a UI: https://react.i18next.com/guides/multiple-translation-files#manage-your-translations-with-a-management-gui)
resources: {
uz: {
translation: {
welcome: "Xush kelibsiz",
goodbye: "Xayr"
}
},
ru: {
translation: {
welcome: "Добро пожаловать",
goodbye: "До свидания"
}
},
en: {
translation: {
welcome: "Welcome",
goodbye: "Goodbye"
}
}
},
lng: "en", // if you're using a language detector, do not define the lng option
fallbackLng: "en",
interpolation: {
escapeValue: false // react already safes from xss => https://www.i18next.com/translation-function/interpolation#unescape
}
});
Как только мы подключимся i18next-http-backend
, по умолчанию он загрузит перевод с этого пути.
'../public/locales/{lang}/translation.json'
Этот путь считается по умолчанию для i18next-http-backend
загрузки.
Шаг 2. Нам нужно создать этот путь locales/{lang}/translation.json
внутри общей папки.
Теперь нам нужно удалить эту часть кода из i18n.js
файла
И добавьте наши переводы внутри translation.json
файла для каждого языка.
UZ
RU
EN
Теперь проверьте результат в браузере