비동기 처리 방식 - promise & async & await

페리·2021년 6월 30일
0
post-thumbnail

부트캠프를 하는 도중, 잘 알지 못했던 비동기 처리에 대해 정리하는 시간을 가지게 되었다.

mozilla 사이트에서는 다음과 같이 정의한다.

Async

async function 선언은 항상 AsyncFunction 객체를 반환하는 하나의 비동기 함수를 정의한다. 비동기 함수는 이벤트 루프를 통해 비동기적으로 작동하는 함수이다.
이 async 함수는 항상 promise를 반환한다. 그리고 async 함수 내에는 await가 포함될 수 있는데, await는 async 함수의 실행을 일시 중지하고 전달된 promise의 해결을 기다린 다음 async 함수의 실행을 다시 시작하고 완료 후에 값을 반환한다.

Promise

async 함수에 의해 반환된 값으로 해결되거나 async 함수 내에서 발생하는 캐치되지 않는 예외로 거부되는 값

예시는 다음과 같다.

function resolveAfter2Seconds() {
   return new Promise(resolve => {
      setTimeout(() => {
         resolve('resolved');
      }, 2000);
   });
}

async function asyncCall() {
   console.log('calling');
   const result = await resolveAfter2Seconds();
   console.log(result);
}

asyncCall();
  1. asyncCall 함수가 먼저 실행된다.
  2. calling log가 나타난다.
  3. async 함수 내의 await에 의해 resolveAfter2Seconds가 실행되고, async 함수를 일시정지한다.
  4. resolveAfter2Seconds 함수는 Promise 객체를 반환하는데, setTimeout로 2초 이후에 resolve가 실행된다.
  5. Promise 객체는 pending 상태로 대기하다가, resolve 될 때 async 함수의 실행을 재개하면서 받아온 result를 log로 찍는다.

Challenge

n개의 api가 들어왔다고 할 때, 최종 접근 가능한 스테이트의 어레이로 변환해주는 함수를 짜세요.

const url1 = "https://reqres.in/api/users";
const url2 = "https://reqres.in/api/users";
const url3 = "https://reqres.in/api/users";

const urlArray = [url1, url2, url3];

function fetchArray(urlArr) {
   return new Promise(async (resolve, reject) => {
      const arr = [
         await fetch(urlArr[0]).then(res => res.json()),
         await fetch(urlArr[1]).then(res => res.json()),
         await fetch(urlArr[2]).then(res => res.json())
      ]
      resolve(arr);
   });
}

async function convert() {
  const result = await fetchArray(urlArray);
  console.log(result);
}

convert();

convert 함수를 실행하게 되면 다음과 같이 결과가 나온다.

  1. convert 함수에서 fetchArray 함수에 await을 걸어놓았기 때문에 순차적으로 result를 받아온 뒤에 log를 찍게 된다.
  2. fetchArray 함수에서는 Promise 객체를 반환하는데, Promise 내부에서도 반드시 순차적으로 실행되어야 하는 부분이 있기 때문에 async arrow 함수로 정의했고, await을 통해 arr가 구성되고나서 resolve를 실행함으로써, 온전히 변경된 arr를 반환하도록 하였다.
  3. 본래 convert 함수에서는 await 되어있던 fetchArray에서 Promise 객체가 반환되었으므로, url에서 받아와 변경된 state들로 구성되어있는 arr를 log로 찍게되는 것이다.

0개의 댓글