我正在尝试为数组的每个项添加一些额外的值。所以我有一个包含对象的数组,它们有:x,y和z字段。然后,我想根据http.get调用的响应为数组中的每个对象添加其他项。
主要数据是:帖子
见下面的代码:
router.get('/api/posts', function(req, res){
postModel.find({})
.limit(10)
.exec(function(err, posts) {
var options = {
host: 'localhost',
port: 3000,
path: '/user?id=12345678',
method: 'GET'
};
if(posts){
posts.forEach(function(post) {
var req = http.get(options, function(res) {
var bodyChunks = [];
res.on('data', function(chunk) {
bodyChunks.push(chunk);
}).on('end', function() {
var body = Buffer.concat(bodyChunks);
var parsedBody = JSON.parse(body);
post.fullname = parsedBody.user.fullname;
post.profilePic = parsedBody.user.profilePic;
});
});
});
res.json({
posts : posts
});
} else {
res.send('Post does not exist');
}
});
});
在 post.profilePic = parsedBody.user.profilePic 时 - profilePic 变量存在,但是当我通过 res从节点获得响应时.json ,其他值不是。
我在这里缺少什么?我一直使用这种方法与我的Angular前端没有问题。
由于
答案 0 :(得分:2)
这是一个非常常见的问题,您将异步代码视为同步代码。 http.get
未立即完成,也不会阻止代码继续执行,因此在您的请求完成之前调用res.json
。有很多方法可以解决这个问题,我会发布我的最爱 - Javascript Promises。
// use map instead of forEach to transform your array
// of posts into an array of promises
var postPromises = posts.map(function(post) {
return new Promise(function(resolve) {
var req = http.get(options, function(res) {
var bodyChunks = [];
res.on('data', function(chunk) {
bodyChunks.push(chunk);
}).on('end', function() {
var body = Buffer.concat(bodyChunks);
var parsedBody = JSON.parse(body);
post.fullname = parsedBody.user.fullname;
post.profilePic = parsedBody.user.profilePic;
// resolve the promise with the updated post
resolve(post);
});
});
});
});
// once all requests complete, send the data
Promise.all(postPromises).then(function(posts) {
res.json({
posts: posts
});
});
答案 1 :(得分:0)
根据回调节点工作。您在forEach循环中未完成回调,并且您正在回复用户。这是问题所在。
编写代码,我可以建议解决方案。
router.get('/api/posts', function(req, res){
postModel.find({})
.limit(10)
.exec(function(err, posts) {
var options = {
host: 'localhost',
port: 3000,
path: '/user?id=12345678',
method: 'GET'
};
if(posts){
var EventEmitter = require('events');
var HttpEvent = new EventEmitter();
let counts = 0;
let length = posts.length;
posts.forEach(function(post) {
var req = http.get(options, function(res) {
var bodyChunks = [];
res.on('data', function(chunk) {
bodyChunks.push(chunk);
}).on('end', function() {
var body = Buffer.concat(bodyChunks);
var parsedBody = JSON.parse(body);
posts.fullname = parsedBody.user.fullname;
posts.profilePic = parsedBody.user.profilePic;
HttpEvent.emit('done');
});
});
});
HttpEvent.on('done',()=>{
counts += 1;
if(counts == length){
res.json({
posts : posts
});
}
})
} else {
res.send('Post does not exist');
}
});
});
你正在做的另一件事是
post.fullname = parsedBody.user.fullname;
post.profilePic = parsedBody.user.profilePic;
应该是
posts.fullname = parsedBody.user.fullname;
posts.profilePic = parsedBody.user.profilePic;