Я пытаюсь создать массив обещаний, которые будут выводить сообщение на консоль при выполнении. Однако кажется, что он печатается только один раз, хотя в массиве есть 10 объектов обещаний.
Я пробовал решение в Обещания ES6/вызов функции после выполнения нескольких обещаний (нельзя использовать Promises.all) но это все еще не работает.
function fillArrayWithPromise(promise, numTimes) {
let promiseArr = Array(numTimes).fill(promise);
console.info(promiseArr.join("-"));
return promiseArr
}
var sendStuffB = new Promise(
function(resolve, reject) {
try {
console.info("submitted one req");
} catch (error) {
console.info("Error: " + error);
}
}
)
let testA = fillArrayWithPromise(sendStuffB, 10);
Promise.all(
testA.map(promise => Promise.resolve(promise).catch(err => console.info(error)))
).then(function() {
console.info("End");
});
Я ожидал, что консоль будет печатать 10 раз «Один объект отправлен», но он печатается на консоли только один раз и после этого продолжает работать бесконечно долго.
Вот журнал ошибок: Запуск тестового сценария... Один объект отправлен отправлен один запрос [object Promise]-[object Promise]-[object Promise]-[object Promise]-[object Promise]-[object Promise]-[object Promise]-[object Promise]-[object Promise]-[object Promise]
NB: Совершенно бесполезно копировать один и тот же объект обещания в массив.
Здесь две ошибки: вы не разрешаете обещание, и у вас есть одно и то же обещание (которое будет выполнено только один раз) 10 раз.
Вы не вызываете функцию разрешения в промисах, поэтому они никогда не завершатся. Попробуйте сделать это:
var sendStuffB = new Promise(
function(resolve, reject) {
try {
console.info("submitted one req");
resolve();
} catch (error) {
console.info("Error: " + error);
reject(error);
}
}
)
@Andreas - когда функция была вызвана при создании обещания. Обратите внимание, что функция никогда не завершается, а не никогда не звонят
@Tom не разрешается, поэтому End
не печатается. Это не должно влиять submitted one req
@AyushGupta, вы правы, есть только одно обещание, которое ожидается 10 раз (в отличие от создания 10 отдельных обещаний, как в вашем ответе, что, вероятно, и было желаемым)
@Andreas Promise.resolve
создает новое обещание, которое немедленно преобразуется в значение, которое вы передаете, однако, когда это значение является обещанием, оно ожидает разрешения этого обещания и возвращает его значение разрешения. Это не заставляет переданное обещание разрешиться, но ждет его.
Потому что sendStuffB
— это только одно обещание, поэтому оно разрешается только один раз. Все остальные элементы в вашем массиве являются ссылками на одно и то же разрешенное обещание.
Вместо этого в функции fillArrayWithPromise
передайте функцию, которая возвращает обещание, и вызовите эту функцию отдельно для каждого элемента массива.
Кроме того, всегда не забывайте разрешать или отклонять промис в функции конструктора промисов по мере необходимости.
function fillArrayWithPromise(promiseFn, numTimes) {
let promiseArr = Array(numTimes).fill(promiseFn).map(fn => fn()); //see this
return promiseArr
}
var sendStuffB = () => new Promise( // converted to function
function(resolve, reject) {
try {
console.info("submitted one req");
resolve(); // remember to resolve
} catch (error) {
console.info("Error: " + error);
reject(error); // reject
}
}
)
let testA = fillArrayWithPromise(sendStuffB, 10);
Promise.all(
testA.map(promise => Promise.resolve(promise).catch(err => console.info(error)))
).then(function() {
console.info("End");
});
@Андреас Андреас, нет, Promise.resolve(promise)
в этом случае сводится к невыполненному обещанию.
Как видно по Promise.resolve(new Promise(() => {})).then(console.info)
Это базовый пример функциональности Promise.all.
Это может помочь вам.
const delayArray = [1000,1500,2000];
const promises = delayArray.map((item) => {
return new Promise((resolve,reject) => {
setTimeout(()=>{
console.info('I was resolved in' + item + 'ms');
resolve('Resolved' + item + 'ms');
},item);
});
});
Promise.all(promises)
.then((values) => console.info(values));
Promise
.promise
вfillArrayWithPromise
является ссылкой наsendStuffB
, поэтому вы заканчиваетесь массивомnumTimes
копий этой ссылки, но не копиями упомянутогоPromise