简体   繁体   English

Sails.js / Waterline填充深层嵌套关联

[英]Sails.js/Waterline populate deep nested association

I understand that there is no built-in way in Sails.js/Waterline of populating deep nested associations yet, so I am trying to use bluebird promises to accomplish that but I'm running into a problem. 我知道在Sails.js / Waterline中没有内置的方式来填充深层嵌套的关联,所以我试图使用蓝鸟的承诺来实现这一点,但我遇到了一个问题。

I'm successfully retrieving the user, and all the posts (populated with the images collection) associated with it (console.log shows me that everything is filled properly). 我正在成功检索用户,以及与之关联的所有帖子(填充了图像集合)(console.log向我显示所有内容都已正确填充)。 However, when I override the property "post" of the user and try to assign the fully populated posts retrieved before, it does not fill properly the images property of Post.js. 但是,当我覆盖用户的属性“post”并尝试分配之前检索的完全填充的帖子时,它不能正确填充Post.js的images属性。 It is like the ORM is preventing the image collection of Post.js to be manually assigned. 这就像ORM阻止手动分配Post.js的图像集合。

What am I doing wrong? 我究竟做错了什么? What is the best way of populating deep nested one-to-many associations? 填充深层嵌套的一对多关联的最佳方法是什么?

Bellow I've pasted all the code that I'm executing.... 贝娄我已经粘贴了我正在执行的所有代码....

// Populate nested association
nested: function (req, res, next){
var username = req.param("id");

User
.findOneByUsername(username)
.populateAll()      
.then(function (user){
    var posts = Post.find({
        "user": user.id
    })
    .populate('images')
    .populate('category')
    .then(function (posts){
        return posts;
    });
    return [user, posts];
})
.spread(function (user, posts){
    user.posts = posts; // This won't work.... It assigns all the fields properly but the images collection attribute
    res.json(user);
}).catch(function (err){
    if (err) return res.serverError(err);
});
}

// --- User.js Model --- //
module.exports = {
   attributes: {
    .....,
    posts: {
        collection: "post",
        via: "user"
    },
    .....
   }
 }

// --- Post.js Model --- //
module.exports = {
    attributes: {
       ....,
       user: {
         model: "user"
       },
       images: {
         collection: "postImage",
         via: "post"
       },
       ....
    }
}

// --- PostImage.js Model --- //
module.exports = {

   attributes: {
     ....,
     post: {
       model: "post"
     }
   },
}

Regards, 问候,

Sávio Lucena 萨维奥卢塞纳

This might be an old question, but its better to have an answer, so sails.js users can benefit of it. 这可能是一个老问题,但最好有一个答案,所以sails.js用户可以从中受益。

Your issue here is that when sails returns a record (Inside an array), the keys of that record that correspond to associations, are in fact getters/setters , and it seems that the setter does not allows what you want. 你的问题是,当sails返回一条记录(在数组内)时,该记录中与关联对应的键实际上是getter / setter ,而且似乎setter不允许你想要的东西。 You can use Object.getOwnPropertyDescriptor(user, 'posts') to confirm. 您可以使用Object.getOwnPropertyDescriptor(user, 'posts')进行确认。 So what you need to do in order to be able to override that property as you want, is to call .toObject on it, (or clone its properties via _.clone or manually looping but you'll get a lot of junk with it, so stick to the .toObject ), in any case you get a new object with the properties you need, and there is no restriction in how you modify it now. 所以你需要做的就是能够根据需要覆盖该属性,就是在它上面调用.toObject ,(或者通过_.clone克隆它的属性或者手动循环但是你会得到很多垃圾,所以坚持.toObject ),无论如何你得到一个具有你需要的属性的新对象,现在你如何修改它没有任何限制。

So your code will look like this: 所以你的代码看起来像这样:

User
.findOneByUsername(username)
.populateAll()      
.then(function (user){
    var posts = Post.find({
        "user": user.id
    })
    .populate('images')
    .populate('category')
    .then(function (posts){
        return posts;
    });
    return [user, posts];
})
.spread(function (user, posts){
    user = user.toObject() // <- HERE IS THE CHANGE!
    user.posts = posts; // It will work now
    res.json(user);
}).catch(function (err){
    if (err) return res.serverError(err);
});
}

You have to overwrite each post id object in user.posts array. 您必须覆盖user.posts数组中的每个post id对象。 For more info check this answer https://stackoverflow.com/a/26452990/4261327 . 有关详细信息,请查看此答案https://stackoverflow.com/a/26452990/4261327

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

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