32

I have an array item with a French accent ([WIPDescription] => Recette Soupe à lOignon Sans Boeuf US). The data is being properly pulled from the database (mysql).

However, when I try to encode this as json using the php built in json_encode it produces a null json value (OS X server: php 5.3.4, json 1.2.1 enabled).

In a Linux server, the description is cut off after the first accent character.

I tried all the json_encode options with no success. Any suggestions?

Thank you.

Natkeeran
  • 1,719
  • 6
  • 29
  • 52

7 Answers7

61

I found this to be the easiest way to deal with it

echo json_encode($array, JSON_PRETTY_PRINT | JSON_UNESCAPED_UNICODE | JSON_UNESCAPED_SLASHES);

JSON_PRETTY_PRINT - makes is readable
JSON_UNESCAPED_UNICODE - encodes characters correctly
JSON_UNESCAPED_SLASHES - gets rid of escape slash '\'
also notice that these option are separated by a pipe '|'

Pete
  • 611
  • 1
  • 5
  • 3
18

json_encode only wants utf-8. Depending on your character set, you can use iconv or utf8_encode before calling json_encode on your variable. Probably with array_walk_recursive.

As requested, an unfinished way to alter an array, with the assumptions that (1) it doesn't contain objects, and (2) the array keys are in ascii / lower bounds, so can be left as is:

$current_charset = 'ISO-8859-15';//or what it is now
array_walk_recursive($array,function(&$value) use ($current_charset){
     $value = iconv('UTF-8//TRANSLIT',$current_charset,$value);

});
NDM
  • 6,731
  • 3
  • 39
  • 52
Wrikken
  • 69,272
  • 8
  • 97
  • 136
  • array_walk_recursive requires a user-defined function. Would you suggest he make one which literally calls utf8_encode on each value? If so how would that affect the actual array values - would they be returned or passed by reference? This sounds like a great idea I just can't put it together in my head. – Maverick Aug 03 '11 at 15:46
  • 1
    @Matt Anderson: OK, just this once... I'll edit in an example that doesn't work on objects, but will work on arrays, and assumes the keys are ascii (=valid in ascii/ISO-8859-*/utf-8). – Wrikken Aug 03 '11 at 15:49
  • The database collation and character set is set as utf8_unicode_ci. How do I determine the character set of the mysql returned array? – Natkeeran Aug 03 '11 at 16:11
  • 3
    Thank you. When I used mysql_query("SET NAMES 'utf8'", $Connection); it works fine. (I do realize that I have to use the mysql_set_character_set() function to properly do this.) – Natkeeran Aug 03 '11 at 16:18
  • @Natkeeran: indeed, would work too, and I always use the query-variant (especially in PDO), I see no reason why `mysql_set_charset` would be better. Granted, the manual does state it, but I have yet to find a reason why. – Wrikken Aug 03 '11 at 16:23
  • @Wrikken Hi i have username coming from database if simple echo it everything is fine it prints `诶ó` but after putting it in array and json_encode it becomes `\u8bf6\u00f3`. I'm really stuck in it can you please help? i have tried iconv it makes the username empty. – Muhammad Babar Aug 17 '14 at 07:18
  • @MuhammadBabar: Isn't that just the representation in unicode in json? I'm not necessarily seeing a problem here. – Wrikken Aug 17 '14 at 11:01
  • so you mean the unicode is automatically converted by html? also what about if i'm accessing the data via a webservice in mobile client? is it still OK? @Wrikken – Muhammad Babar Aug 17 '14 at 12:48
12

Another solution would be to use htmlentities or utf8_encode before using json_encode to pass the encoded char

like this:

   $array = array('myvalue' => utf8_encode('ééàà'));
   return json_encode($array);

Or using htmlentities :

   $array = array('myvalue' => htmlentities('ééàà'));
   return json_encode($array);
sdespont
  • 13,915
  • 9
  • 56
  • 97
  • And when in the browser how to decode back to utf8? –  May 24 '15 at 02:47
  • @Inanikian Using PHP `header('Content-Type: text/html; charset=utf-8');` and HTML `` – sdespont May 24 '15 at 06:44
  • I tried `header('Content-Type:application/json; charset=utf-8')` but still have the code u/... So I decided to remove the french word `à`... –  May 24 '15 at 10:55
  • This solved my problem with json_encoding a string with ó in it. Thank you! – DiMono Aug 16 '21 at 16:06
6
<? 

$sql=mysql_query("SELECT * FROM TABLE...");

while($row=mysql_fetch_array($sql))
{
    $output[]=array_map("utf8_encode", $row);
}
print(json_encode($output));
mysql_close();

?>
Mike Bryant
  • 2,455
  • 9
  • 39
  • 60
3

If you deal with diacritics you can also add JSON_PARTIAL_OUTPUT_ON_ERROR and it will remove only the problems and leave the rest intact. I used utf_encode before I found this but it was messing up diacritics.

echo json_encode($data, JSON_PRETTY_PRINT | JSON_UNESCAPED_UNICODE | JSON_UNESCAPED_SLASHES | JSON_PARTIAL_OUTPUT_ON_ERROR);
mihaidp
  • 310
  • 2
  • 11
1
$json = utf8_encode($string);

$json = json_decode($json);
Josua Marcel C
  • 3,122
  • 6
  • 45
  • 87
1

Per the PHP docs

This function only works with UTF-8 encoded data.

AlienWebguy
  • 76,997
  • 17
  • 122
  • 145