将JSON数据存储从Node.js到MongoDB

Storing JSON data from Node.js to MongoDB

本文关键字:js MongoDB Node JSON 数据 存储      更新时间:2023-09-26

我正在通过他们的API从Wundground提取JSON格式的天气数据,没有问题。我正在尝试将该数据存储在MongoDB中以供以后使用。我实际上获得了数据,并能够将其写入Mongo中的集合。但是,当我执行db.collection.find()时,看起来每个单独的字符都是单独保存的,而不是JSON格式。以下是获取数据并应保存到 Mongo 的代码片段:

// Define the Wunderground method.
var method = "/api/" + apiKey + "/conditions/q/" + state + "/" + city + ".json";
// Define the HTTP post properties.
var options = {
  host: 'api.wunderground.com',
  path: method,
  method: 'GET',
  port: 80
};
// Create the HTTP POST.
var request = http.request(options, function (response) {
  var str = '';
  // Create the listener for data being returned.
  response.on('data', function (chunk) {
    str += chunk;

    // Create the listener for the end of the POST.
    response.on('end', function (){
      db.collection('weathercollection').save(str, function(err, records) {
        if (err) throw err;
        console.log("record added");
      });
    });

JSON格式的天气数据的一小部分摘录:

{ "current_observation": {
    "image": {
    "url": "http://icons-ak.com/graphics/logo.png",
    "title": "Weather Underground"
    },
    "display_location": {
    "full":"My City, State",
    "city":"My City",

在保存到 Mongo 之前,我不应该解析数据,对吗?那么我错过了什么。正如我所说,如果我将所有天气数据完美地输出到控制台,我似乎只是在 Node.JS 和 MongoDB 之间做错了什么。

谢谢。

更新***

我确实尝试以这种方式解析"str"

// Create the listener for data being returned.
response.on('data', function (chunk) {
str += chunk;
var jsonResult = JSON.parse(str);
// Create the listener for the end of the POST.
response.on('end', function (){
  db.collection('weathercollection').save(jsonResult, function(err, records) {
    if (err) throw err;
    console.log("record added");`

这似乎也不起作用。我会再看一遍。

是的,你需要给你的send函数一个JavaScript对象(参见MongoDB原生驱动程序文档,看起来你正在使用),但你给它发送一个字符串(这就是为什么你可以在每个data事件上连接它)。您必须使用 JSON.parse(str) 将字符串转换为完整对象。

如果要确定要处理的数据类型,请打印 typeof strtypeof JSON.parse(str) 的结果。

编辑:您的代码中有第二个问题。response对象实际上是一个流,这意味着它在接收数据时会发出数据。这也意味着您可以多次接收data事件。这就是为什么您需要:

  1. 创建空字符串
  2. 在每个 data 事件上,将刚刚收到的区块连接到字符串
  3. 仅在您确定不会再收到任何数据时尝试在结束时解析它。

在您提供的更新代码段中,您尝试解析第一个数据事件上的字符串,但这可能是不完整的字符串。

这是实现此目的的正确方法:

var str = '';
response.on('data', function(chunk) {
  str += chunk;
});
response.on('end', function() {
  var myObject = JSON.parse(str);
  // Send the Mongo query here
});

与此问题相关的是,您还注册了 end 事件的侦听器,这很好,但是您在每个data事件上都添加了一个新的侦听器!这意味着如果您收到 5 个数据事件,您将调用将对象添加到 MongoDB 的函数的 5 倍......在上面的代码段中,请注意,我已将response.on('end', function() {…})移到了response.on('data')回调的外部。

var MongoClient = require('mongodb').MongoClient, format = require('util').format;
MongoClient.connect('mongodb://127.0.0.1:27017/test', function(err,db) {
    if (err) throw err;
    console.log("Connected to Database");
    var document = {name:"David", title:"About MongoDB"};
    // insert record
    db.collection('test').insert(document, function(err, records) {
        if (err) throw err;
        console.log("Record added as " + records[0]._id);
    });
});

参考资料:http://code.runnable.com/UW3ef2Tkq498AABE/insert-a-record-in-mongodb-using-mongodb-native-for-node-js