【问题标题】:Trouble with posting JSON data (with node request) to Express server for saving into MongoDB将 JSON 数据(带有节点请求)发布到 Express 服务器以保存到 MongoDB 时出现问题
【发布时间】:2016-11-06 19:48:43
【问题描述】:

我使用 MongoDB 作为我的节点/Express 应用程序的后端数据库。总结一下我面临的问题,我不知道如何在我的 Express 应用程序中设置 body-parser 配置,因为服务器端应用程序没有收到客户端应用程序(也是 node.js 应用程序)发布的完整 JSON )。在大多数情况下,客户端将请求正文中的 JSON 发送到 RESTful 端点。例外情况是需要上传文件的单一情况,因为这是一个多部分正文,所以我使用requestform-data 来构建这种类型的请求,并在服务器端使用multer 来处理多部分请求,因为 body-parser 不处理此类请求。

在服务器端(Express),我对 Express 应用进行了以下配置:

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

在节点客户端上,我使用以下代码构建 JSON 样式的 JavaScript 对象并将其发布到 RESTful 端点:

我在客户端编写请求时遇到困难,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;
  }
});

请注意,我通过将内容类型明确指定为 application/JSON 以及使用 JSON.stringify 将 JavaScript 对象转换为 JSON 字符串来尝试了上述代码的多个版本。 MongoDB 集合 (class) 存储以下类型的文档,其中包含 外键 到另外两个集合(subjectstudent):

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

在服务器日志中,我看到以下错误:

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)

这很奇怪,因为子文档的 scores 数组是空的 (scores: []),而在客户端,我发送了一个非空数组,其中包含一些学生的表演元素.

我是否违反了将 JSON 发布到 Express 应用程序的正确方法?我该如何解决这个问题?

编辑:2016 年 7 月 5 日 我将正文解析器中间件配置改为使用extended: true

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

node.js 仍然使用node-request 模块来编写和发送 POST 请求,使用以下代码:

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

现在可以了,但让我困惑的是,由于内容类型是 application/json,bodyParser.urlencoded({ extended: true })(或 false)有什么关系?

【问题讨论】:

  • 在节点后端接收到的 json 是否按原样(整个文档)?
  • @cs04iz1 是的,它是整个文档,看起来是字符串化的。

标签: json node.js mongodb express node-request


【解决方案1】:

问题在于您的第一个请求中的 form: JSON.stringify(class)form 采用 url 编码形式输入,字符串化 json 不起作用。检查内容类型标头(application/x-www-form-urlencoded)

json: class 在您的第二个 sn-p 中起作用,因为它可以处理 json 数据并正确设置正确的内容类型标头。

【讨论】:

    【解决方案2】:

    在发送之前尝试 .toJSON() 方法而不是类。

    【讨论】:

    • 你的意思是不执行JSON.stringify(class)?
    • 是的,试试 class.toJSON()
    • 我试过了,但出现错误...Underlying error: class.toJSON is not a function
    猜你喜欢
    • 2021-09-12
    • 2019-01-31
    • 2016-01-11
    • 1970-01-01
    • 2014-10-17
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多