在某些情况下需要停止多步承诺 [英] Need to stop a mutli-step Promise under certain conditions
问题描述
我正在尝试停止执行多步骤Promise.基本上,在Firebase向我返回一个数字后,如果 snapshot.size === 0
,则无需继续执行其余操作.我已经尝试过 return
,并且已经尝试过 throw
,但是似乎都无法阻止错误的发生,即:
I am trying to stop a multi-step Promise execution. Basically, after Firebase returns a number to me, if snapshot.size === 0
there is no need to continue with the rest. I've tried return
and I've tried throw
but neither seem to stop the error from happening which is:
> error TypeError: snapshot.map is not a function
> at userSources.get.then.then.snapshot (/Users/username/Personal Projects/ionic-attempt1/functions/index.js:108:14)
> at process._tickCallback (internal/process/next_tick.js:68:7)
> (node:18880) UnhandledPromiseRejectionWarning: Error [ERR_HTTP_HEADERS_SENT]: Cannot set headers after they are sent to the client
> at ServerResponse.setHeader (_http_outgoing.js:470:11)
> at ServerResponse.header (/Users/username/Personal Projects/ionic-attempt1/functions/node_modules/express/lib/response.js:771:10)
> at ServerResponse.send (/Users/username/Personal Projects/ionic-attempt1/functions/node_modules/express/lib/response.js:170:12)
> at ServerResponse.json (/Users/username/Personal Projects/ionic-attempt1/functions/node_modules/express/lib/response.js:267:15)
> at userSources.get.then.then.then.then.catch.error (/Users/username/Personal Projects/ionic-attempt1/functions/index.js:231:32)
> at process._tickCallback (internal/process/next_tick.js:68:7)
> (node:18880) UnhandledPromiseRejectionWarning: Unhandled promise rejection. This error originated either by throwing inside of an async function without a catch block, or by rejecting a promise which was not handled with .catch(). (rejection id: 1)
> (node:18880) [DEP0018] DeprecationWarning: Unhandled promise rejections are deprecated. In the future, promise rejections that are not handled will terminate the Node.js process with a non-zero exit code.
i functions: Finished "services" in ~1s
现在,第一个错误 TypeError:snapshot.map不是函数
实际上在下一个 .then
中,所以我什至不希望发生这种情况.最下面的部分是我不喜欢的,谈论承诺拒绝将如何终止该过程.
Now the first error TypeError: snapshot.map is not a function
is actually in the next .then
so it's something I don't even want to happen. The bottom part is what I don't like, talking about how promise rejections will terminatee the process.
这是我的代码:
var sources = [];
var userSources = firestore
.collection('sources')
.where('last_queried', '<', oneHourAgo)
.where('enabled', '==', true)
.where('uid', '==', uid);
userSources
.get()
.then(snapshot => {
if (snapshot.size === 0) {
console.log('fetch: no sources found in the last hour.');
return response.status(200).json({ message: 'No sources need updating' });
//throw response.status(200).json({ message: 'No sources need updating' });
}
snapshot.forEach(doc => {
var source = doc.data();
// update last time checked
firestore
.collection('sources')
.doc(doc.id)
.set({ last_queried: firebase.firestore.Timestamp.now() }, { merge: true });
sources.push({
id: doc.id,
name: source.name,
access_token: source.access_token
});
});
return sources;
})
.then(snapshot => {
return Promise.all(
snapshot.map(source => {
// Omitting code here
})
);
})
.then(all_accounts => {
console.log('all accounts retrieved.');
// Omitting code here
return accounts;
})
.then(accounts => {
return response.status(200).json({ message: accountLength + ' accounts updated', accounts: accounts });
})
.catch(error => {
console.log('error', error);
return response.status(200).json({ message: 'Error: ' + error });
});
推荐答案
会发生这种情况,它进入这种情况:
what happens is, it enters this case:
.get()
.then(snapshot => {
if (snapshot.size === 0) {
// the code touchs here, this function returns something that is not an array
console.log('fetch: no sources found in the last hour.');
return response.status(200).json({ message: 'No sources need updating' });
//throw response.status(200).json({ message: 'No sources need updating' });
}
在下一个.然后打电话给你:
in the next .then call you have this:
.then(snapshot => {
// snapshot is not an array anymore, and that's causing TypeError: snapshot.map is not a function
return Promise.all(
snapshot.map(source => {
// Omitting code here
})
);
})
您需要的是在第二个.then内更改为这样的功能
What you need is to change to some function like this inside the second .then
.then(snapshot => {
if (!Array.isArray(snapshot)) {
// do something here
}
return Promise.all(
snapshot.map(source => {
// Omitting code here
})
);
})
或者您可以拒绝第一个.then方法调用中的promise链,使用
Or you could reject the promise chain from the first .then method call, using
.then(() => {
// some code
return Promise.reject(new Error('fail'))
})
这篇关于在某些情况下需要停止多步承诺的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!