Javascript 在节点js上迭代
嗨,我遇到了一个问题,我试图迭代一个键列表,创建一个匹配实体的列表 代码如下所示Javascript 在节点js上迭代,javascript,node.js,promise,Javascript,Node.js,Promise,嗨,我遇到了一个问题,我试图迭代一个键列表,创建一个匹配实体的列表 代码如下所示 let previous = undefined; for (let i = offset; i < response.keys.length; i++) { logger.debug("iteration " + i + " previous: " + previous) logger.debug("instance key: " + response.keys[i]) if (pr
let previous = undefined;
for (let i = offset; i < response.keys.length; i++) {
logger.debug("iteration " + i + " previous: " + previous)
logger.debug("instance key: " + response.keys[i])
if (previous) {
previous = previous
.then((entities) => {
if (entities.length === limit) {
i = response.keys.length;
} else {
readEntity(response.keys[i])
.then((instance) => {
matchInstance(instance, conditions)
logger.debug("is match: " + isMatch)
.then((isMatch) => {
if (isMatch)
entities.push(instance);
//resolve(entities);
}).catch((err) => {
reject(err)
})
}).catch((err) => {
reject(err)
})
}
}).catch((err) => {
reject(err)
})
} else {
previous = readEntity(response.keys[i])
.then((instance) => {
logger.debug("reading instance: " + instance.key)
matchInstance(instance, conditions)
.then((isMatch) => {
if (isMatch) {
return instance
} else {
logger.debug("instance does not match")
}
}).catch((err) => {
reject(err)
})
}).catch((err) => {
reject(err)
})
}
}
let previous=未定义;
for(设i=offset;i{
if(entities.length==限制){
i=响应。键。长度;
}否则{
readEntity(response.keys[i])
.然后((实例)=>{
matchInstance(实例、条件)
调试(“is匹配:+isMatch”)
.然后((isMatch)=>{
如果(isMatch)
实体。推送(实例);
//解决(实体);
}).catch((错误)=>{
拒绝(错误)
})
}).catch((错误)=>{
拒绝(错误)
})
}
}).catch((错误)=>{
拒绝(错误)
})
}否则{
previous=readEntity(response.keys[i])
.然后((实例)=>{
debug(“读取实例:“+instance.key”)
matchInstance(实例、条件)
.然后((isMatch)=>{
如果(isMatch){
返回实例
}否则{
debug(“实例不匹配”)
}
}).catch((错误)=>{
拒绝(错误)
})
}).catch((错误)=>{
拒绝(错误)
})
}
}
但是它只通过for循环一次,就像,它没有返回任何东西
我也有一些调试
2017-10-04T15:09:58+0200 <debug> data.js:202 (seekKeys.then) iteration 0 previous: undefined
2017-10-04T15:09:58+0200 <debug> data.js:203 (seekKeys.then) instance key: employees/existing@...
2017-10-04T15:09:58+0200 <debug> data.js:202 (seekKeys.then) iteration 1 previous: [object Promise]
2017-10-04T15:09:58+0200 <debug> data.js:203 (seekKeys.then) instance key: employees/test@...
2017-10-04T15:09:58+0200 <debug> data.js:202 (seekKeys.then) iteration 2 previous: [object Promise]
2017-10-04T15:09:58+0200 <debug> data.js:203 (seekKeys.then) instance key: employees/unique@...
2017-10-04T15:09:58+0200 <debug> data.js:202 (seekKeys.then) iteration 3 previous: [object Promise]
2017-10-04T15:09:58+0200 <debug> data.js:203 (seekKeys.then) instance key: employees/update@...
2017-10-04T15:09:59+0200 <debug> data.js:231 (readEntity.then) reading instance: existing@...
2017-10-04T15:09:59+0200 <debug> data.js:237 (matchInstance.then) instance does not match
2017-10-04T15:09:58+0200 data.js:202(参见kkeys.then)迭代0上一次:未定义
2017-10-04T15:09:58+0200 data.js:203(seekKeys.then)实例键:employees/existing@...
2017-10-04T15:09:58+0200 data.js:202(seekKeys.then)迭代1上一次:[对象承诺]
2017-10-04T15:09:58+0200 data.js:203(seekKeys.then)实例键:employees/test@...
2017-10-04T15:09:58+0200 data.js:202(seekKeys.then)迭代2上一次:[对象承诺]
2017-10-04T15:09:58+0200 data.js:203(seekKeys.then)实例键:employees/unique@...
2017-10-04T15:09:58+0200 data.js:202(seekKeys.then)迭代3上一次:[对象承诺]
2017-10-04T15:09:58+0200 data.js:203(seekKeys.then)实例键:employees/update@...
2017-10-04T15:09:59+0200 data.js:231(readEntity.then)读取实例:existing@...
2017-10-04T15:09:59+0200 data.js:237(matchInstance.then)实例不匹配
如果你需要更多信息,请告诉我。谢谢您可以为此编写递归函数(不推荐):
let index = 0;
let errors = [];
function promiseIterator (index) {
if (response.keys[index]) {
readEntity(response.keys[index]).then((instance) => {
matchInstance(instance, conditions).then(() => {
logger.debug("is match: " + isMatch).then(() => {
if (isMatch) entities.push(instance);
promiseIterator(index+1);
});
});
}).catch((err) => {
//error handler
errors.push({keyIndex: index, err: err});
promiseIterator(index+1);
});
}
}
promiseIterator(offset);
// do your stuff with error array
以上代码可能不太准确,请根据您的要求进行调整
但由于您需要迭代承诺,建议使用库并根据您的要求实现每个或所有功能。您可以为此编写递归函数(不推荐):
let index = 0;
let errors = [];
function promiseIterator (index) {
if (response.keys[index]) {
readEntity(response.keys[index]).then((instance) => {
matchInstance(instance, conditions).then(() => {
logger.debug("is match: " + isMatch).then(() => {
if (isMatch) entities.push(instance);
promiseIterator(index+1);
});
});
}).catch((err) => {
//error handler
errors.push({keyIndex: index, err: err});
promiseIterator(index+1);
});
}
}
promiseIterator(offset);
// do your stuff with error array
以上代码可能不太准确,请根据您的要求进行调整
但由于您需要迭代承诺,建议您使用库并根据您的需求实现
每个
或所有
功能。下一次,如果:,实际上,您已经用文字(以及代码)解释了您试图实现的目标。我试图对代码的目标进行反向工程,我认为您正试图这样做:
response.keys中有一个值数组
限制
匹配数,并在有限制
匹配项后停止寻找更多匹配项response.keys
中的项目顺序查找这些匹配项readEntity(val)检测匹配项。然后()
后跟matchInstance()。然后()
测试limit
long的匹配项数组limit
结果后停止处理的要求使您的特定案例稍微复杂一些
.reduce()承诺链
序列化基于承诺的异步操作的一种经典设计模式是使用.reduce()
,其中,reduce中的累加器值是一个承诺,并链接到该承诺以强制序列化。您可以这样实现:
// get subset of response.keys that we can process with .reduce()
let keys = response.keys.slice(offset);
keys.reduce((p, val) => {
// return promise so we continually chain
return p.then(entities => {
// if entities is not yet full
if (entities.length < limit) {
return readEntity(val).then(instance => {
return matchInstance(instance, conditions).then(isMatch => {
if (isMatch) {
entities.push(instance);
}
// resolved value is entities so that is passed down the chain
return entities;
});
});
} else {
return entities;
}
});
}, Promise.resolve([])).then(entities => {
// process results here
}).catch(err => {
// process error here
});
示例实现:
使用Bluebird的Promise.mapSeries()运行系列中的内容 具有许多用于管理和排序承诺的有用功能。其中有一个函数,它接受数组作为输入,并序列化对数组中的每个项调用函数。由于您要求在达到
限制
结果后停止,因此我们不得不使用与通常稍有不同的方法,但它仍然使代码相当简单:
let entities = [];
Promise.mapSeries(response.keys.slice(offset), item => {
if (entities.length < limit) {
return readEntity(item).then(instance => {
return matchInstance(instance, conditions).then(isMatch => {
if (isMatch) {
entities.push(instance);
}
});
});
}
}).then(() => {
// process entities result here
}).catch(err => {
// handle error here
});
let entities=[];
Promise.mapSeries(response.keys.sl