Одна статья 19 языков: структура файлов, prompt перевода, 5 реальных ловушек, как POST за раз.
Официальная документация Anthropic и OpenAI только на английском. Это огромная дыра в глобальной экосистеме контента для AI-разработчиков. how2claude закрывает эту дыру — каждая статья выходит сразу на 19 языках: zh / en / zh-TW / ja / ko / es / pt-BR / id / vi / tr / ar / fr / de / it / ru / uk / pl / he / th.
Нанимать людей нереально (20 переводов на статью, по несколько тысяч долларов за каждый). Отдать это Claude — предельная стоимость сваливается почти до нуля, но кинуть через забор «переведи на японский» и получаешь текст с ярко выраженным машинным привкусом, где голос автора испарился. Дальше — полный поток, как делать это правильно: структура файлов, как писать переводческий prompt, где Claude гарантированно спотыкается, как отправить 19 языков плюс твиты по языкам на API одним POST.
Две очень разные вещи.
Перевод переносит смысл с языка A на язык B — то, что делает Google Translate. Читается «правильно», но «плоско».
Локализация сохраняет регистр, ритм и технический уровень автора, переписывая на «голосе тех-блога» целевого языка. Результат читается так, будто написано носителем.
Перевод для Claude — работа на 5 минут; локализация требует, чтобы в prompt было прописано:
Команда /write-article в how2claude несёт стилевое требование на каждый язык:
| Файл языка | Стилевое требование |
|---|---|
ja.md |
Тон тех-блога, естественный японский |
ko.md |
Тон тех-блога, естественный корейский |
zh-TW.md |
Тайваньское словоупотребление, традиционные иероглифы |
ar.md |
Современный стандартный арабский (письменный) |
id.md |
Стандартный индонезийский |
Выглядит как одна лишняя строка. Но для Claude это определяющее — без неё по умолчанию выходит «учебниковый перевод».
Одна папка на черновик, 20 файлов:
docs/drafts/let-claude-translate-articles/
├── meta.json # title + summary для всех 19 языков
├── zh.md # китайский (источник, пишется первым)
├── en.md # английский (первая волна переводов)
├── zh-TW.md
├── ja.md
├── ko.md
├── ...(ещё 14)
└── th.md
meta.json:
{
"category_slug": "use-cases",
"series_slug": "writing",
"free": true,
"title": {
"zh": "让 Claude 把一篇文章翻译成 19 种语言",
"en": "Letting Claude Translate One Article Into 19 Languages",
"ru": "Дать Claude перевести одну статью на 19 языков",
"...": "..."
},
"summary": {
"ru": "Одна статья 19 языков: структура файлов, prompt перевода, 5 реальных ловушек, как POST за раз.",
"...": "..."
}
}
Первая строка каждого файла .md — # заголовок, остальное — тело. Title берётся не из первой строки md, а из meta.json — так у каждого языка заголовок — это отдельно отточенная короткая фраза, а не первая фраза статьи, которая при переводе могла раздуться.
Два неправильных потока:
Неправильно: цепочка переводов. zh → en → ja → ko → ...
Проблема: ja опирается на en, ko на ja — каждый прыжок теряет крупицу смысла. К моменту th (тайский) — информация четвёртых рук.
Правильно: лучевой перевод. Закрыть zh → сгенерировать en / ja / ko / ar / id / ... напрямую из источника.
Каждый язык выходит прямо из оригинала, без пересадочных станций.
Структура prompt (упакована в /write-article):
Это статья тех-блога про X, источник — китайский:
[полный zh.md]
Переведи на следующие языки, с требованиями по языку:
- ja.md: тон тех-блога, естественный японский
- ko.md: тон тех-блога, естественный корейский
- ar.md: современный стандартный арабский (письменный)
...
Правила:
1. Сохраняй прямой, профессиональный, слегка самоироничный регистр автора
2. Не переводи блоки кода, команды, имена API, URL
3. Заголовки, подзаголовки, ход абзацев можно перекомпоновывать
4. Отдельный title по языку — короткий, с крючком, не буквальный перевод исходного заголовка
Переводить 18 языков параллельно, одна сессия Claude — всё. Один важный момент: делать в одной сессии / на одной версии модели — голос дрейфует между сессиями и поколениями модели.
X считает CJK-символы (китайский/японский/корейский) строже. Я попросил Claude генерировать твиты с такими ограничениями:
На первом проходе три китайских твита вылезли за лимит (160, 164, 152). Claude буквально перевёл английские твиты — английский твит на 260 символов в китайском выходит ровно на границу.
Правило: китайские твиты нужно переписывать, а не переводить. Требования: потолок 140 символов, обязательный крючок, небольшая потеря деталей допустима.
zh → zh-TW провоцирует лень: прогнать через конвертер упрощённого в традиционный. Иероглифы совпадают, словарь — нет:
| zh | zh-TW (неправ.) | zh-TW (прав.) |
|---|---|---|
| 文件 | 文件 | 檔案 |
| 信息 | 信息 | 資訊 |
| 软件 | 軟件 | 軟體 |
| 视频 | 視頻 | 影片 |
Когда просишь у Claude zh-TW, говори обе части: «тайваньское словоупотребление, традиционные иероглифы». «Только традиционные» даст конвертацию символов.
Арабский и иврит читают справа налево. На стороне Rails нужен <html dir="rtl"> и варианты rtl: в Tailwind. Но и в самом переводе есть ловушки:
unicode-bidi: isolate, иначе код «засосёт» в RTL-поток، вместо ,, ؟ вместо ?. Claude по умолчанию ставит английские знаки; надо явно прописать2026) внутри абзаца, идущего справа налево. Браузеры с этим справляются, но Claude в сыром тексте часто путаетРазговорные обороты оригинала («одним махом», «наступил на грабли», «улетел в молоко») Claude переводит в японский/корейский по умолчанию формальными письменными формами (「一気に実装」「落とし穴」「失敗」) — смысл совпадает, тон испаряется.
Лечение: прописать в prompt — «сохраняй прямой, слегка самоироничный, неформальный тон тех-блога; не академизируй». Даже так некоторые языки (немецкий, русский) сядут чуть «формальнее» источника — сами языки имеют bias к письменному регистру.
Строки в коде делятся на две корзины — UI-текст (переводим) и плейсхолдеры/имена переменных (нет):
t("pricing.page_title") # не переводим (i18n key)
"user_id" # не переводим (имя переменной)
"Monthly subscription" # показывается в тексте как пример → не переводим
Для всего, что соседствует с кодом, «не переводим» — более безопасное дефолт-решение. То, что действительно надо переводить, — это файлы i18n locale (config/locales/xx.yml), и это отдельная задача.
/publish-article шлёт POST черновика на how2claude.com/api/articles:
{
"category_slug": "use-cases",
"series_slug": "writing",
"free": true,
"thread": true,
"title": { "zh": "...", "en": "...", "ja": "...", ... },
"summary": { "zh": "...", "en": "...", ... },
"content": { "zh": "<md>", "en": "<md>", ... },
"tweets": { "en": ["...", "..."], "zh": [...], ... }
}
Один запрос ~300KB (19 языков × ~15KB). Сервер раскладывает в таблицы БД:
articles, title / summary / content — jsonb по ключу localex_queue_tweets, по locale + аккаунту, отправляется в очередь расписанияТвиты уходят только на locale с подключённым X-аккаунтом (сейчас en/zh/ja/ko/ar/id — 6). Языки без аккаунта шлют []. Проверка аккаунтов:
Account.all.each { |a| puts "#{a.locale}: #{a.name}" }
# en: @how2claude
# zh: @howtoclaude
# ja: @how2claude_ja
# ko: @how2claude_ko
# ar: @how2claude_ar
# id: @how2claude_id
Дать Claude перевести одну статью на 19 языков — полный чек-лист:
dir="rtl" + варианты rtl: Tailwind на стороне Rails. Смешанная пунктуация и изоляция блоков кода — отдельная работа.Реальное узкое горлышко — не качество перевода — модели класса Claude 4 переводят на японский/корейский/арабский/русский почти на уровне носителя. Узкое горлышко — готов ли ты поставить одну статью перед читателями на 19 языках одновременно. Технически это 5 минут. С точки зрения контента — готовность обслужить в 200 раз большую аудиторию одновременно.