# General Translation Knowledge Base: Как мигрировать с react-i18next на gt-react?
URL: https://generaltranslation.com/ru/kb/migrate-from-react-i18next.mdx
Docs index: https://generaltranslation.com/llms.txt
Description: Установите gt-react рядом с react-i18next, используйте общий cookie-файл локали и переносите компоненты по одному — с ключей t() и `<Trans>` на встроенный текст в `<T>` и useGT. General Translation переводит перенесённый текст, используя его JSX как контекст, а ваша команда может исправить перевод в панели управления. Ещё не перенесённые компоненты сохраняют проверенные переводы react-i18next.
Category: Интернационализация
Last updated: 2026-11-11
Authors: Kevin Wu
Published: 2026-11-11

react-i18next выполняет рендеринг переводов, которые вы записываете в отдельный JSON-файл для каждого языка и пространства имён. gt-react выполняет рендеринг текста, написанного прямо в компонентах, а General Translation генерирует переводы с помощью [`npx gt translate`](/docs/cli/reference/commands/translate). Миграция сводится к тому, чтобы заменить каждый поиск по ключу `t('key')` исходным текстом, на который он ссылается. Переносить можно по одному компоненту, пока обе библиотеки работают параллельно.

Чтобы пользоваться General Translation, мигрировать не обязательно. CLI `gt` обнаруживает `i18next` в вашем `package.json` и переводит JSON-файлы i18next, сохраняя синтаксис переменных `{{variable}}`. Мигрировать стоит, если вы хотите держать текст рядом с JSX, который выполняет его рендеринг, не придумывать ключи и не синхронизировать файлы для каждого языка вручную.

## Как API react-i18next соотносятся с gt-react?

| react-i18next                                      | gt-react                                                                                                                                                                                                                       |
| -------------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
| `i18n.init({ lng, supportedLngs, resources })`     | `gt.config.json` (`defaultLocale`, `locales`) и [`initializeGTSPA`](/docs/react/reference/config#initialize-spa) во входном файле                                                                                              |
| `I18nextProvider` / `initReactI18next`             | В одностраничном приложении (SPA) провайдер не нужен; приложения, отрисованные на сервере, используют [`initializeGT`](/docs/react/reference/config#initialize) с [`GTProvider`](/docs/react/reference/components/gt-provider) |
| `<Trans i18nKey="..." components={...}>`           | [`<T>`](/docs/react/reference/components/t), в который оборачивается сам JSX, а ссылки и разметка пишутся прямо внутри                                                                                                         |
| `t('key')` для строк                               | [`useGT`](/docs/react/reference/hooks/use-gt) с исходной строкой или [`useTranslations`](/docs/react/reference/hooks/use-translations), если нужно сохранить ключи                                                             |
| Интерполяция `{{name}}`                            | [`<Var>`](/docs/react/reference/components/var) в JSX; `{name}` в строках                                                                                                                                                      |
| `key_one` / `key_other` с `count`                  | [`<Plural>`](/docs/react/reference/components/plural) в JSX; ICU `{n, plural, ...}` в строках                                                                                                                                  |
| `useTranslation('ns')` или `keyPrefix`             | `useTranslations('ns')` ограничивает поиск по ключу заданным префиксом                                                                                                                                                         |
| `{{val, number}}` и другие средства форматирования | [`<Num>`](/docs/react/reference/components/num), [`<Currency>`](/docs/react/reference/components/currency) и [`<DateTime>`](/docs/react/reference/components/datetime)                                                         |
| `i18n.changeLanguage()` / `i18n.language`          | [`useSetLocale`](/docs/react/reference/hooks/use-set-locale) / [`useLocale`](/docs/react/reference/hooks/use-locale) или компонент [`<LocaleSelector>`](/docs/react/reference/components/locale-selector)                      |
| `i18next-browser-languagedetector`                 | Встроенное определение: сначала cookie-файл `generaltranslation.locale`, затем языки браузера                                                                                                                                  |
| `fallbackLng`                                      | Если перевода нет, выполняется рендеринг исходного текста                                                                                                                                                                                 |

## Шаг 1: Установите gt-react вместе с react-i18next

Следуйте руководству [Быстрый старт SPA для React](/docs/react/react-spa-quickstart), если у вас приложение на Vite или webpack, либо руководству [Быстрый старт React](/docs/react/react-quickstart), если приложение отрисовывается на сервере. В SPA настройка выглядит так:

1. Установите `gt-react` и CLI `gt` как dev-зависимость.
2. Создайте `gt.config.json` с той же исходной локалью и теми же целевыми локалями, что и в конфигурации i18next.
3. Добавьте функцию [`loadTranslations`](/docs/react/reference/functions/load-translations) и вызовите [`initializeGTSPA`](/docs/react/reference/config#initialize-spa) во входном файле, который импортирует остальную часть приложения только после загрузки переводов.
4. Войдите с помощью [`npx gt login`](/docs/cli/reference/commands/login) и укажите идентификатор проекта.

Оставьте `i18n.init` и JSON-файлы на месте. Пока вы не перенесёте хотя бы один компонент, для пользователей ничего не изменится. Если в `gt.config.json` ваши файлы i18next указаны в `files`, удалите эту запись, чтобы за перевод каждой строки отвечал только один источник: JSON хранит переводы для ещё не мигрированных компонентов, а новый или изменённый текст пишется прямо в коде с помощью gt-react.

## Шаг 2: Используйте одну активную локаль

Две библиотеки могут по-разному определять язык пользователя. Пусть переключателем будет gt-react, а i18next читает тот же cookie-файл:

```ts title="src/i18n.ts"
import i18n from 'i18next';
import LanguageDetector from 'i18next-browser-languagedetector';
import { initReactI18next } from 'react-i18next';

i18n
  .use(LanguageDetector)
  .use(initReactI18next)
  .init({
    // ...ваши текущие параметры
    detection: {
      order: ['cookie', 'navigator'],
      lookupCookie: 'generaltranslation.locale', // cookie-файл, в который пишет gt-react
      caches: [],
    },
  });
```

Замените старое меню выбора языка на [`<LocaleSelector>`](/docs/react/reference/components/locale-selector) из gt-react или на элемент управления, который вызывает [`useSetLocale`](/docs/react/reference/hooks/use-set-locale). В SPA при смене языка записывается cookie-файл и страница перезагружается, поэтому обе библиотеки сразу запускаются на новом языке. Прежде чем двигаться дальше, проверьте переходы между уже мигрированными и ещё не мигрированными экранами.

## Шаг 3: переносите компоненты по одному

Скопируйте текст на исходном языке из JSON в компонент, а переменные оставьте переменными. Было:

```json title="public/locales/en/translation.json"
{
  "inbox": "Hi {{name}}, <link>open your inbox</link>.",
  "messages_one": "You have {{count}} message",
  "messages_other": "You have {{count}} messages"
}
```

```tsx title="src/Inbox.tsx"
import { Trans, useTranslation } from 'react-i18next';

export function Inbox({ name, count }: { name: string; count: number }) {
  const { t } = useTranslation();
  return (
    <>
      <Trans i18nKey="inbox" values={{ name }} components={{ link: <a href="/inbox" /> }} />
      <p>{t('messages', { count })}</p>
    </>
  );
}
```

После:

```tsx title="src/Inbox.tsx"
import { T, Var, Plural, Num } from 'gt-react';

export function Inbox({ name, count }: { name: string; count: number }) {
  return (
    <T>
      Hi <Var>{name}</Var>, <a href="/inbox">open your inbox</a>.
      <p>
        <Plural
          n={count}
          singular={<>You have <Num>{count}</Num> message</>}
          plural={<>You have <Num>{count}</Num> messages</>}
        />
      </p>
    </T>
  );
}
```

Ссылка остаётся настоящим элементом `<a>`, а не превращается в нумерованный плейсхолдер. General Translation переводит весь блок целиком, используя его структуру как контекст, а на основе написанных вами форм `singular` и `plural` генерирует формы, нужные каждому языку перевода, например формы `few` и `many` в польском. Затем [`<Plural>`](/docs/react/reference/components/plural) выбирает подходящую форму для каждого числа.

Для строк вне JSX, например подсказок в полях ввода и всплывающих уведомлений, используйте [`useGT`](/docs/react/reference/hooks/use-gt). Переменные заключаются в одинарные фигурные скобки, а для неоднозначных слов можно добавить контекст:

```tsx
import { useGT } from 'gt-react';

function Search({ count }: { count: number }) {
  const gt = useGT();
  return <input placeholder={gt('Search {count} projects', { count })} />;
}

// В обработчике событий с подсказкой для переводчика:
toast(gt('Saved {fileName}', { fileName, $context: 'toast after saving a file' }));
```

Первый аргумент должен быть статической строкой, а не шаблонным литералом или результатом конкатенации. После переноса каждого пакета компонентов запускайте [`npx gt translate`](/docs/cli/reference/commands/translate) и проверяйте все локали.

## Можно ли сохранить ключи переводов?

Да. Перенесите ключи в единый [словарь](/docs/react/guides/translating-with-dictionaries) gt-react и замените `useTranslation` на [`useTranslations`](/docs/react/reference/hooks/use-translations). Сам вызов для поиска по ключу не меняется:

```tsx
// До
import { useTranslation } from 'react-i18next';
const { t } = useTranslation();

// После
import { useTranslations } from 'gt-react';
const t = useTranslations();

return <h1>{t('home.welcome', { name })}</h1>;
```

Записи словаря используют формат ICU MessageFormat, поэтому в JSON нужно внести три изменения:

* `{{name}}` заменяется на `{name}`.
* Ключи форм множественного числа объединяются в одну запись: `"messages": "You have {count, plural, one {# message} other {# messages}}"`.
* Файлы пространств имён объединяются в один `dictionary.json`, где каждое пространство имён становится ключом верхнего уровня. `useTranslation('settings')` заменяется на `useTranslations('settings')`.

[`npx gt validate`](/docs/cli/reference/commands/validate) выдаёт предупреждения о записях с некорректным синтаксисом ICU. В отличие от i18next, который при отсутствии записи возвращает ключ, [`useTranslations`](/docs/react/reference/hooks/use-translations) выбрасывает исключение, поэтому следите, чтобы id и записи были синхронизированы.

## Что происходит с существующими переводами?

Компоненты, которые вы ещё не перенесли, по-прежнему рендерят проверенные переводы react-i18next, поэтому поэтапная миграция затрагивает только те экраны, с которыми вы работаете. Для текстов, перенесённых в [`<T>`](/docs/react/reference/components/t), [`useGT`](/docs/react/reference/hooks/use-gt) или словарь gt-react, [`npx gt translate`](/docs/cli/reference/commands/translate) создаёт новые переводы с учётом JSX-структуры [`<T>`](/docs/react/reference/components/t) и добавленного вами контекста. Glossary и пользовательские промпты [контекстной группы](/docs/platform/dashboard/guides/defining-context-for-translations) помогают сохранить вашу терминологию и тон. После этого рецензенты могут поправить любые формулировки в [панели управления](/docs/platform/dashboard/guides/reviewing-translations).

Если все проверенные переводы должны остаться в точности такими, как есть, оставьте react-i18next и поручите General Translation переводить его JSON-файлы. (См. [General Translation vs. i18next](/kb/general-translation-vs-i18next).)

## Шаг 4: Удалите react-i18next

Когда поиск по `useTranslation`, `<Trans` и `i18next` перестанет что-либо находить, удалите файл `i18n.init`, JSON-файлы, детектор языка, а также зависимости `i18next` и `react-i18next`. Затем добавьте [`npx gt translate`](/docs/cli/reference/commands/translate) в процесс сборки или в [CI](/kb/translations-in-ci), чтобы в каждом релизе новые тексты сразу выходили переведёнными.

## Часто задаваемые вопросы

### Нужно ли мигрировать всё сразу?

Нет. Обе библиотеки могут выполнять рендеринг на одной странице, если они используют одну и ту же локаль. Переносите маршруты или функции по одному, а i18next удалите, когда его перестанет использовать последний компонент.

### Поддерживает ли gt-react серверный рендеринг?

Да. В приложениях React с серверным рендерингом вместо [`initializeGTSPA`](/docs/react/reference/config#initialize-spa) используется [`initializeGT`](/docs/react/reference/config#initialize) вместе с [`GTProvider`](/docs/react/reference/components/gt-provider). Подробнее см. в руководстве [Быстрый старт React](/docs/react/react-quickstart), а если вы используете `gt-next` — в руководстве [Быстрый старт Next.js](/docs/react/nextjs-quickstart).

### Бесплатен ли gt-react?

gt-react распространяется под лицензией MIT и выполняет рендеринг переводов, включённых в сборку, без учётной записи. Генерация переводов с помощью General Translation [оплачивается по факту использования](https://generaltranslation.com/pricing).

## Ключевые выводы

* Используйте gt-react параллельно с react-i18next, направьте детектор языка i18next на cookie-файл `generaltranslation.locale` и переключайте языки через gt-react.
* Замените `<Trans>` и поиск по ключу встроенным текстом в [`<T>`](/docs/react/reference/components/t) и [`useGT`](/docs/react/reference/hooks/use-gt); `{{var}}` заменяется на [`<Var>`](/docs/react/reference/components/var) или `{var}`, а ключи форм множественного числа — на [`<Plural>`](/docs/react/reference/components/plural) с `singular` и `plural`.
* Компоненты, которые вы не переносили, сохраняют проверенные переводы; перенесённый текст переводится с использованием его JSX в качестве контекста и проходит проверку в панели управления.
* Чтобы сохранить ключи, преобразуйте JSON в единый ICU-словарь и используйте [`useTranslations`](/docs/react/reference/hooks/use-translations).
* Удаляйте i18next, только когда он больше нигде не используется, а затем запускайте [`npx gt translate`](/docs/cli/reference/commands/translate) в CI.

## Related questions

- [Альтернативы i18next: General Translation или i18next](https://generaltranslation.com/ru/kb/general-translation-vs-i18next.mdx): Выбирайте General Translation, если хотите хранить тексты прямо в React-компонентах и создавать переводы с учётом их JSX-структуры и контекста продукта. Можно также оставить i18next и переводить существующие каталоги с помощью General Translation. i18next отвечает за рендеринг сообщений и выбор форм множественного числа, а сами переводы предоставляет отдельный сервис.
- [Как перевести React-приложение?](https://generaltranslation.com/ru/kb/translate-react-app.mdx): Перевод React-приложения состоит из двух этапов — интернационализации компонентов, чтобы они отображались на языке пользователя, и перевода каждой строки на все поддерживаемые языки. gt-react от General Translation переводит JSX на месте в компоненте `<T>`, а npx gt translate создаёт по одному файлу на каждый язык.
- [Как перевести строки вне JSX?](https://generaltranslation.com/ru/kb/translate-strings-outside-jsx.mdx): Пропускайте каждую строку, которая не является дочерним элементом JSX (например, плейсхолдер или константу в области видимости модуля), через функцию перевода в том месте, где выполняется её рендеринг. Такую функцию возвращает хук useGT от General Translation, а msg вместе с useMessages переводит константы, определённые вне компонента.
- [Как работать с формами множественного числа в React?](https://generaltranslation.com/ru/kb/how-to-handle-plurals-in-react.mdx): Чтобы работать с формами множественного числа в React, задайте для каждого языка по одному предложению на каждую форму множественного числа и выбирайте нужное по правилам множественного числа этого языка — ведь в английском 2 формы, в русском 4, а в арабском 6. Компонент `<Plural>` от General Translation в gt-react и gt-next принимает формы на исходном языке, а General Translation генерирует формы, нужные каждому языку перевода.
- [Как поддерживать переводы в актуальном состоянии при каждом развёртывании?](https://generaltranslation.com/ru/kb/translations-in-ci.mdx): Запускайте перевод как этап конвейера перед каждой сборкой для рабочей среды — тогда новые тексты попадут в то же развёртывание, что и сами изменения, уже переведёнными. В CLI gt от General Translation для этого служит команда npx gt translate, которая использует ключ API проекта и идентификатор проекта, сохранённые как секреты CI.

## Previous and next questions

- Previous question: [Как мигрировать с next-intl на gt-next?](https://generaltranslation.com/ru/kb/migrate-from-next-intl.mdx)
- Next question: [Как мигрировать с vue-i18n на gt-vue?](https://generaltranslation.com/ru/kb/migrate-from-vue-i18n.mdx)

## Sitemap

See the [Knowledge Base sitemap](https://generaltranslation.com/ru/kb/sitemap.md) for every article.
