Trouble with posting JSON data (with node request) to Express server for saving into MongoDB

时间秒杀一切 提交于 2019-12-02 16:38:03

问题


I use MongoDB as the back-end database for my node/Express application. To summarize the problem I am facing, I don't know how to set up the body-parser configuration in my Express app, because the server side application is not receiving the full JSON posted by the client application (also a node.js app). For the most part, the client is sending JSON in the request body to RESTful endpoints. The exception being a single case where a file needs to be uploaded and since that is a multipart body, I am using request and form-data to build that type of request and using multer on the server side to process the multipart request, since body-parser does not process such requests.

On the server-side (Express), I have the following configuration of the Express app:

let app = express();
app.use(bodyParser.json());
app.use(bodyParser.urlencoded({ extended: false }));

On the node client, I am using the following code to build up a JSON-style JavaScript object and post it to a RESTful endpoint:

I am having difficulty composing the request on the client side, with node-request:

// class is a JavaScript/JSON object within scope of this code
let req = request.post({
  //headers: { 'Content-Type': 'application/json' },
  url: 'http://localhost:3000/classes',
  //form: class
  form: JSON.stringify(class)
}, function (err, resp, body) {
  if (err) {
    throw err;
  }
});

Note that I attempted multiple versions of the above code by explicitly specifying the content type as application/JSON, as well as using JSON.stringify to convert the JavaScript object into a JSON string. The MongoDB collection (class) stores the following type of document, which contains foreign keys to two other collections (subject and student):

{
  "_id" : ObjectId("57758f15f68da08c254ebee1"),
  "name" : "Grade 5 - Section A",
  "scores" : [{
    "studentId" : ObjectId("5776bd36ffc8227405d364d2"),
    "performance": [{
      "subjectId" : ObjectId("577694ecbf6f3a781759c54a"),
      "score" : 86,
      "maximum" : 100,
      "grade" : "B+"
    }]
  }]
}

In the server logs, I see the following error:

Tue, 05 Jul 2016 04:34:46 GMT classReportApp:routes:classes class received from client: { _id: 577b38e65967097c25876764, scores: [] }
RangeError: Invalid status code: 0
    at ServerResponse.writeHead (_http_server.js:192:11)
    at ServerResponse.writeHead (C:\Development\classReportApp\node_modules\morgan\node_modules\on-headers\index.js:55:19)
    at ServerResponse._implicitHeader (_http_server.js:157:8)
    at ServerResponse.OutgoingMessage.end (_http_outgoing.js:566:10)
    at ServerResponse.send (C:\Development\classReportApp\node_modules\express\lib\response.js:205:10)
    at ServerResponse.json (C:\Development\classReportApp\node_modules\express\lib\response.js:250:15)
    at C:\Development\classReportApp\server-process\app.js:80:26
    at Layer.handle_error (C:\Development\classReportApp\node_modules\express\lib\router\layer.js:71:5)
    at trim_prefix (C:\Development\classReportApp\node_modules\express\lib\router\index.js:310:13)
    at C:\Development\classReportApp\node_modules\express\lib\router\index.js:280:7
    at Function.process_params (C:\Development\classReportApp\node_modules\express\lib\router\index.js:330:12)

which is strange because scores array of sub-documents is empty (scores: []), whereas on the client side, I am sending a non-empty array with some students' performances elements in it.

Have I violated the right way to post JSON to Express apps? How do I fix this?

Edited: 7/5/2016 I changed the body parser middle-ware configuration to use extended: true instead.

app.use(bodyParser.json());
app.use(bodyParser.urlencoded({ extended: true }));

The node.js is still using the node-request module to compose and send the POST request, using the following code:

let req = request({
  url: 'http://localhost:3000/classes',
  method: 'POST',
  json: class
}, function (err, resp, body) {
  if (err) {
    throw err;
  }
  else {
    // process response
  }
});

This works now, but what confuses me is that since the content type is application/json, how does the bodyParser.urlencoded({ extended: true }) (or false) matter?


回答1:


Issue is with form: JSON.stringify(class) in your first request. form takes url encoded form input, stringified json won't work. check content-type header (application/x-www-form-urlencoded)

json: class in your 2nd snippet works as this handles json data and sets correct content type header correctly.




回答2:


Try .toJSON() method over class before sending.



来源:https://stackoverflow.com/questions/38195552/trouble-with-posting-json-data-with-node-request-to-express-server-for-saving

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!