Локализация Contentful: где ломается мультиязычный контент
В Contentful мультиязычность — свойство модели, а не отдельный модуль: каждое поле записи либо локализуемо, либо общее для всех локалей. Первый сбой растёт именно отсюда — заголовок и текст помечены локализуемыми, а часть адреса, обложка и метаполя остались общими. Английская версия открывается, но адрес и превью в ней русские: это уже не перевод, а смесь языков.
Дальше — рассинхрон переводов. Редактор правит текст в базовой локали, перевод обновляется вручную и отстаёт; чем чаще выходят правки, тем шире расхождение, и через месяц никто не скажет, какая версия актуальна. Резервная локаль маскирует проблему: посетитель видит подставленный текст основного языка и не понимает, почему половина страницы чужая.
Отдельная история — дубли записей. Если локализацию не настроили сразу, команда заводит по записи на каждый язык и связывает их руками: связи рвутся при первом переименовании, ассеты дублируются, реестр растёт быстрее контента, а две версии начинают конфликтовать по одному и тому же адресу.
Сверху ложится переключатель языка. Он строится по списку локалей в пространстве, а не по факту наличия перевода, поэтому нажатие на другой язык ведёт на пустую страницу или на битый адрес версии — часть адреса не локализована, маршрут собран по старому шаблону. Ниже разбираем, как это закрывается на уровне модели, маршрутов и сборки.
Что даёт управляемая многоязычность сайта
Языковая версия — это не копия страницы, а отдельная запись с локалью и правилом подстановки. Когда схема версий описана в модели контента, а не в шаблонах, редактор наполняет страницу на новом языке теми же полями, что и на основном, а разработчик не переносит разметку руками. В Contentful локали, связи между версиями и история изменений живут в одном хранилище — отсюда и управляемость.
Четыре эффекта, которые видно в метриках.
- Срок выпуска страницы. Новый язык собирается из готовых блоков: переводится текст, структура и компоненты переиспользуются. Вместо выкладки отдельной копии со своей вёрсткой — публикация локали в том же дереве.
- Объём ручных правок. Подстановка настраивается по полю: пустой перевод показывает значение языка по умолчанию. Раздел открывается, не дожидаясь полного перевода, а правка текста не расходится по копиям.
- Класс отказов. Языковые адреса и связи между версиями строятся из данных, а не из ручных списков. Уходит типовой сбой, когда после релиза часть локалей отдаёт основной язык или теряет страницу.
- Доля зарубежного трафика. Посетитель попадает на свой язык с первого захода и остаётся на нём. Растёт доля визитов на локальной версии и глубина просмотра, потому что переключать язык вручную не нужно.
Схема версий задаёт и порядок работы: новую локаль включают настройкой, а не отдельным проектом.
Модели локализации Contentful: сравнение вариантов
Contentful хранит языковые версии двумя разными способами: перевод на уровне поля внутри записи либо отдельная запись под каждый язык. Модели локализации отличаются не только хранением — от них зависят схема адресов, подстановка недостающих переводов и права редакторов, а смена модели посреди проекта обходится дороже, чем выбор на старте.
| Вариант | Когда подходит | Ограничения |
|---|---|---|
| Язык как поле записи | Набор полей одинаков для всех языков, переводы публикуют синхронно | Одна схема на все языки: поле под отдельный рынок не добавить, права на язык не раздать |
| Отдельная запись на язык | У рынков свои поля, свои даты публикации и собственные связи | Межъязыковые связи дублируются вручную и рассинхронизируются, объём контента растёт пропорционально числу языков |
| Отдельное пространство под язык | Нужна изоляция: свои модели, права и независимый график релизов | Схему синхронизируют вручную, медиа дублируется, сквозной поиск по языкам не работает |
Выбор модели ведут по трём признакам: расходятся ли схемы между рынками, кто отвечает за публикацию и сколько языков планируется в ближайший год. Дальше модель задаёт поведение подстановки: при локализации на уровне поля недостающий перевод отдаёт базовая локаль по каждому полю отдельно, а при отдельных записях связи между языками приходится вести самому.
Этапы внедрения мультиязычного контура
Мультиязычный контур ломается не на переводах, а на модели данных: пока локаль не заведена в структуру, каждый новый язык превращается в ручное дублирование записей и расхождение версий. Ниже — шесть шагов, где каждый опирается на предыдущий, поэтому переделки не всплывают на середине.
- Аудит контентной модели. Разбираем типы записей Contentful и поля: где текст, где ссылки на другие записи, где значения зашиты в шаблон. Отмечаем поля, обязательные к переводу, и общие для всех языков — изображения, ключи интеграций, служебные значения.
- Проектирование схемы языков. Фиксируем перечень локалей, основную локаль и региональные варианты с едиными кодами. Отдельно решаем, нужны ли варианты письма справа налево и как это сказывается на вёрстке — от этого зависят макеты и длина строк.
- Правила резервной подстановки. Задаём цепочку: нет перевода — берём значение регионального варианта, затем основной локали. Определяем поля, где подстановка допустима, и те, где нужен полный перевод, иначе чужой текст всплывёт на витрине.
- Настройка и связка с рендерингом. Локали привязываем к адресам, добавляем языковые альтернативы для поисковых систем, переключатель и метаданные. Общие элементы — меню, подвал, форматы дат и чисел — переводим словарями, а не дублями записей.
- Проверка переключения. Прогоняем все маршруты в каждой локали: пустые поля, битые ссылки, обрезанные кнопки, поведение кэша и индексация. Смотрим не только главную, но и карточки, формы и страницы ошибок.
- Приёмка и передача. Отдаём чек-лист добавления локали, регламент для редакторов и список полей, обязательных к заполнению. Дальше новый язык заводится по инструкции, без правок в коде.
Что передаём после внедрения: конфигурации и регламенты
Передаём не набор разрозненных настроек, а рабочую модель мультиязычного контента: у каждого артефакта есть владелец в вашей команде и понятный порядок изменений. Ниже — что именно остаётся у вас после запуска и по каким точкам инженер принимает работу.
- Конфигурация языков. Список локалей, язык по умолчанию и цепочка подстановки «язык-регион → язык → основной»: незаполненное поле показывает осмысленный текст, а не пустой блок в вёрстке.
- Схемы связей записей. Карта типов контента и ссылок между ними: что переводится отдельной записью, а что остаётся общим (изображения, справочники, характеристики). Отдельно — как связи не распадаются при добавлении нового языка.
- Политики доступа к черновикам. Роли переводчика, редактора и разработчика, права на предпросмотр неопубликованного контента и запрет публикации в основной канал для внештатных авторов.
- Регламент выпуска переводов. Порядок «черновик → вычитка → публикация», ответственный за утверждение и правило для частично переведённых материалов.
- Правила маршрутизации. Формирование адресов по языкам, редиректы со старых адресов, определение языка посетителя — на уровне маршрутизатора приложения.
- Автопроверки полноты. Задача на этапе сборки сообщает о локали с незаполненными обязательными полями: пропущенный перевод не доезжает до пользователя.
- Документация. Карта контентных моделей, инструкция для редакторов, схема ролей и токенов доступа.
- Передача и сопровождение. Запись обсуждения спорных мест, журнал публикаций и канал для вопросов после запуска.
Опишите задачу — вернёмся с оценкой и планом, включая перечень артефактов под ваш контур.
Кейс: 12 языков и рост доли зарубежного трафика
Что было до
Контент для каждого языка лежал в отдельной таблице, а строки интерфейса — прямо в компонентах. Новая локаль означала правки в четырёх десятках файлов, и ни один не был связан с остальными: перевод приходил позже вёрстки, и мы вручную сверяли, что не осталось пустых блоков. Недостающий ключ отдавался как пустая строка — пользователь видел дыру в разметке вместо английского текста.
Срок выпуска языковой версии — около трёх недель: половина на правки, половина на проверку регрессий.
Что изменили
Контент переехал в Contentful, локализуемые поля описаны на уровне модели: у сущности один набор полей и значения по локалям, а не параллельные копии записей. Цепочка подстановки задана явно — если польского текста нет, отдаётся английский. Сборка формирует статическую страницу для каждой локали, указатели языка и карта сайта генерируются из того же списка локалей. Проверка полноты словаря встроена в сборку: неполный перевод блокирует слияние и не доходит до пользователей.
Что стало
Срок выпуска новой локали — два дня: переводчик работает в интерфейсе редактора, разработчик подключает маршрут и подстановку. Объём ручных правок при выпуске языка упал примерно в восемь раз — сверка ключей ушла из процесса. Класс ошибок «пустой блок вместо перевода» закрыт конструктивно. Доля зарубежных посетителей выросла с 4% до 19% после первых шести языков и до 27% к двенадцати.
Что делать, если контент уже переведён, а схема языков меняется
Частично настроенная многоязычность в Contentful — самый частый случай: две-три локали заведены, часть полей локализована, часть тянется из базовой через подстановку, а код языка зашит в маршрут. Смена схемы языков здесь не «переключение настройки», а миграция данных: у каждой записи меняется набор локализованных полей и связей.
Начинаем с инвентаризации: какие типы контента действительно переведены, где перевод лежит в нелокализуемом поле, какие локали включены, но пусты, и по какой цепочке сейчас идёт подстановка. Отдельно смотрим поля-связки и ссылки на медиа — при смене схемы рвутся именно они, а не тексты.
Миграцию контента выполняем скриптом через API управления: выгружаем записи со всеми локалями, сопоставляем старые коды языков с новыми, пишем обратно. Работаем на копии окружения, скрипт идемпотентен и перезапускаем: сначала переносим справочники, затем контент, который на них ссылается. Перед прогоном фиксируем снимок — он же служит точкой отката.
Адреса сохраняем через таблицу соответствия локалей маршрутам, а не через код языка в пути. Старые пути продолжают отвечать постоянным перенаправлением, новые добавляются рядом — внешние ссылки и поисковая выдача не теряются.
Главный риск перехода — тихие пустые поля: после смены цепочки подстановки запись собирается, но отдаёт пустоту. Поэтому цепочку выстраиваем явно, прогоняем сборку и инвалидацию кэша до переключения, а саму схему меняем за один проход, чтобы не остаться в состоянии полуперехода.
Технические сомнения по мультиязычной схеме
На согласовании объёма работ по локализации Contentful повторяются одни и те же пять развилок. Отвечаем на них до старта — чтобы спорные места не всплыли в середине внедрения, когда менять решение уже поздно.
Что показывать на языке, где перевода ещё нет?
Для каждого поля задаём язык-источник. Пустое значение не оставляет дыру в вёрстке: посетитель видит осмысленный текст, а резервная подстановка работает на уровне поля — частично переведённая страница остаётся целой.
Что с адресами страниц на каждом языке?
Адреса строим из локализованного заголовка либо оставляем стабильный нейтральный адрес с префиксом языка. Второй вариант дешевле в поддержке: ссылки не рвутся при правке текста, а перенаправления нужны только при смене структуры.
Обязательно переводить все поля сразу?
Нет. Делим поля на обязательные к переводу и вспомогательные — служебные подписи, технические описания, значения по умолчанию. Частичный перевод сокращает первый этап, а полнота наполнения видна в отчёте по языкам.
Не замедлит ли мультиязычность сборку?
Сборка идёт только по изменившимся языкам и полям, остальное берётся из кэша. Добавление языка прибавляет секунды, а не минуты — если схему контента заложили заранее, а не доклеивали поверх готовых страниц.
Кто отвечает за качество переводов?
Мы отвечаем за схему, подстановку, адреса и сборку. Тексты — на стороне заказчика или его переводчика; со своей стороны даём глоссарий, перечень обязательных полей и отчёт о пробелах, чтобы пропуски были видны до публикации.
Обсудим задачу: схема языков, сроки и порядок работ
Чтобы вернуться с оценкой сроков и планом внедрения, а не с общими словами, нужны входные данные: перечень локалей и их приоритет, кто переводит и кто публикует контент, текущая схема типов и полей, а также как устроена маршрутизация языков в приложении. Из этого складывается состав работ, и уже по нему считаем сроки по этапам.
Порядок работ выстраиваем так, чтобы каждый шаг опирался на проверенный предыдущий:
- фиксируем схему локалей и цепочки фолбэка: какой язык подставляется, когда перевода нет, и что при этом видит пользователь;
- правим контент-модель: где поле локализуемое, где общее, какие связи нельзя дублировать по языкам;
- настраиваем переключение языка и адреса страниц, включая корректные метаданные для поисковых систем;
- описываем роли редакторов и порядок публикации: кто переводит, кто проверяет, в какой очерёдности выходит локаль;
- ловим неполные переводы, смешанные языки внутри одного документа и поведение кэша при обновлении локали;
- передаём документацию: схему локалей, соглашения по полям и инструкцию для редакторов.
Каждый пункт получает отдельную оценку, поэтому часть объёма можно закрывать поэтапно — например, сначала две локали, затем остальные. Опишите задачу и текущее состояние контента — вернёмся с планом внедрения, составом работ и сроками.







