Writing JSON object to .json file on server

You are double-encoding. There is no need to encode in JS and PHP, just do it on one side, and just do it once.

// step 1: build data structure
var data = {
    metros: graph.getVerticies(),
    routes: graph.getEdges()
}

// step 2: convert data structure to JSON
$.ajax({
    type : "POST",
    url : "json.php",
    data : {
        json : JSON.stringify(data)
    }
});

Note that the dataType parameter denotes the expected response type, not the the type you send the data as. Post requests will be sent as application/x-www-form-urlencoded by default.

I don't think you need that parameter at all. You could trim that down to:

$.post("json.php", {json : JSON.stringify(data)});

Then (in PHP) do:

<?php
   $json = $_POST['json'];

   /* sanity check */
   if (json_decode($json) != null)
   {
     $file = fopen('new_map_data.json','w+');
     fwrite($file, $json);
     fclose($file);
   }
   else
   {
     // user has posted invalid JSON, handle the error 
   }
?>

Don't JSON.stringify. You get a double JSON encoding by doing that.

You first convert your array elements to a JSON string, then you add them to your full object, and then you encode your big object, but when encoding the elements already encoded are treated as simple strings so all the special chars are escaped. You need to have one big object and encode it just once. The encoder will take care of the children.

For the on row problem try sending a JSON data type header: Content-type: text/json I think (didn't google for it). But rendering will depend only on your browser. Also it may be possible to encode with indentation.


Probably too late to answer the question. But I encountered the same issue. I resolved it by using "JSON_PRETTY_PRINT"

Following is my code:

<?php

if(isset($_POST['object'])) {
    $json = json_encode($_POST['object'],JSON_PRETTY_PRINT);
    $fp = fopen('results.json', 'w');
    fwrite($fp, $json);
    fclose($fp);
} else {
    echo "Object Not Received";
}
?>