POST json data via ajax sends an empty array

2020-08-17 17:51发布

问题:

I'm trying to post data via ajax, this is my info:

    var jsondata =
                {"address" : [
                { "id": addid, "streetaddress": streetaddress, "city": city, "state": state,  "zipcode": zipcode, "latitude": latitude},
            ]   
            };  

    var jsontosend = JSON.stringify(jsondata, null, 2);

ajax function:

    $.ajax({
                type: "POST",
                url: "process.php",
                contentType: "application/json; charset=utf-8",
                dataType: "JSON",
                data: jsontosend,
                success: function(msg){
                   alert(msg);
                          }
             });

            return false;

            alert('Data sent');

}

on the php end, when i print_r($_POST) it just says

    array(0) {
    }

I'm alerting (jsontosend) and its showing me everything perfectly, as well as in firebug using post mothod, its showing all the params sent in a perfect clean manner.

The only way it passes any data is if I use GET method.

Any advice is greatly appreciated!

EDIT: adding POST data from firebug. this is whats being alerted from the alert function:

    {"address":[{"id":1473294,"streetaddress":"3784 Howard Ave","city":"Washington DC","state":"DC","zipcode":20895,"latitude":39.027820587}]}

this is what firebug is showing as whats being passed when using POST method:

    myData=%7B%0A++++%22address%22%3A+%5B%0A++++++++%7B%0A++++++++++++%22id%22%3A+76076%2C%0A++++++++++++%22streetaddress%22%3A+%223784+Howard+Ave%22%2C%0A++++++++++++%22city%22%3A+%22Washington+DC%22%2C%0A++++++++++++%22state%22%3A+%22DC%22%2C%0A++++++++++++%22zipcode%22%3A+20895%2C%0A++++++++++++%22latitude%22%3A+39.027820587%0A++++++++%7D%0A++++%5D%0A%7D

and this is the response for var_dump of $_POST:

    array(0) {

}

this is a var_dump of $_POST['myData']

    NULL

回答1:

I'm skeptical of the way you're using the contentType property. Try taking out contentType. The default content type is application/x-www-form-urlencoded (http://api.jquery.com/jQuery.ajax/).

Also, use something like {mydata: jsontosend} for your data property.

$.ajax({
            type: "POST",
            url: "process.php",
            //contentType: "application/json; charset=utf-8",
            dataType: "JSON",
            data: {mydata: jsontosend},
            success: function(msg){
               alert(msg);
                      }
         });


回答2:

Use

data:{myData: jsontosend}

It should send myData as a parameter in your request.



回答3:

PHP doesn't understand application/json requests (by default). See this question: How to post JSON to PHP with curl



回答4:

I found that the comment provided by dkulkarni was the best solution here. It is necessary to read directly from the input stream to get POST data of any complexity. Changing the value of $.ajax({contentType: ''}) did not work for me..

In order to troubleshoot this problem I had set up a controller method to echo back the JSON I was posting to my server. Changing the ContentType header made no difference. But after reading dkulkarni's comment I changed my server code from this:

    return $_POST;

to this:

    $data = file_get_contents('php://input');
    return json_decode($data);

It worked perfectly.



回答5:

As dkulkarni commented in his post (Jan 24 at 7:53), the only way to retrieve JSON sent with Content-Type application/json seems to be to retrieve it directly from the input stream.

I made a lot of tests with different approaches, but always when I set Content-Type to JSON, the $_POST in PHP is empty.

My problem is I need to set Content-Type to JSON, because the server (where I don't have access) expects it, otherwise it returns unsupported datatype. I suppose they are retrieving directly from input stream.

Why I have to reproduce that in own PHP file? Because I need to make a proxy for testing issues, but thats not the point of this thread.



回答6:

Try removing ' dataType: "JSON" ' from the ajax request and check.



回答7:

Taking contentType out is not a good idea. You DO want to send this data in JSON format. Key is to do what has been mentioned above, instead of trying to access the data on the receiving end (the target php file) with $data= $_POST it is critical to use $data = file_get_contents('php://input');

Here is an example of the entire round trip for a scenario with php and knockout.js:

JS (on requesting page):

function() {
   var payload = ko.toJSON({ YOUR KNOCKOUT OBJECT });
   jQuery.ajax({
            url: 'target.php',
            type: "POST",
            data: payload,
            datatype: "json",
            processData: false,
            contentType: "application/json; charset=utf-8",
            success: function (result) {
                alert(result);
            }
        });
 };

And then in target.php (the page receiving the request):

$data = file_get_contents('php://input');
$payload_jsonDecoded = json_decode($data