Post-processor плагины

Роль post-processor в цепочке перевода

В i18next процесс получения финальной строки перевода проходит через несколько этапов: загрузка ресурсов, выбор ключа, интерполяция переменных и последующая обработка результата. Post-processor подключается на финальной стадии и изменяет уже сформированную строку перед возвратом в приложение.

Ключевая особенность этого этапа заключается в том, что входом всегда выступает готовый перевод, а не ключ и не сырые ресурсы. Это делает post-processor удобным инструментом для форматирования, пост-обработки HTML, маскирования текста, применения кастомных правил отображения и интеграции сторонних систем.


Архитектура post-processor в i18next

Post-processor реализуется как объект с методом обработки строки. Он регистрируется в экземпляре i18next и вызывается автоматически при указании имени процессора в опциях перевода.

Общий поток выглядит следующим образом:

  1. Поиск ключа перевода
  2. Интерполяция переменных
  3. Применение post-processor
  4. Возврат результата

Post-processor может быть применён:

  • к отдельному вызову t()
  • глобально через конфигурацию
  • цепочкой (несколько процессоров подряд)

Интерфейс post-processor

Любой post-processor реализует контракт:

  • name — имя процессора
  • process(value, key, options, translator) — функция обработки строки
const myPostProcessor = {
  name: 'myPostProcessor',
  process(value, key, options, translator) {
    return value;
  }
};

Параметры метода process

  • value — строка перевода после интерполяции
  • key — ключ перевода
  • options — параметры вызова t()
  • translator — экземпляр i18next (доступ к API внутри процесса)

Регистрация post-processor

Для подключения используется метод addPostProcessor:

import i18next from 'i18next';

i18next.addPostProcessor('uppercase', {
  name: 'uppercase',
  process(value) {
    return value.toUpperCase();
  }
});

После регистрации процессор становится доступен через опцию postProcess.


Использование post-processor в переводах

Применение происходит через параметр postProcess:

i18next.t('welcome_message', {
  postProcess: 'uppercase'
});

Можно применять несколько процессоров последовательно:

i18next.t('welcome_message', {
  postProcess: 'trim,uppercase'
});

В этом случае строка проходит через цепочку обработчиков слева направо.


Встроенные механизмы post-processing

В экосистеме i18next существует ряд распространённых post-processor решений, применяемых через плагины:

  • форматирование чисел и дат
  • HTML sanitization
  • markdown-парсинг
  • sprintf-подобное форматирование
  • кастомная локализация символов

Каждый из них реализуется как отдельный модуль, подключаемый через addPostProcessor.


Пример: очистка HTML

Post-processor часто используется для фильтрации HTML-строк:

const sanitizePostProcessor = {
  name: 'sanitize',
  process(value) {
    return value.replace(/<script[^>]*>.*?<\/script>/gi, '');
  }
};

i18next.addPostProcessor('sanitize', sanitizePostProcessor);

Использование:

i18next.t('html_content', {
  postProcess: 'sanitize'
});

Пример: форматирование текста

Пост-обработка может использоваться для трансформации строк без изменения переводов:

const exclamationPostProcessor = {
  name: 'exclaim',
  process(value) {
    return `${value}!`;
  }
};

i18next.addPostProcessor('exclaim', exclamationPostProcessor);

Применение:

i18next.t('hello', {
  postProcess: 'exclaim'
});

Доступ к контексту через translator

Третий параметр translator позволяет взаимодействовать с системой перевода:

const debugPostProcessor = {
  name: 'debug',
  process(value, key, options, translator) {
    console.log('Key:', key);
    console.log('Options:', options);
    console.log('Language:', translator.language);
    return value;
  }
};

Это полезно для отладки, аналитики и динамического изменения поведения в зависимости от языка.


Условная логика в post-processor

Post-processor может менять поведение на основе параметров:

const genderPostProcessor = {
  name: 'gender',
  process(value, key, options) {
    if (options.gender === 'female') {
      return value.replace('User', 'User (f)');
    }
    return value;
  }
};

Использование:

i18next.t('user_label', {
  gender: 'female',
  postProcess: 'gender'
});

Цепочки post-processor’ов

Post-processor’ы могут комбинироваться. Порядок выполнения имеет значение:

i18next.t('message', {
  postProcess: 'trim,uppercase,sanitize'
});

Каждый процессор получает результат предыдущего, формируя конвейер обработки строки.


Переиспользование и модульная структура

Post-processor удобно выносить в отдельные модули:

export const capitalizePostProcessor = {
  name: 'capitalize',
  process(value) {
    return value.charAt(0).toUpperCase() + value.slice(1);
  }
};

Подключение:

i18next.addPostProcessor(capitalizePostProcessor.name, capitalizePostProcessor);

Такая структура позволяет:

  • изолировать логику преобразования
  • переиспользовать обработчики между проектами
  • тестировать трансформации отдельно от i18n

Интеграция с интерполяцией

Post-processor применяется после интерполяции:

i18next.t('greeting', {
  name: 'Alex',
  postProcess: 'uppercase'
});

Если перевод:

Hello {{name}}

Результат интерполяции → Hello Alex После post-process → HELLO ALEX


Особенности порядка выполнения

Важно учитывать последовательность этапов:

  • сначала подстановка переменных
  • затем обработка pluralization
  • затем post-processor

Это означает, что post-processor работает с уже финальной формой строки, что исключает необходимость ручной обработки интерполяционных конструкций.


Ошибки и ограничения

Post-processor не предназначен для:

  • изменения ключей перевода
  • доступа к сырому JSON ресурсов
  • выполнения асинхронных операций
  • модификации структуры i18next

Все операции выполняются синхронно. Возвращаемое значение должно быть строкой.


Производительность post-processor’ов

Так как post-processor вызывается при каждом t():

  • сложные регулярные выражения могут влиять на производительность
  • цепочки из большого числа процессоров увеличивают latency
  • лучше избегать тяжёлых вычислений внутри process

Оптимизация достигается за счёт:

  • кэширования результатов
  • минимизации цепочек
  • использования простых трансформаций

Расширенные сценарии применения

Post-processor используется в сложных системах локализации:

  • динамическая фильтрация контента по ролям пользователя
  • адаптация текста под региональные нормы
  • постобработка переводов из внешних систем (CMS)
  • интеграция с форматерами дат, валют и единиц измерения
  • обработка безопасного HTML в многоязычных интерфейсах

Совместимость с middleware и plugins

Post-processor является частью расширяемой архитектуры i18next и может использоваться совместно с:

  • backend plugins (загрузка переводов)
  • language detectors
  • interpolation parsers
  • pluralization rules

Он всегда выполняется после основной цепочки перевода, не влияя на upstream-логику.