티스토리 뷰

Javascript

[JS] async / await 개념정리

yojessie 2022. 5. 14. 22:29

await & async

promise가 콜백지옥을 무찌를 수 있는 좋은 방법이지만

그래도 코드가 복잡하기는 하다.

 

그래서 ES8 문법으로 awaitasync 가 추가되었다.

await 과 async 는 promise를 더 깔끔하게 사용할 수 있는 방법이다.

하지만 경우에 따라 더 좋은 방법들이 다르기때문에, 적절히 섞어서 활용하는 것이 필요하다.

 

 

 

 

 

promise 복습을 먼저 해보자

1초 후 텍스트 출력, 다시 2초후 텍스트 출력, 다시 3초후 텍스트를 출력하는 함수가 있다.

function timer(time) {
  return new Promise((resolve, reject) => {
    setTimeout(() => {
      resolve(time);
    }, time);
  });
}

console.log("start"); // 작업의 시작을 알리는 텍스트 출력
timer(1000)
  .then((result) => {
    console.log(result);
    return timer(result + 1000);
  })
  .then((result) => {
    console.log(result);
    return timer(result + 1000);
  })
  .then((result) => {
    console.log(result); // promise chain으로 작업을 연결
    console.log("end"); // 작업의 끝을 알리는 텍스트 출력 코드를 비동기처리
  });

promise를 이용해서 콜백지옥을 탈출했다.

promise chain을 통해 여러 작업들을 병렬로 잘 정리했지만, 아직도 이 코드가 복잡해보였던 슨생님들은 더 좋은 것을 만들어내셨다.

 

 

 

 

 

await, async를 사용해 다시 정리해보자

await는 promise를 실행하는 코드를 마치 동기적으로 작동하는 코드처럼

깔끔하게 순서대로 적을 수 있게 하는 syntactic sugar 이다.

 

 

기본적으로는 promise 함수를 사용할때, 앞에 await를 붙이면 된다.

await timer(1000);

이렇게 실행하는 함수는 결국 promise에서 resolve에 정의되어있는 리턴값을 받아 오는데,

그값을 변수에 저장해서 다음 작업에 사용하면 된다.

let result = await timer(1000);
console.log(result);

 

 

하지만 이렇게 바꿔 실행하면

'await는 async 함수 안에서만 실행할 수 있다'는 에러 문구가 뜬다.

 

그래서 await를 사용하려면 이렇게 바꿔줘야한다.

async function run() {
  let result = await timer(1000);
  console.log(result);
}
run();

 

async 가 앞에 붙은 함수를 만들어서 코드를 안에 넣고, 실행시켰다.

 

 

 

 

 

그래서 위에 then으로 병렬 정리했던 코드를 다시 한번 await를 사용해 바꿔 볼 수 있다.

async function run() {
  console.log("start");
  let result = await timer(1000);
  console.log(result);
  result = await timer(result + 1000);
  console.log(result);
  result = await timer(result + 1000);
  console.log(result);
  console.log("end");
}
run();

위 then 메소드를 활용한 것과 동일한 결과를 얻을 수 있다.

 

 

 

 

비동기처리가 한번 더 필요하다면?

async 함수를 실행했는데, 또 앞 뒤로 시작과 끝을 알리는 메세지가 출력되게 하려면?

console.log("parent start");
run();
console.log("parent end");

console.log('parent end') 는 동기적으로 실행되기때문에 비동기코드(setTimeout)가 실행되기 전에 먼저 실행된 것을 볼 수 있다.

 

 

그렇다면 이 코드들이 비동기처리 될 수 있도록 다시한번 await 시켜줄 수 있다.

async function run2() {
  console.log("parent start");
  await run();
  console.log("parent end");
}

run2();

 

 

💡

여기서 run 함수에 await 처리가 가능한 이유를 짚고가야한다.

console.log(run())으로 run 함수를 출력해보면

 

이렇게 promise 함수가 나오는 것을 확인해볼 수 있다.

async 함수는 또 다시 promise 함수를 리턴하는 것이다.

 

이것이 run()에도 다시 awiat를 붙이고, 그것을 다시 async 함수에 넣는 작업이 가능한 이유이다.

 

 

 


 

 

 

위에 정리한 내용은 이고잉님 강의를 보고 다시 정리해본 내용이다.

promise, await, async를 이해하기위해 많은 글과 강의를 돌고돌아

이제 겨우 조금 정리가 된 것 같다.

 

이 내용을 얼른 활용할 수 있는 날이 오면 좋겠다.

 

 

 

 

 

 

 

댓글
공지사항
최근에 올라온 글
최근에 달린 댓글
Total
Today
Yesterday
링크
«   2024/05   »
1 2 3 4
5 6 7 8 9 10 11
12 13 14 15 16 17 18
19 20 21 22 23 24 25
26 27 28 29 30 31
글 보관함