2016-04-27 7 views
2

Функция json_encode требует действительной строки UTF-8. У меня есть строка, которая может быть в другой кодировке. Мне нужно игнорировать или заменять все недопустимые символы, чтобы иметь возможность конвертировать в JSON.Sanitize UTF-8 в PHP

  1. Это должно быть нечто очень простое и надежное.
  2. Ошибка в модуле для ручной проверки, поэтому mojibake в порядке.
  3. Код, ответственный за исправление кодировки, находится в другом модуле. (Он был сломан, подумал.) Я не хочу дублировать ответственность.

Шестнадцатиричный примера недостоверной строки: 496e76616c6964206d61726b2096

Мое текущее решение:

$raw_str = hex2bin('496e76616c6964206d61726b2096'); 
$sane_str = @\iconv('UTF-8', 'UTF-8//IGNORE', $raw_str); 

Три проблемы с моим кодом:

  1. iconv выглядит немного слишком тяжелым.
  2. Многим программистам не нравится @.
  3. iconv может игнорировать слишком много: целая строка.

Любая идея?

Существует аналогичный вопрос, но меня не интересует конверсия. Ensuring valid utf-8 in PHP

+0

Если вы не заботитесь о преобразовании ... что вы пытаетесь сделать тогда? –

+0

Мне нужна действительная строка UTF-8 для json_encode. Действительный моджибак в порядке. Это все. – Michas

+0

Честно говоря, ваше решение является самым чистым, которого я вижу. Если вы не хотите использовать '@', вы можете запустить строку с помощью проверки кодировки, что является неприятным. –

ответ

1

Я думаю, что это лучшее решение.

$raw_str = hex2bin('496e76616c6964206d61726b2096'); 
$sane_str = mb_convert_encoding($raw_str, 'UTF-8', 'UTF-8'); 
3

Вы должны изучить mb_convert_encoding. Он способен конвертировать текст из любой кодировки в другую. Я должен был использовать его для аналогичного проекта: http://php.net/manual/en/function.mb-convert-encoding.php

+2

Комментарий больше, чем ответ! Используйте комментарии, когда вы делаете комментарии _Не мой нисходящий путь кстати_ – RiggsFolly

+2

Пожалуйста, не используйте ответы, чтобы задать вопросы о разъяснении. –

+0

Прошу прощения, все еще изучая систему. Хотя я думаю, что это функция, которую он ищет. – raphael75

1

json_encode expects UTF-8 encoded string. Проверка кодирования с использованием функции на основе W3C рекомендуется регулярное выражение ответа в Ensuring valid utf-8 in PHP

function encodeUtf8($string){ 
if (preg_match('%^(?: 
     [\x09\x0A\x0D\x20-\x7E]   # ASCII 
    | [\xC2-\xDF][\x80-\xBF]    # non-overlong 2-byte 
    | \xE0[\xA0-\xBF][\x80-\xBF]   # excluding overlongs 
    | [\xE1-\xEC\xEE\xEF][\x80-\xBF]{2} # straight 3-byte 
    | \xED[\x80-\x9F][\x80-\xBF]   # excluding surrogates 
    | \xF0[\x90-\xBF][\x80-\xBF]{2}  # planes 1-3 
    | [\xF1-\xF3][\x80-\xBF]{3}   # planes 4-15 
    | \xF4[\x80-\x8F][\x80-\xBF]{2}  # plane 16 
)*$%xs', $string)) 
    return $string; 
else 
    return iconv('CP1252', 'UTF-8', $string); 
} 

Тогда вы могли бы использовать:

$sane_str = encodeUtf8($raw_str); 
1

Вы можете использовать mb_detect_encoding, чтобы обнаружить, если это не UTF-8, а затем использовать mb_convert_encoding чтобы преобразовать в текст в UTF-8

<?php 
/** 
* Convert json blob to UTF-8 
* @param $string String to be decoded 
* @return bool|string 
*/ 
function convert_json($string) 
{ 
    if (ctype_print($string)) { // binary 
     return false; 
    } 
    $from = mb_detect_encoding($string, ['auto']); 
    $to = 'UTF-8'; 
    if ($from !== $to) { 
     $string = mb_convert_encoding($string, $to, $from); 
    } 
    return $string; 
}