Почему этот код JavaScript async/await не работает должным образом?
Я пробовал читать руководства и учебные пособия для async/await, но я не могу найти что-либо в этом адресе.
Вот код, о котором идет речь:
var func1 = new Promise((resolve, reject) => {
console.log("Func1");
setTimeout(() => {
resolve(10);
}, 100);
});
var func2 = new Promise((resolve, reject) => {
console.log("Func2");
setTimeout(() => {
resolve(20);
}, 5000);
})
let run = async() => {
let var1 = await func1;
let var2 = await func2;
console.log(var1);
console.log(var2);
}
run();
Ответы
Ответ 1
Причиной этого является то, что вы уже запускали своих исполнителей обещаний раньше. Исполнители Promise сразу оцениваются при передаче конструктору Promise
, поэтому вы получите следующее:
var func1 = new Promise((resolve, reject) => ...); // Logs "Func1"
var func2 = new Promise((resolve, reject) => ...); // Logs "Func2"
let run = async() => {
let var1 = await func1;
console.log(var1); // Logs 10
let var2 = await func2;
console.log(var2); // Logs 20
}
run();
Ответ 2
Основная проблема здесь func1
и func2
не являются функциями; Они promises. Как говорит Jonas W., promises немедленно вызовет их обратный вызов (resolve, reject) =>
, и их ожидание просто заставляет их ждать, пока они не будут решены.
Здесь вы можете увидеть желаемый результат:
var func1 = () => {
return new Promise((resolve, reject) => {
console.log("Func1");
setTimeout(() => {
resolve(10);
}, 100);
});
}
var func2 = () => {
return new Promise((resolve, reject) => {
console.log("Func2");
setTimeout(() => {
resolve(20);
}, 5000);
});
}
let run = async() => {
let var1 = await func1();
let var2 = await func2();
console.log(var1);
console.log(var2);
}
run();
Ответ 3
await
в основном означает, что перед продолжением доступно следующее значение. Обещание начинает решаться, когда вы его создаете, неважно, когда его ждут.
Ответ 4
Функция запуска находится в синхронном порядке, например. код выполняет его шаг за шагом:
- вызовите func1() и дождитесь ответа.
- вызовите func2() и дождитесь ответа.
- log var1.
- log var2.
Таким образом, последние 2 шага будут выполняться только тогда, когда вызов функции func2() завершит обещание, например. данные после таймаута. Таким образом, он будет ждать полные 5 секунд до регистрации как var1, так и var2.
Другой способ довольно разный
1. вызовите func1() и дождитесь ответа.
2. log var1.
3. вызовите func2() и дождитесь ответа.
4. log var2.
Шаг 2 будет ждать, пока первый шаг не вернет данные, например. после 100 мс, а затем перейдем к тому же для шага 3 и 4.