Извлечение данных из вашей базы данных является асинхронным, ваш текущий код игнорирует это и пытается продолжить до разрешения обещания.
Это довольно распространенная ошибка, когда люди не привыкли к обещаниям.Обещания - это в основном симпатичные обратные вызовы, вместо (err, info)
вы получаете функцию .then
и .catch
(и несколько других).
Вам необходимо поместить свой код электронной почты в функцию .then
.Так что это будет примерно так:
function sendEmail() {
let recipientEmail;
if (careHome === 'ACareHome') {
admin.database().ref('managers').once("value").then((snapshot) => {
let managerEmail = snapshot.child("Manager Name").val();
recipientEmail = managerEmail;
console.log(`Recipient is ${recipientEmail}`);
const mailOptions = {
from: '*****', // sender address
subject: `An appointment has been requested at ${ACareHome}.`,
html: `Hello, an appointment has been booked at ${ACareHome} on ${date} at ${time}. The requestors name is, ${firstName}. You can email them on ${email}.`
};
mailOptions.to = recipientEmail;
return new Promise(function promise(resolve, reject) {
transporter.sendMail(mailOptions, function(error, info){
if (error) {
return console.log(error);
return reject(error);
}
console.log('Message sent: ' + info.response);
return resolve(info);
});
});
});
}
}
Я сделал три вещи здесь.
- Я все обернул в функцию для простоты.
- Я переместил код отправки электронного письма в функцию обещания
.then
.Это означает, что как только что-то будет получено из базы данных, которую вы отправляете по электронной почте, теперь вы ждете ответа. - Я заключил в функцию transporter.sendMail.Для этого есть утилиты, но для ясности я показал вам, как это сделать вручную.Это означает, что новая функция из пункта 1 теперь возвращает обещание.Теперь вы можете использовать верхнюю функцию
sendMail
так же, как вы делали код вашей базы данных, вызывая sendMail().then(result...).catch(error...)
.
Часто более идиоматично не смешивать код обратного вызова и обещания путем обертываниялюбой код, ориентированный на обратный вызов, с такими вещами, как Bluebird.promisify, или завершение функции, ориентированной на обратный вызов, вручную, как я.Это означает, что вы просто имеете дело с кодом типа .then
и .catch
.
Прошу прощения, если вы уже знали о Promises vs Callbacks, это обычная тема, которую я вижу по вопросам, поэтому я ответил на неев полном объеме.