Adding the contentType: "application/json" make error

2.6k views Asked by At

I want to have a service that calls from an HTML file. for example like this:

// POST api/values
public ActionResult Post([FromBody]Models.FormEntry[] composit)
{
    //Some Code here ...

    return new HttpStatusCodeResult(200);
}

then I call this service from an HTML file like below:

<script>
    function onSubmit(form) {
        var data = $(form).serializeArray();
            $.ajax({
                type: "POST",
                url: "http://localhost:45407/api/values",
                data: JSON.stringify(data),
                dataType: "text",
                //contentType: "application/json",
                success: function () { alert('YES!'); },
                error: function () { alert('NO NO NO!'); }});
    }
</script>

its behave nomally but sending nothing to service, and the composit argument gives null value. when I Uncomment the contentType: "application/json" it makes error and service doesn't call. I test it by the postman (Chrome extension) and it works perfectly. the postman recommends me this code:

var settings = {
    "async": true,
    "crossDomain": true,
    "url": "http://localhost:45407/api/values",
    "method": "POST",
    "headers": {
        "content-type": "application/json",
        "cache-control": "no-cache",
        "postman-token": "e1b9721b-2925-c413-69e0-b1b21de239cb"
      },
      "processData": false,
      "data": data
    }

    $.ajax(settings).done(function (response) {
          console.log(response);
    });

I replace above code with mine, but the service call still has an unknown error. I think it is maybe a security consideration, that we not allow to sent requests from localhost, for this reson I add <httpProtocol> under the <system.webServer> tag in service web.config file like this:

<httpProtocol>
  <customHeaders>
  <add name="Access-Control-Allow-Origin" value="*" />
  <add name="Access-Control-Allow-Methods" value="POST,GET,OPTIONS,PUT,DELETE" />
  <add name="Access-Control-Allow-Headers" value="Origin, X-Requested-With, Content-Type, Accept, soapaction" />
  </customHeaders>
</httpProtocol>

for this problem, I saw this links:

So how can I call a Restful service from an HTML file and sent a JSON array in the request body, by setting a true Content Type?

2

There are 2 answers

4
sideshowbarker On

Adding the content-type: application/json request header triggers your browser to do a CORS preflight OPTIONS request.

https://developer.mozilla.org/en-US/docs/Web/HTTP/Access_control_CORS has more details.

So how can I call a Restful service from an HTML file and sent a JSON array in the request body, by setting a true Content Type?

You need to configure the server for the http://localhost:45407/api/values endpoint to send an Access-Control-Allow-Methods response header that includes Content-Type in its value.

Exactly how you do that depends on what particular server backend http://localhost:45407 is running. But regardless, it needs to be configured on that server. You can’t do it from the client side.

1
Ankit Vishwakarma On

Sending Headers to the browser is the work of a server. An ajax call is a client request. You need not to send header on it. In fact, you can return type can be 'json'. You need not serializeArray, serialize function will work

A short form of post request is as follows:

$.post('http://localhost:45407/api/values',
    $('#formId').serialize(), function(response){
         //callback body
    }, 'json');

Now on the server side , you need some changes before sending the response set the header 'application/json' if this is a cross domain request ajax call will not work. You will have to whitelist the request domain.

header('Access-Control-Allow-Origin: *');  

You can use any particular url instead of using "*". This wildcard character actually allowing all request to be valid if they are coming from outside the domain the resource exists.