@krekerov
Fullstack ninja

Почему slim framework неправильно отдает кириллицу?

Разрабатываю бекенд на slim framework.
Данные отдаются в json вида
{name:"\u0414\u0436\u0438\u0414\u0438\u0421\u0438 \u0421\u0435\u0440\u0432\u0438\u0441\u0435\u0437"}

Хотелось бы чтобы данные передавались нормально.

1) Вот пример приложения
$app = new \Slim\Slim();
//Company handle
$app->contentType('text/html; charset=utf-8');


2) в соединении с базой тоже указана кодировка
function getConnection() {
    $dbhost="";
    $dbuser="";
    $dbpass="";
    $dbname="crm";
    $dbh = new PDO("mysql:host=$dbhost;dbname=$dbname;charset=utf8", $dbuser, $dbpass);
    $dbh->exec("set names utf8");
    $dbh->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
    return $dbh;
}

3) Все файлы сохранены в UTF8
4) Данные в базе хранятся тоже в utf8

Не пойму где затык. так и должны данные передаваться?
Буду признателен за помощь
  • Вопрос задан
  • 3738 просмотров
Решения вопроса 4
VasiliyIsaichkin
@VasiliyIsaichkin
Web front/back-end (JS-full stack) app developer
Дык, так это в PHP json_encode так работает, это же юникод последовательности.
Костыль: если у вас новый PHP (начиная с PHP 5.4.0.) найдите в фреймворке где используется json_encode и используйте json_encode($data, JSON_UNESCAPED_UNICODE);
Если PHP старый то можно использовать свой кодер:
public function to_json($data) {
        if ($data === null) {
            $data = [];
        }
        $isArray = true;
        $keys = array_keys($data);
        $prevKey = -1;
        foreach ($keys as $key)
            if (!is_numeric($key) || $prevKey + 1 != $key) {
                $isArray = false;
                break;
            } else
                $prevKey++;
        unset($keys);
        $items = array();
        foreach ($data as $key => $value) {
            $item = (!$isArray ? "\"$key\":" : '');
            if (is_array($value))
                $item .= $this->to_json($value);
            elseif (is_null($value))
                $item .= 'null';
            elseif (is_bool($value))
                $item .= $value ? 'true' : 'false';
            elseif (is_string($value))
                $item .= '"' . preg_replace('%([\\x00-\\x1f\\x22\\x5c])%e', 'sprintf("\\\\u%04X", ord("$1"))', $value) . '"';
            elseif (is_numeric($value))
                $item .= $value;
            else
                throw new Exception('Wrong argument.');
            $items[] = $item;
        }
        return ($isArray ? '[' : '{') . implode(',', $items) . ($isArray ? ']' : '}');
    }
Ответ написан
@krekerov Автор вопроса
Fullstack ninja
Причем данне в массиве приходят нормально.
после функции json_encode() кириллица становится такой
Ответ написан
Комментировать
avalak
@avalak
Используйте JSON_UNESCAPED_UNICODE. пример
Ответ написан
Комментировать
@krekerov Автор вопроса
Fullstack ninja
JSON_UNESCAPED_UNICODE было бы решением, но wamp не заработал с php 5.4
Поэтому для старых версий вот такая функция
function fix_json($str) {
    return preg_replace_callback(
    '/\\\\u([0-9a-f]{4})/i',
    function ($matches) {
        $sym = mb_convert_encoding(
                pack('H*', $matches[1]), 
                'UTF-8', 
                'UTF-16'
                );
        return $sym;
    },
    $str
    );
}
Ответ написан
Пригласить эксперта
Ваш ответ на вопрос

Войдите, чтобы написать ответ

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