2014-10-23 25 views
10

Tôi hiểu rằng không có cách tích hợp trong Sails.js/Waterline của các liên kết lồng nhau sâu, vì vậy tôi đang cố gắng sử dụng lời hứa bluebird để thực hiện điều đó nhưng tôi chạy vào một vấn đề.Sails.js/Waterline điền vào liên kết lồng nhau sâu

Tôi đang truy xuất thành công người dùng và tất cả các bài đăng (được điền bằng bộ sưu tập hình ảnh) được liên kết với nó (console.log cho tôi biết mọi thứ được điền chính xác). Tuy nhiên, khi tôi ghi đè thuộc tính "bài đăng" của người dùng và cố gắng chỉ định các bài đăng được điền đầy đủ được truy xuất trước đó, nó không điền đúng thuộc tính hình ảnh của Post.js. Nó giống như ORM đang ngăn cản bộ sưu tập hình ảnh của Post.js được gán thủ công.

Tôi đang làm gì sai? Cách tốt nhất để điền các liên kết lồng nhau từ một đến nhiều là gì?

Bellow Tôi đã dán tất cả các mã mà tôi đang thực hiện ....

// 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" 
    } 
    }, 
} 

Kính trọng,

Savio Lucena

Trả lời

11

Đây có thể là câu hỏi cũ, nhưng tốt hơn nên có câu trả lời, vì vậy người dùng sails.js có thể hưởng lợi từ nó.

Vấn đề của bạn ở đây là khi cánh buồm trả về bản ghi (Bên trong mảng), các khóa của bản ghi tương ứng với các liên kết, thực tế là getters/setters, và có vẻ như người đặt không cho phép bạn muốn. Bạn có thể sử dụng Object.getOwnPropertyDescriptor(user, 'posts') để xác nhận. Vì vậy, những gì bạn cần làm để có thể ghi đè thuộc tính như bạn muốn, là gọi .toObject trên đó, (hoặc nhân bản thuộc tính của nó qua _.clone hoặc lặp theo cách thủ công nhưng bạn sẽ nhận được rất nhiều rác với nó, vì vậy dính vào .toObject), trong mọi trường hợp, bạn sẽ có được một đối tượng mới với các thuộc tính bạn cần và không có giới hạn nào trong cách bạn sửa đổi nó ngay bây giờ.

Vì vậy, mã của bạn sẽ trông như thế này:

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); 
}); 
} 
0

Bạn cần phải ghi đè lên mỗi đối tượng bài id trong sử dụng mảng .posts. Để biết thêm thông tin, hãy kiểm tra câu trả lời này https://stackoverflow.com/a/26452990/4261327.

+1

Jani, bạn có thể khai thác thêm trong câu trả lời của bạn? Tôi đã thử tất cả các loại ghi đè, nhưng bằng cách nào đó bởi vì hình ảnh là một liên kết nhiều-nhiều, nó ngăn chặn trường cụ thể đó bị ghi đè. –

Các vấn đề liên quan