Elettracompany.com

Компьютерный справочник
0 просмотров
Рейтинг статьи
1 звезда2 звезды3 звезды4 звезды5 звезд
Загрузка...

Php locale ru

Локали и кодировки

Введение

При разработке веб-приложений есть три важных момента, связанных с кодировками: информация в файлах-сценариях, информация в базе данных и браузер пользователя. Если выставить хотя бы одну кодировку неверно, то, в лучшем случае, данные отобразятся неверно, в худшем, безвозвратно потеряются. Чтобы этого не произошло, а приложение работало корректно при любых настройках сервера, нужно правильно выставить кодировки.

Работа с локалями в PHP

Работа с локалями в PHP выглядит одинаково и в UNIX, и в Windows, и в любой другой платформе. Для установки значений локали служит всего одна функция setlocale() . Чтобы выставить локаль, нужно передать функции первым аргументом категорию, на которую эта локаль распространяется, последующими список возможных локалей. Результатом будет название первой подходящей локали, которая и была установлена.

Локали в Windows

Для того, чтобы узнать, какие локали доступны в Windows, нужно зайти в панель управления, «Язык и региональные стандарты».

На вкладке «Дополнительно», в разделе «Кодовые страницы таблиц преобразования» показан список всех возможных локалей для Windows, которые можно использовать в PHP.

Кодовые страницы, которые отмечены в списке, из PHP могут быть использованы по их номеру.

В общем случае, использование выглядит по следующей схеме: Язык_Регион.Номер_кодовой_страницы

Для России это может выглядеть как Russian_Russia.1251 (cp1251) или Russian_Russia.20866 (KOI8-R).

Для Украины — Ukrainian_Ukraine.1251 (cp1251).

Вместо длинных названий можно использовать сокращённые russian , american , ukrainian и так далее. При этом кодовая страница выставится с учётом региональных настроек, для России и Украины — 1251, для Америки — 1252.

Единственная кодировка, с которой у меня возникли проблемы, как ни странно, оказалась UTF-8. При попытке выставить эту кодировку, выставляются все категории локалей, кроме основной. Вывод локализованных сообщений при этом идёт в cp1251.

Пока это можно списать на внутренний механизм PHP работы со строками. С шестой версии PHP вся обработка строк должна будет вестись в UTF-8, но до тех пор надо просто знать об этом и делать поправку.

Ещё одной странностью при работе с локалями в PHP на Windows является неправильная работа с категориями локалей. Так, например, я выставляю локаль на функции времени KOI8-R, setlocale(LC_TIME, ‘Russian_Russia.20866’) , но почему-то выставляется cp1251 на все категории. Суть проблемы я так и не понял, возможно, это просто баг (проверялось на PHP 5.2.3), а возможно, что внутренний механизм Windows просто не позволяет этого делать. Хотя по мне, так это чистой воды баг.

В общем-то, на этом можно и закончить разговор о локалях на Windows. Главное, запомнить, что локали, которые портированы из UNIX, под WIndows работают только для «галочки». Шаг влево, шаг вправо и результат будет непредсказуемым. Безопасно можно использовать только cp1251 (windows-1251) и KOI8-R, и только для LC_ALL .

Локали в UNIX

Выше я описал работу с локалями в Windows, теперь можно заострить внимание на UNIX-like системах. Для простоты, я буду их называть UNIX, а подразумевать FreeBSD :). В контексте данной статьи это не особо важно.

Итак, дистрибутивы UNIX поставляются в одном виде для всех, и работа рассчитана на многопользовательский режим, поэтому о правильной настройке локали должен заботиться сам пользователь, например:

Так может выглядеть работа системной команды locale , которая выводит текущие настройки локали для пользователя. А так, обычно, выглядят настройки локали для пользователя, под которым работает PHP:

Функция ucwords() должна была сделать заглавными первые буквы всех слов. А перед этим strtolower() должна была предварительно все заглавные буквы сделать строчными. Но ничего не произошло. Так же не будет работать следующий код:

Хотя w является множеством знаков, из которых может состоять слово (алфавит, цифры и _), регулярное выражение не срабатывает. Причина как раз в том, что, работая с cp1251, мы не сказали об этом php. Чтобы исправить положение, достаточно воспользоваться функцией setlocale() и указать правильную локаль, например, так:

Здесь первый аргумент — это категория, на которую будет распространяться локаль (константа LC_*), второй — название локали. Начиная с версии 4.3.0 можно указывать несколько имён локалей в виде массива или в качестве дополнительных аргументов. После вызова функция установит первую подходящую локаль и вернёт её имя:

С помощью команды grep я отобрал локали, которые поддерживают русский язык. Любую из них можно использовать, однако следует понимать, что данные должны быть в кодировке, на которую рассчитана локаль. Если же это правило не будет соблюдено, то результат может оказаться весьма неожиданным:

Читать еще:  Ldap search php

Если учесть, что koi8-r достаточно популярная кодировка для UNIX-севреров, а windows-1251 для русскоязычных сайтов, то подобное «необычное» поведение не такая уж и редкость. Когда-то я и сам столкнулся с этой проблемой при портировании проекта на реальный хостинг.

После установки правильной локали все примеры, которые не работали выше, будут работать как нужно!

По-русски заговорит и функция strftime(), которая корректно работает с локалями, а также и всё остальное, что зависит от локали.

Кодировки в MySQL

Напомню, что возможность задавать кодировки появилась только в MySQL 4.1.11 и выше.

В отличие от php, проблемы с кодировками базы данных проявляют себя гораздо быстрее, чем проблемы с локалью. И связано это прежде всего с хранением и выборкой данных, поскольку от этого зависит информация на сайте. Я не буду подробно расписывать все тонкости, поскольку есть отдельная статья, остановлюсь на самых важных моментах.

Первое, чему необходимо научиться, смотреть текущие настройки соединения с mysql:

Критичными для пользователя являются character_set_client и character_set_results, которые отвечают за кодировку, в которой данные поступают в базу, и кодировку, в которой данные поступают из базы к пользователю. Если эти две кодировки отличаются от той, в которой работает клиент, в нашем случае php-скрипты, то неминуемо будут «странности», например, при сортировке выборки или внесении данных в базу.

Второе, что необходимо знать, как правильно сообщить mysql о кодировках. Самый простой и правильный способ, это использовать запрос set names:

После этого три переменные character_set_client, character_set_connection и character_set_results примут значение cp1251. Это будет означать — клиент работает в кодировке windows-1251 (cp1251).

Помимо этого можно устанавливать непосредственно серверные переменные:

Теперь данные поступают и извлекаются в разных кодировках.

Список доступных кодировок можно просмотреть так:

И третье, что необходимо знать, — правила создания таблиц для хранения данных в нужной кодировке. К слову, данные можно хранить в любой кодировке, а работать с ними в кодировке клиента. Однако, важно понимать, что кодировки носят национальный характер и должны соответствовать вносимым данным. Иначе будут потери. Для русского языка есть три национальных кодировки koi8r, cp866, cp1251, которые могут конвертироваться друг в друга без потерь. Также можно использовать интернациональную кодировку UTF8.

Кодировку можно выставить на базу данных, таблицу и поле таблицы. Так, например, можно создать базу данных в кодировке koi8r:

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

Следующим шагом я создам таблицу в cp1251 и одним полем в utf8:

После того, как таблица создана с нужными параметрами кодировки, mysql автоматически начинает переводить данные при внесении и выборке.

Данные хранятся в разном виде, но поступают к пользователю именно так, как надо!

Подробнее с кодировками и проблемами их использования можно ознакомиться на http://dev.mysql.com/doc/refman/5.1/en/charset.html.

Кодировка HTML-страниц

Объявить кодировку html-страницы можно двумя способами: через заголовки и мета-тег в самой странице. Мета-тег используется только в статичных страницах.

Я не буду его разбирать, это проблемы html. Во всех остальных случаях предпочтительней использовать HTTP-заголовок Content-Type.

PHP позволяет работать с HTTP-заголовками посредством функции header():

Но браузер отобразит страницу корректно только в том случае, когда php-файлы сами были созданы в кодировке cp1251. Также нужно понимать, что заголовки должны быть отправлены до любого вывода на экран.

При необходимости перекодировать страницы «на лету», достаточно воспользоваться буферизацией и iconv:

Надпись «Привет, мир!» будет выведена в юникоде, при этом браузер получит информацию о кодировке через заголовки и правильно отобразит страницу. Но важно понимать, что внутри скрипта и при соединении с базой данных надо использовать windows-1251 (cp1251), поскольку страница должна быть сформирована в одной кодировке.

Важно помнить, что функции iconv доступны не всегда, и проверка на доступность этих функций не будет лишней.

Заключение

Для безопасной разработки русскоязычных веб-проектов необходимо включать в файл с общими настройками следующие команды:

Как ни странно, но эти три строчки кода значительно повышают портируемость веб-проектов.

Читать еще:  Php subcat orchestrator employment

© 2020 Антон Прибора. При копировании материалов с сайта, пожалуйста, указывайте ссылку на источник.

setlocale

(PHP 4, PHP 5, PHP 7)

setlocale — Устанавливает настройки локали

Описание

Устанавливает настройки локали.

Информация о локали модифицируется во всем процессе, а не по каждому потоку отдельно. Если вы используете PHP на многопоточном сервере, таком как IIS, HHVM или Apache под Windows, вы можете обнаружить неожиданные изменения в настройках локали во время выполнения скриптов, никогда и не вызывавших setlocale() . Это происходит из-за того, что другие скрипты, запущенные в параллельных потоках данного процесса, в то же самое время поменяли настройки локали для всего процесса с помощью setlocale() .

Список параметров

Параметр category — это именованная константа, определяющая категорию функций, на которые будет влиять установка локали:

  • LC_ALL — все нижеперечисленное
  • LC_COLLATE — функции сравнения строк, см. strcoll()
  • LC_CTYPE — функции преобразования и классификации строк, например strtoupper()
  • LC_MONETARY — для функции localeconv()
  • LC_NUMERIC — задает символ десятичного разделения (см. также localeconv() )
  • LC_TIME — форматирование даты/времени функцией strftime()
  • LC_MESSAGES — для системных сообщений (доступна, если PHP был скомпилирован с поддержкой libintl)

Если в качестве locale передана пустая строка «» или NULL , имена локалей будут взяты из одноименных переменных окружения или переменной с именем «LANG».

Если в качестве locale передан «0», локаль изменена не будет, а будет возвращено текущее значение.

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

(Необязательные аргументы в виде строк или массивов для установки настроек локали до первой успешной попытки.)

Замечание:

На Windows setlocale(LC_ALL, ») устанавливает имена локалей из системных региональных/языковых настроек (доступных через Панель Управления).

Возвращаемые значения

Возвращает имя вновь установленной локали или FALSE , если система не поддерживает установку локали, указанная локаль не существует или передано недопустимое имя категории.

Недопустимое имя категории также вызывает предупреждение. Имена локалей и категорий описаны в » RFC 1766 и » ISO 639. Разные системы имеют различные схемы именования локалей.

Замечание:

Возвращаемое функцией setlocale() значение зависит от системы, на которой запущен PHP. Она возвращает точно то же значение, что и системная функция setlocale.

Форум PHP программистов ► PHP основы ► Кодировки

Жадный квантификатор

Профиль
Группа: Эксперт

Сообщений: 6130
Пользователь №: 4795
На форуме: 11 лет, 11 месяцев, 27 дней
Карма: 118

На выходе получаем тоже что и на входе.

— выдает ru_RU.UTF-8, что говорит о том что локаль установленна корректно.

При этом даты через strftime выводятся на нормальном русском языке.

— работает на «ура», вот только у меня уже везде используются обычные строковые функции.

На форуме нашел похожую тему, но последний вариант мне не подходит потому как в дальнейшем на сайте будет еще немецкий и польский языки.

Если кто сталкивался с подобной несправедливостью по отношению к русскому языку, буду рад узнать вариант решения данной траблы!

twin, пока единственный рабочий вариант — использование mbstring модуля:

mb_internal_encoding ( ‘UTF-8’ ); // Устанавливаем кодировку строк
setlocale ( LC_ALL , ‘ru_RU.UTF-8’ ); // Устанавливаем нужную локаль (для дат, денег, запятых и пр.)

// Юзаем вместо обычных строчных функций mb_* (модуль mbstring)
echo mb_strtoupper ( ‘Hello World!’ ). ‘
‘ ; // Для английского
echo mb_strtoupper ( ‘СоТоНа’ ). ‘
‘ ; // Для русского
echo mb_strtoupper ( ‘Beiträge’ ). ‘
‘ ; // Для немецкого
echo mb_strtoupper ( ‘Zmień wygląd’ ); // Для польского

Просто изначально использовал в движке обычные строковые функции, не думал что будет такая проблема.
Сейчас все заменил на mb_, проблем нет!

Итак в продолжении темы напишу немного про дружбу регулярок и русских букв в utf8.

Написал я форум , сделал все красиво, в юникоде Потом думаю — «какой же форум без поиска?!» и прикрутил к нему поиск (тоже красивый — с подсветкой ). Играл с ним 3 дня и 3 ночи, нарадоваться не мог, пока случайно не создал топик на русском. И одолела меня злость на эти мультибайтовые кодировки, — русские буквы отказывались подсвечиваться (точнее подсвечивались, но регистрозависимо), и начал я гром и молнии метать по всему гуглу в поисках вакцины от неверных.

Читать еще:  Main php cmd share details

Первое что мне пришло в голову, — заглянуть на родной php .net. Там я прочитал, что mb_internal_encoding(‘UTF-8’); выставляется для текстовых функций. Надо сказать, что все обычные строковые функции я перезагрузил [по совету vasa_c] с помощью строчки php _value mbstring.func_overload «7» в .htaccess-е (Что значит 7-ка, можно прочитать тут). Но как оказалось мало установить кодировку символов, нужно установить кодировку самих регулярных выражений с помощью mb_regex_encoding(‘UTF-8’);. Все бы хорошо, но вот отказывалась eregi_replace() работать регистронезависимо. И с модификаторами и без — никак. Я уже подумывал на это дело забить, но что-то меня потянуло к гуглу опять. И нарыл я инфу, что PCRE и без всяких перезагрузок работают с НЕлатиницей! Нужно всего-навсего добавить модификатор u. Тоесть регулярка получится примерно такой —

Может кому пригодится сей рассказ
Надеюсь моя эпопея с русскими буквами на этом закончится

Как использовать функции PHP Locale

Я запускаю PHP на windows vista . Итак, я пытаюсь узнать, как работают функции locale. Я начал с того, что

setlocale(LC_ALL, $locale) и localeconv()

Сначала он работал с CLDR locale IDs(я думаю. Только что начал изучать PHP локаль), как «en_US», «en_UK» и т. д., В результате чего, как показано в примерах документации PHP. Но теперь setlocale() и localeconv() работают только с $locale значениями, такими как «English_United Kingdom.1252» и «English_United States.1252» , которые, как я считаю, основаны на windows locale IDs.

Поэтому, когда я делаю:

Я получаю эти результаты:

Как заставить мои скрипты реагировать на CLDR locale IDs?

2 Ответа

setlocale() возвращает false в вашем случае. Руководство:

Возвращает новый текущий locale или FALSE, если функция locale не реализован на вашей платформе

Попробуйте использовать одно из следующих значений: «usa», «america», «Соединенные Штаты», «Соединенные Штаты» или «us»

Функции setlocale , localeconv и связанные с ними функции не работают с идентификаторами и данными Unicode CLDR locale. Вместо этого они варьируются в зависимости от операционной системы, с идентификаторами POSIX locale и данными в системах *nix и строками Microsoft locale и данными в системах Windows.

Если вы действительно хотите использовать Unicode CLDR locale идентификаторы и данные для унифицированного взаимодействия независимо от операционной системы, используйте вместо этого международное расширение . Он доступен с PHP 5.3 и представляет собой оболочку вокруг библиотеки ICU (International Components for Unicode), которая предоставляет стандартизированные данные CLDR locale.

Похожие вопросы:

Я использую PHP 5.4.18 и пытаюсь использовать объект Locale. Я попробовал следующие вызовы: $locale = locale_accept_from_http($_SERVER[‘HTTP_ACCEPT_LANGUAGE’]); $locale =.

Как получить Locale используя Php, я хочу получить часовой пояс, основанный на местоположении, есть ли вообще возможность попасть в php. Мне нужно преобразовать его в GMT и сохранить Database.Again.

Можно ли отсортировать массив PHP с параметром locale? Это и есть настройка: Я делаю интерактивный отсортированный список в PHP. По вводу пользователя, одна из нескольких категорий (столбцов) может.

Я использую Apache и php 7 в системе Ubuntu. После установки немецких локалей и запуска locale -a для проверки установленных локалей я получаю C, C.UTF-8, de_DE, de_DE@euro, de_DE.iso88591.

Я сижу на машине с en_US locale и этот кусок кода PHP setlocale(LC_ALL,’de_DE.utf8′); var_dump((string)1.234); возвращается string(5) 1.234 в то время как на машине моего коллеги, у которой есть.

Я хотел бы получить текущую систему locale сервера (скажем windows 7 os). Это делается для того, чтобы разные языковые настройки использовали разные части кода в PHP. Однако я не смог найти ни.

На данный момент я не понимаю, почему действительно важно использовать функции mbstring в PHP при работе с UTF-8? Мой locale под linux уже установлен в UTF-8, так почему же функции вроде strlen .

Может ли значение по умолчанию locale быть помещено в php.ini или .htaccess ? Эквивалент функции php setlocale(LC_MONETARY, ‘it_IT’); например

Я создаю функцию,которая должна возвращать лучший перевод в зависимости от locale пользователя. Вход представляет собой массив (из BDD) перевода одного и того же текста на многих языках, язык.

Ссылка на основную публикацию
Adblock
detector