Intereting Posts
PHP создает новый сеанс с каждой перезагрузкой GWT с -noserver Переназначение массива освобождает память, используемую им? Как объединить несколько изображений и текст в одно изображение? Доступ запрещен для пользователя 'homestead' @ 'localhost' (с использованием пароля: YES) множественные приложения codeigniter с поддоменами wild card, mod_rewrite переназначение поддоменов в .php Асинхронный ответ PHP Curl Уничтожить сеанс PHP при закрытии Сохранение вывода openssl_random_pseudo_bytes в Postgres с использованием php? Я получаю сообщение об ошибке: неверная последовательность байтов для кодирования "UTF8" Генератор документации PHPDoc в или из Eclipse? Запрос MySQL с несколькими операциями «OR» PHP: проверьте, загружен ли файл напрямую, а не включен? php var_dump ($ object) или print_r ($ object) в файл журнала Я не могу заставить strpos работать с новой строкой Эффективная перезагрузка данных / передача данных с сервера на клиент

Проблемы с PHP / Gettext

Я помню, как несколько месяцев назад тестировал несколько тестов с помощью gettext, и следующий код работал отлично:

putenv('LANG=l33t'); putenv('LANGUAGE=l33t'); putenv('LC_MESSAGES=l33t'); if (defined('LC_MESSAGES')) // available if PHP was compiled with libintl { setlocale(LC_MESSAGES, 'l33t'); } else { setlocale(LC_ALL, 'l33t'); } bindtextdomain('default', './locale'); // ./locale/l33t/LC_MESSAGES/default.mo bind_textdomain_codeset('default', 'UTF-8'); textdomain('default'); echo _('Hello World!'); // h3110 w0r1d! 

Это отлично работало (под Windows XP и CentOS, если я правильно помню), что было хорошо, потому что я мог использовать произвольные «локали», не беспокоясь о том, были ли они установлены в системе или нет. Однако, похоже, это больше не работает, мне интересно, почему …


Red Hat + PHP 5.2.11:

Я могу переключаться между различными локалями, и переводы отображают соответствие, пока вызов setlocale() не возвращает false (если локаль доступна / установлена ​​в системе).

Это не идеально (было бы здорово, если бы я мог просто указать gettext в любой произвольный каталог переводов без проверки на наличие локали), но это приемлемо. В дальнейшем я проведу еще несколько тестов.

Windows 7 + PHP 5.3.1 (XAMPP):

setlocale() всегда возвращает false (даже при использовании LC_ALL вместо LC_MESSAGES ), если я не использую какой-либо допустимый локаль Windows, такой как eng , deu или ptg – в этом случае локаль кажется правильно установленным, но переводы все еще не отображаются , Я не могу проверить прямо сейчас, потому что у меня открыто несколько вкладок, но я думаю, что самый первый вызов этого скрипта дает правильный перевод (перезапуск Apache не будет делать трюк).

Я не уверен, связано ли это с ошибкой PHP # 49349 . Я проверю это на пару часов.


Есть ли способ использовать расширение gettext (а не чистые PHP-реализации, такие как php-gettext или Zend Translate Adapter ) надежно в разных операционных системах (возможно, с пользовательскими локалями, такими как l33t )?

Кроме того, абсолютно необходимо использовать setlocale(LC_ALL, ...) ? Я бы предпочел оставить настройки TIME , NUMERIC и MONETARY (специально) неаудированными (по умолчанию для языкового стандарта POSIX ).


У меня была идея … Можно ли вызвать setlocale() с очень распространенной локалью (например, C , POSIX или en_US ) и указать язык через домен? Что-то вроде этого:

 /lang/C/LC_MESSAGES/domain.pt.mo /lang/C/LC_MESSAGES/domain.de.mo /lang/C/LC_MESSAGES/domain.en.mo /lang/C/LC_MESSAGES/domain2.pt.mo /lang/C/LC_MESSAGES/domain2.de.mo /lang/C/LC_MESSAGES/domain2.en.mo 

Будет ли эта работа над * nix и Windows платами без проблем?

    Gettext не слишком практичен для webapps.

    • Например, он не соблюдает / не использует предпочтения стиля Accept-Language сам по себе.
    • Как правило, некоторые проблемы кэширования возникают на общих веб-хостах (mod_php SAPI).

    Поэтому я иногда предпочитаю, чтобы PHP-модуль не существовал, а удобная функция имени функции _() была доступна для пользовательских реализаций.
    (Имел мой собственный gettext.php , который работал более надежно).

    Ваши варианты:

    1. Anway, согласно нескольким сообщениям об ошибках, порт Windows gettext имел некоторые недостатки с UTF-8. Возможно, ваша версия снова затронута. Поэтому попробуйте bind_textdomain_codeset('default', 'ISO-8859-1'); для начинающих. Кроме того, он предпочитает переменные среды в Windows IIRC, поэтому putenv("LC_ALL", "fr_FR"); может работать лучше, чем setlocale() . Особенно эффективен, если вы позже (gettext.dll).

      Также дайте ему шанс включить в него кодировку LANG=en_GB.ISO-8859-1 . (Так как ваш исходный текст по-английски в любом случае, забота о кодировке здесь не очень похожа, но, вероятно, распространенный случай, когда gettext срабатывает над собой.) О, и иногда это UTF8 не UTF-8; также попробуйте ASCII.

    2. Альтернативно обходить gettext. Идея вашего домена близка, но я бы просто использовал предопределенный ./locale/ subdir для языков:

       ./lang/en/locale/C/LC_MESSAGES/domain.mo 

      Затем просто вызовите bindtextdomain("default", "./lang/{$APP_LANG}/locale") не предоставляя gettext-комнате для толкования. Он всегда будет искать / C /, но правильный каталог локали уже был введен. Но попробуйте установить символическую ссылку из $ LANG в / C /.

    3. Укусить в гну. Откажитесь от gettext. «PhpWiki» имел специальный скрипт преобразования awk. Он преобразует файлы .po в скрипты массива .php (да, очень oldschool), и вместо этого использует вместо этого функцию __ (). Закрыть. И более надежный.

    Этот код не будет работать отлично в каждой системе, потому что каждый репозиторий языковых систем + php-версия отличается, в частности.

    Если вы хотите согласованности, вам нужно использовать что-то вроде Zend_Translate, которое, если вы устанавливаете Zend в каждой системе (одна и та же версия), все они будут соответствовать друг другу, потому что они используют одни и те же данные локализации, имена локалей и кодовые базы.

    Есть множество ошибок с setlocale , это просто ненадежно. См. Комментарии @ http://php.net/manual/en/function.setlocale.php