Problem
I’ve got a basic php structure with three nested arrays.
I don’t utilize any specific objects, and I create the arrays myself using two nested loops.
Here’s an example of the array’s var dump that I want to convert to Json.
array (size=2)
'tram B' =>
array (size=2)
0 =>
array (size=3)
'name' => string 'Ile Verte' (length=9)
'distance' => int 298
'stationID' => int 762
1 =>
array (size=3)
'name' => string 'La Tronche Hôpital' (length=18)
'distance' => int 425
'stationID' => int 771
16 =>
array (size=4)
0 =>
array (size=3)
'name' => string 'Bastille' (length=8)
'distance' => int 531
'stationID' => int 397
1 =>
array (size=3)
'name' => string 'Xavier Jouvin' (length=13)
'distance' => int 589
'stationID' => int 438
I have a similar structure in another script, and json encode works perfectly. So I’m not sure why json encode isn’t working here.
There appears to be an issue with the encoding. The json encode function works when mb detect encoding returns ASCII, but not when it returns UTF8.
Edit2: JSON ERROR UTF8 is returned by json last error(), which means: Malformed UTF-8 characters, potentially encoded wrongly.
Asked by Matthieu Riegler
Solution #1
After two hours of digging (cf Edits)
I discovered the following:
Here’s a recursive function that will cause all the strings in an array to be converted to UTF-8:
function utf8ize($d) {
if (is_array($d)) {
foreach ($d as $k => $v) {
$d[$k] = utf8ize($v);
}
} else if (is_string ($d)) {
return utf8_encode($d);
}
return $d;
}
Simply put it like this:
echo json_encode(utf8ize($data));
Note: According to the documentation, utf8 encode() converts ISO-8859-1 strings to UTF-8, so if you’re unsure about the input encoding, iconv() or mb convert encoding() may be better options.
Answered by Matthieu Riegler
Solution #2
Matthieu Riegler gave a great approach, but I had to make a few changes to make it work with objects:
function utf8ize($d) {
if (is_array($d))
foreach ($d as $k => $v)
$d[$k] = utf8ize($v);
else if(is_object($d))
foreach ($d as $k => $v)
$d->$k = utf8ize($v);
else
return utf8_encode($d);
return $d;
}
Finally, json last error() can be useful for troubleshooting the json encode() and json encode() routines.
Answered by Adam Bubela
Solution #3
Setting charset=utf8 in my PDO connection solved this problem for me.
$dbo = new PDO('mysql:host=localhost;dbname=yourdb;charset=utf8', $username, $password);
Answered by fayd
Solution #4
Adam Bubela also provided an excellent solution that assisted me in resolving my issue, and here is the simplified function:
function utf8ize($d)
{
if (is_array($d) || is_object($d))
foreach ($d as &$v) $v = utf8ize($v);
else
return utf8_encode($d);
return $d;
}
Answered by Alex
Solution #5
On PHP 5.6, I’m having the same issue. On Windows 7, I run Open Server with Nginx. UTF-8 is used for all charsets. According to the official paperwork, flags are, in theory,
should be able to resolve this. Regrettably, this is not the case in my instance. I do not know, why. All snippets above do not solve my problem, thus I have found my own implementation. I believe it could help someone. At least, Russian letters pass the test.
function utf8ize($d) {
if (is_array($d) || is_object($d)) {
foreach ($d as &$v) $v = utf8ize($v);
} else {
$enc = mb_detect_encoding($d);
$value = iconv($enc, 'UTF-8', $d);
return $value;
}
return $d;
}
Answered by Vsevolod Azovsky
Post is based on https://stackoverflow.com/questions/19361282/why-would-json-encode-return-an-empty-string