Поэтому я обычно занимаюсь асинхронными функциями, используя цепочку .then
. Но на этот раз он этого не решает. Это ситуация.
return Promise.all([
Banner.findOne(),
event.findOne({
status: true
}),
Account.find({
accType: 'employer'
})
.then(([banner, event, account]) => {
res.render('index', {
title: 'Web Project Studio',
user: req.user,
banner: banner,
event: event,
employer: account
});
}).catch(e => {
console.error(e);
})
]);
Так что это сработало, и все было здорово. Но теперь я решил изменить способ выбора активного event
. Я вызываю коллекцию, называемую generalInfo
и захватываю идентификатор к текущему событию. Вот что у меня есть до сих пор:
return Promise.all([
Banner.findOne(),
GeneralInfo.findOne(),
Account.find({
accType: 'employer'
})
]).then(([banner, generalInfo, account]) => {
Event.findById(generalInfo.activeEventId).then(r => {
console.log('test');
var event = r;
res.render('index', {
title: 'Web Project Studio',
user: req.user,
banner: banner,
event: event,
employer: account
});
}).catch(e => console.log(e));
}
}).catch(e => {
console.error(e);
})
Но этот код начинает выглядеть как аддон.
Я также пробовал что-то вроде этого:
var banner = await Banner.findOne().catch(e => console.log(e));
var currentEvent = await GeneralInfo.findOne().catch(e => console.log(e));
currentEvent.then(async r => {
var event = await Event.findOneById(r.activeEventId).catch(e => console.log(e));
}).catch(e => console.log(e));
Это не завершено, но это как-то показывает мой образ мыслей. Но опять же, не повезло.
Итак, как я могу ладить с асинксом, не .then
навсегда? Мне нужно передать все возвращенные объекты функции render
.
Вы можете просто гнездиться раньше, что имеет преимущество перекрытия больше (см. ***
комментарий (ы)):
return Promise.all([
Banner.findOne(),
GeneralInfo.findOne()
.then(generalInfo => Event.findById(generalInfo.activeEventId)), // ***
Account.find({
accType: 'employer'
})
}).then(([banner, event, account]) => {
res.render('index', {
title: 'Web Project Studio',
user: req.user,
banner: banner,
event: event,
employer: account
});
}).catch(e => {
console.error(e);
});
Если вы делаете это событие generalInfo => много, вы можете обернуть его в служебную функцию.
С другой стороны, если они не должны пересекаться, как это, вы можете свести к минимуму вложенности, добавив еще один, then
:
return Promise.all([
Banner.findOne(),
GeneralInfo.findOne(),
Account.find({
accType: 'employer'
})
]).then(([banner, generalInfo, account]) => {
return Event.findById(generalInfo.activeEventId).then(event => { // ***
return [banner, event, account]; // ***
}); // ***
}).then(([banner, event, account]) => {
res.render('index', {
title: 'Web Project Studio',
user: req.user,
banner: banner,
event: event,
employer: account
});
}).catch(e => {
console.error(e);
})
Это должно сработать.
return Promise.all([
Banner.findOne(),
GeneralInfo.findOne(),
Account.find({
accType: 'employer'
})
]).then(async ([banner, generalInfo, account]) => {
res.render('index', {
title: 'Web Project Studio',
user: req.user,
banner: banner,
event: await Event.findById(generalInfo.activeEventId),
employer: account
});
}).catch(e => {
console.error(e);
})