Kuzma's PHP LookHome page: http://kuzma.russofile.ru |
|
Многоязычные приложения с использованием PHP и GetTextОригинал: http://zez.org/article/articleview/42/ (Luis Argerich) Перевод: Феськов Кузьма (http://www.russofile.ru/kuzma/)
Если вы WEB-разработчик, который создает как небольшие ресурсы, так и большие порталы с сотнями страниц, то в один прекрасный момент вы можете столкнуться с необходимостью перевода вашего проекта на другой язык или обеспечить поддержку нескольких языков в рамках одного проекта. Перевод подразумевает под собой только перевод строк в коде. Вы можете подойти к этому с умом, а можете просто просматривать весь код и переводить в нем все строки. Последний метод достаточно болезнен и порождает много ошибок, к тому же, такой код – это всего лишь заплатка, а не код для многократного использования. Интернационализация помогает построить стратегию производства сайтов так, чтобы вы всегда легко могли перевести ваши файлы на другой язык. Именно описание такого подхода – цель этой статьи. Добро пожаловать в GNUGNU имеет в своем арсенале очень хороший набор инструментов для производства многоязычных приложений. Этот набор называется GetText. Он был разработан для языков C и C++, но так же прекрасно подходит для других языков, типа PHP. Возможно, GetText уже установлен на вашей UNIX системе. Чтобы проверить это, наберите в командной строке getetxt и нажмите Ввод (Enter). Если указанного набора компонентов нет, возьмите его, например, здесь: ftp.gnu.org. Произведите установку. Если gettext у вас уже установлен, то мы переходим к следующей части нашей статьи. ОТ ПЕРЕВОДЧИКАЕсли вы используете в своей работе не только Unix/Linux системы, но так же и Windows, далее я опишу шаги, которые потребуется проделать для установки GetText на вашей Windows системе. Вам необходимо скачать файлы с этой страницы: http://sourceforge.net/projects/gettext. Для работы вам понадобится gettext-win32 и пакет libconv-win32. После того, как вы скачаете указанные выше файлы, проделайте следующие манипуляции:
Перезапустите WEB-сервер Apache и выполните команду phpinfo(). Если вы все сделали правильно, то PHP сообщит вам о том, что модуль GetText установлен и enabled (включен). Интернационализация PHP скриптовЧтобы использовать GetText в ваших приложениях, написанных на PHP, вы должны будете изменить все ваши скрипты, однако, это необходимо будет сделать всего один раз. Модификации не очень сложны и вы, возможно, даже захотите написать какую-нибудь утилиту, которая будет сканировать код и задавать вопрос типа "хотите изменить это?" и так далее. И так, что же вы должны сделать со своим кодом? Все очень просто, вы всего ли должны будете заменить все строки (string) на подобные:
Да, вы используете неизвестную функцию PHP "подчеркивание" (function "underscore"), которая является псевдонимом к "длинной-чтобы-писать" функции GetText (function gettext). Каждая строка, которую вы хотите перевести, должна быть переведена. Как только вы привыкните к такому способу, вы начнете видеть его преимущества. Всегда пишите ваши строки (string) обернутыми в конструкцию _("string"); (как говорилось выше, можно писать и так: gettext("string");, прим. Переводчика). Извлечение строк из кодаGetText имеет в своем арсенале утилиту xgettext, которая предназначена для извлечения всех "обернутых" строк из ваших исходных кодов. В результате своей работы она создает файл с расширение .po. Чтобы создать .po файл из своих исходников введите:
Чтобы узнать о возможностях этой утилиты подробнее, обратитесь к документации. В результате работы утилиты вы получили .po файл, который должен быть похож на этот:
Это и есть тот файл, который вы дожны отдать переводчикам. Переводчик должен будет дать значение всем msgstr для конкретного языка. Вы можете сделать в файле комментарии, чтобы дать переводчику контекст или какие-либо пояснения. Для этого используйте знак #. Например:
И так далее. Теперь вы имеете "мастер" .po файл для всех "обернутых" строк в ваших скриптах. Если вы будете использовать gettext для непереведенных строк, то в качестве результата будет выдаваться строка из msgid, что является очень хорошим свойством системы. ОТ ПЕРЕВОДЧИКАДля Windows-систем существует специализированный бесплатный редактор .po файлов, который позволяет облегчить работу переводчиков и упростить получение переведенных файлов. Для детальной информации обратитесь на сайт http://poedit.sourceforge.net/. Редактор поддерживает множество языков интерфейса, в том числе и русский язык. Для полноценной работы с .po файлами, необходимо заполнить поля в его заголовке: "Project-Id-Version: PACKAGE VERSION " - Замените PACKAGE VERSION названием своего продукта. "Last-Translator: FULL NAME " – Замените FULL NAME на имя, фамилию переводчика и его e-mail-адрес. "Language-Team: LANGUAGE " – Замените LANGUAGE на название языка, на который переводится приложение (например, Russian). "Content-Type: text/plain; charset=CHARSET " – Замените CHARSET на точное название кодировки, в которой будут переводимые строки (например, UTF-8, Windows-1251). Создание .mo файлов.mo файл – это компилированный для использования с GetText .po файл. Вы должны создать .mo файл для каждого, поддерживаемого вашей системой, языка. Делается он таким способом:
Редактор poedit при сохранении переведенного .po файла автоматически генерирует .mo файл, что создает дополнительные удобства от его использования, прим. Переводчика). Создание каталоговЛучший способ для использования gettext – это создание в корне директорий вашего продукта папки locale. Внутри этой директории необходимо создать поддиректории для всех поддерживаемых системой языков. Внутри них необходимо создать директорию LC_MESSAGES, куда, собственно, вы и положите, имеющиеся у вас к данному моменту, .mo файлы. Приведу пример дерева папок:
Чтобы найти буквенные сочетания для всех возможных языков, воспользуйтесь этой ссылкой: http://www.loc.gov/standards/iso639-2/langcodes.html (оригинальная ссылка автора статьи была перемещена на другое место. Здесь указана новая ссылка, прим. переводчика), либо документацией на GetText. Обращаю ваше внимание, что в официальной документации на GetText есть ошибки в буквенных сочетаниях (прим. переводчика). И так, вы создали дерево директорий и поместили в них необходимые файлы с языковыми ресурсами (.mo файлы). Что же необходимо сделать в ваших PHP скриптах, чтобы все это начало работать? Примеры несколько расширены и изменены, поскольку в оригинальной статье есть некоторые неточности. Эта часть статьи очень сильно отличается от оригинала (прим. переводчика). В соответствии с пожеланиями пользователя, включаем выбранный им язык приложения:
Далее, указываем текущие настройки локали:
Все сообщения вашего приложения будут выводиться в указанной здесь кодировке. Если вы, по каким-либо причинам, хотите выводить сообщения в другой кодировке, скажем в UTF-8, то в PHP есть команда, которая принудительно указывает gettext в какой кодировке вы хотите получать сообщения:
Значение переменной $domain я объясню ниже. Теперь следует указать домен (корневую папку), в котором у нас содержатся все языки проекта.
"my_site" в данном случае название нашего приложения. Замечу, что все файлы с переводом должны иметь название вида my_site.mo, иначе gettext их не увидит. Как вы могли заметить, у нас появилась та самая переменная $domain, о которой я говорил выше. Она содержит название текущего домена. Как вы понимаете, доменов может быть несколько. Это нужно, если ваше приложение состоит из нескольких независимых частей. Далее, мы выбираем текущий домен, тем самым указывая gettext откуда брать переведенные сообщения:
И так, на этом настройки gettext в вашем скрипте закончены. Приведу листинг полностью, в порядке следования действий:
Ну что ж, остается только проверить, все ли правильно мы сделали. Для этого установите нужный вам язык и запустите свое приложение. Все сообщения должны выводить на заданном вами языке. Если этого не произошло, то где-то вкралась ошибка: либо вы не перевели все сообщения, либо неправильно создали дерево каталогов с переводами, возможно, неправильно подобрали буквенное сочетание для нужного вам языка. В общем, вариантов много. Надеюсь все же, что все у вас заработало! |