简体   繁体   中英

Node request module not setting Content-Type as application/json

I am having a strange issue with my NodeJS/Koa.js app where an HTTP request I am making is returning with this error message:

{"Message":"The request entity's media type 'application/x-www-form-urlencoded' is not supported for this resource."

Now, when I make the same request using postman I get correct results back so I have deduced that something is awry in my code. I just can't seem to figure it out. Here is my code to make the request and the payload.

 // Content Type
        if(options.contentType === 'json') {
            headers['Content-Type'] = 'application/json';
        }

        // Content Length
        if(options.contentLength) {
            reqHeaders['Content-Length'] = options.contentLength
        }

        if(headers) {
            for(let key in headers) {
                if(!headers.hasOwnProperty(key)) {
                    continue;
                }

                reqHeaders[key] = headers[key];
            }
        }

        const payload = {
            headers : reqHeaders,
            url     : url,
            method  : requestType,
            timeout : 10000,
            form    : vars,
            followRedirect: true,
            maxRedirects: 10,
            body    : '' || options.body
        };

        return new Promise(function(resolve, reject) {
            request(payload, function(error, response, body) {
                if(response) {
                    if(!error && response.statusCode === 200) {
                        resolve(response, body);
                    } else {
                        if(response.statusCode === 401) {
                            console.log('token expired');
                        }
                        reject(response, body);
                    }
                }
            });
        });

Payload:

{
  "headers": {
    "Cookie": "XDEBUG_SESSION=PHPSTORM",
    "Authorization": "Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJpc3MiOiJkZWdvdWxkLWxvZ2luLmRldiIsImFjY291bnQiOiI1OTY3NmFmZmYyOWE1NWI2MTViOWFiMWEiLCJhdXRoTGV2ZWwiOjAsImlhdCI6MTUwNTg5OTQ3MX0.r-XaeTsQTjSkab9SNjrHgnh6lrgNP0uJCaDIV22A6gM",
    "Content-Type": "application/json"
  },
  "url": "http://54.***.***/api/Report/History",
  "method": "POST",
  "timeout": 10000,
  "form": {
    "AccountId": "59676afff29a55b615b9ab1a",
    "StartDate": "2017-09-19T10:11:47.0266607+00:00",
    "EndDate": "2017-09-19T10:11:47.0266607+00:00",
    "VIN": "SALLAK"
  },
  "followRedirect": true,
  "maxRedirects": 10
}

As you can see, I have the correct Content-Type headers in my headers object that is in the payload I pass to the request function but it still seeems as if it is sending as x-www-form-encoded. Can anyone see what may be going wrong here?

Thanks

The docs read:

  • form - when passed an object or a querystring, this sets body to a querystring representation of value, and adds Content-type: application/x-www-form-urlencoded header.

and

  • json - sets body to JSON representation of value and adds Content-type: application/json header.

You are using form , so it overwrites the header. Try to use json instead. It will overwrite your header anyway, but the value will be 'application/json' which should be okay.

a couple of suggestions if I may:

  • You can use Object.assign to set the headers in the object.
  • Setting json: true will take care of putting the right content-type header.
  • You shouldn't have to set the content-length manually, it's a tricky thing to do. Let request deal with that.
  • If you want to return a promise, consider using request-promise with fullResponse enabled to check for token expiration.

     if(headers) { Object.assign(reqHeaders, headers); } const payload = { headers: reqHeaders, url: url, method: requestType, timeout: 10000, json: true, followRedirect: true, maxRedirects: 10, body: options.body || {}, fullResponse: true }; return rp(payload).then(function(response) { if (response.statusCode === 401) { throw Error('Token expired'); } return response.body; }); 

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM