【问题标题】:Mongoose API get nested items in array by _idMongoose API 通过 _id 获取数组中的嵌套项
【发布时间】:2014-07-18 09:27:45
【问题描述】:

我正在用 Express 和 Mongoose(前面的 Backbone)构建一个 api。我有一个 Mongoose User 模型,其中包含一个名为“orders”的数组。我需要设置一个按 ID 读取单个订单的创建方法。

当我导航到:

http://localhost:3000/test/

对于已登录的用户,我得到以下信息:

{
  "__v": 0,
  "_id": "537d09a1fe47a00000c54514",
  "kittenType": "Grumpy",
  "local": {
    "petname": "Smeagol",
    "password": "$2a$08$X4sF5UmYZ3/2cxfRzpPcq.pphYFRKcb.6xBGupdUyUMgWJlFSr/uq",
    "email": "julie@gmail.com"
  },

  "orders": [
    {
      "title": "Big Max Fountain",
      "description": "Large capacity drinking fountain",
      "quantity": "2",
      "price": 500,
      "_id": "53837e9e681808e6ea9f9ca4",
      "modified": "2014-05-28T23:49:10.232Z"
    },
    {
      "title": "Lotus Fountain",
      "description": "Tranquil pools of water",
      "quantity": "1",
      "price": 1000,
      "_id": "53867762ff514df026b608fa",
      "modified": "2014-05-28T23:55:16.263Z"
    }
  ]
}

当我导航到:

http://localhost:3000/test/orders

我发送登录用户的订单列表(这给了我订单数组:

app.get('/test/orders', function(req, res) {
  User.findOne({'_id': req.user.id }, function(err, user) {
    if (err)
      return done(err);

    if (user) {
      res.send(user.orders);

    }

  });
});

然后我如何通过 id 发送每个订单?

app.get('/test/orders/:id', function(req, res) {
  User.findOne({'_id': req.user.id }, function(err, user) {
    if (err)
      return done(err);

    if (user) {

      //send the order by id here thru the url

    }
  });
});

回复后添加:

var userSchema = mongoose.Schema({

user            : {
    type: mongoose.Schema.ObjectId,
    ref: 'User'
},
orders: [{
    title: String,  
    description: String, 
    quantity : String,
    price : Number,
    modified: { type: Date, default: Date.now }
}],
signup: [{
    name: String,
    courseDay: String,
    time: String,
    location: String,
    modified: { type: Date, default: Date.now }
}],

kittenType   : String,
profilePhoto : String,
profilePage :  String,
local            : {
    email        : String,
    password     : String,
    petname      : String,
    path         : String,

}

路线:

app.get('/test', function(req,res) {
res.send(res.locals.user);
});

app.get('/test/orders', function(req, res) {
User.findOne({'_id': req.user.id }, function(err, user) {
    if (err) 
        return done(err);

    if (user) {
        res.send(user.orders);

    }

});
});

app.post('/api/orders', isLoggedIn, function (req, res){

User.findOne({'_id': req.user.id }, function(err, user) {
    if (err)
        return done(err);

    if (user) {
        user.orders.quantity = req.body.quantity;
        user.orders.description = req.body.description;
        user.orders.title = req.body.title;
        user.orders.price = req.body.price;
        user.orders.modified = req.body.modified;


        user.update({$push: { "orders" : 
            {   title: user.orders.title,
                description: user.orders.description,
                quantity: user.orders.quantity,
                price: user.orders.price,
                modified: user.orders.modified
            }
            }},{safe:true, upsert:true},function(err){
                if(err){
                    console.log(err);
                } else{
                    console.log("Successfully added" + user.orders);
                }
        });

        console.log('located a user');
    }       
});

});

工作获取方法:

app.get('/test/orders/:id', function(req, res) {
  User.findOne({'_id': req.user.id }, function(err, user) {
    if (err)
      return done(err);
    if (user) {
      console.log(user.orders);
      var order = user.orders.filter(function(e){ return e._id == req.params.id })[0]
      console.log(order);
      res.send(order);
    }
  });
});

【问题讨论】:

    标签: node.js api express request mongoose


    【解决方案1】:

    我认为在这种情况下您不需要查找用户。足以找到条件合适的Order

    app.get('/test/orders/:id', function(req, res) {
      Order.findOne({'_id': req.params.id, 'user_id': req.user.id }, function(err, order) {
        if (err)
          return done(err);
        if (order) {
          res.send(order);
        }
      });
    });
    

    但是您应该记录req 以确保您使用正确的ids。这还取决于您未公开的路线。

    或者如果您需要找到User 型号,您可以简单地使用过滤方法。代码与第一种方法几乎相同:

    app.get('/test/orders/:id', function(req, res) {
      User.findOne({'_id': req.user.id }, function(err, user) {
        if (err)
          return done(err);
        if (user) {
          console.log(user.orders); // returns an array
          // console.log(req.id); // to be sure that it returns proper order id
          // perhaps it could be next
          console.log(req.params.id);
    
          var order_id = user.orders.filter(function(e){ return e == req.params.id })[0]
    
          // then find this order
          Order.findOne({'_id': order_id }, function(err1, order) {
            if (err1)
              return done(err1);
            if (order) {
              res.send(order);
            }
          });
        }
      });
    });
    

    【讨论】:

    • 感谢您的回复!我尝试了方法 1 并得到:ReferenceError: Order is not defined。当我尝试方法 2 时,我得到: user.orders.filter(function(e){ return e._id == req.order.id })[0] ^ TypeError: Cannot read property 'id' of undefined 我没有一个单独的订单模式 - 它是我的用户模型的一部分......我现在在底部添加模式和路由到我的原始代码......
    • 好的,那你应该告诉我你的路线,因为看起来它们不包含order_id,或者可能正好有req.order_id
    • 已添加。如果您想看其他内容,请告诉我
    • 好的,谢谢,我更新了我的答案。我建议你 console.log(req); 以确保它包含正确的信息。
    • 选项 2 的旧版本在我添加“req.params.id”时有效。我发布了在原始帖子底部有效的代码。谢谢!
    猜你喜欢
    • 1970-01-01
    • 2020-03-14
    • 2019-02-20
    • 2017-08-15
    • 1970-01-01
    • 2019-07-19
    • 2012-07-05
    • 1970-01-01
    相关资源
    最近更新 更多