Меню

Параллельная обработка асинхронных вызовов

05.07.2018 - java script, ЯП

Running parallel promises

Иногда вы будете запускать несколько асинхронных операций параллельно. И когда они все завершены, вы захочете сделать что то после. Например, вы можете обратиться к разным API, например к Facebook API и Twitter API, и когда оба ответа готовы, только тогда вы уже вернете что-либо клиенту.

Давайте сэмулируем это. Создадим два промиса.

const p1 = new Promise(resolve => {
    setTimeout(() => {
        console.log('Async op 1...');
        resolve(1);
    }, 2000)
});
const p2 = new Promise(resolve => {
    setTimeout(() => {
        console.log('Async op 2...');
        resolve(2);
    }, 2000)
});

И теперь мы хотим сделать что то после, только после того, как оба эти промиса будут завершены. Для этого воспользуемся статическим методом all класса Promise. В него мы передаем массив промисов. Этот метод вернет новый промис с результатом, когда все промисы в массиве дадут результат. Итак, мы можем получить этот промис, затем вызвать then. Передаем результат в колбэк функцию и отображаем в консоли.

Promise.all([p1,p2])
.then(result => console.log(result))
.catch(err => console.log("Error", err.message))
Async op 1...
Async op 2...
[ 1, 2 ]

Нужно прояснить несколько моментов. Во первых это работает не в многопотоке. Мы все еще работаем с одним потоком. Но этот один поток работает с несколькими асинхронными операциями. Почти одновременно. Мы не ждем результата первой асинхронной операции, а сразу запускаем вторую. Поэтому результаты в массиве будут не в том порядке, в каком указывались промисы, а в том, какой промис будет быстрее возвращать свои результаты.

Если хотя бы один промис вернет reject, то итоговый результат будет эта ошибка.

Если же нам не нужно ждать чтобы выполнились все промисы, а только чтобы выполнился любой из списка, то для этого есть метод race класса Promise.

Метки: , , ,

Добавить комментарий

Ваш e-mail не будет опубликован. Обязательные поля помечены *