[TIL] 20210426_Promise, Async/Await

16269 단어 TILTIL

Promise

자바스크립트에서 비동기 처리에 사용되는 객체입니다.

동기 vs 비동기

비동기를 사용하면 불필요한 기다림을 줄일 수 있습니다.

위 그림에서는 4-2-3-1 순서로 작업이 완료가 됩니다. 하지만 작업 완료 순서를 제어하고 싶다면 어떻게 해야 될까요. 콜백 함수를 통해 순서를 제어할 수 있습니다. 하지만 Promise는 그것을 좀 더 간결하게 해줍니다(콜백 지옥으로부터 구원해줍니다).

Promise의 3가지 상태

대기 (Pending): 비동기 처리 로직이 아직 완료되지 않은 상태입니다.
이행 (Fullfiled): 비동기 처리가 완료되어 프로미스가 결과 값을 반환한 상태입니다.
거부 (Rejected): 비동기 처리가 실패하거나 오류가 발생한 상태입니다.

Promise Chaining

프로미스는 여러 개의 프로미스를 연결하여 사용할 수 있습니다. then() 메서드를 사용하면 새로운 프로미스 객체가 반환됩니다. then() 메서드 안의 data는 앞전 프로미스에서 전달받은 return값입니다.

예외처리
아래의 Promise를 리턴하는 sayHello() 함수에서 resolve 대신 reject를 전달한다면, 가장 아래의 catch에서 에러 처리가 됩니다.

// Promise를 리턴하는 함수들
const sayHello = () => {
  return new Promise((resolve, reject) => {
    setTimeout(() => {
      resolve('Hello');
      // reject('Hi. I am an error!');
    }, 500);
  })
}

const callBanseok = () => {
  return new Promise((resolve, reject) => {
    setTimeout(() => {
      resolve('Banseok!')
    }, 300);
  })
}

const greet = () => {
  return new Promise((resolve, reject) => {
    setTimeout(() => {
      resolve('Nice to meet ya!');
    }, 100);
  })
}

// Promise Chaining
sayHello()
  .then(data => {
    console.log('data1 === ', data);
    return callBanseok();
  })
  .then(data => {
    console.log('data2 === ', data);
    return greet();
  })
  .then(data => {
    console.log('data4 === ', data);
  })
  .catch(err => {
    console.log('err === ', err);
  })

동기적으로 작동한다면 greet(), callBanseok(), sayHello() 순으로 실행이 될 것입니다. 하지만 then() 메서드는 여러 개의 Promise 함수들을 연결하고 그것들을 순차적으로 실행시킵니다.

Async/Await

자바스크립트의 비동기 처리 패턴 중 가장 최근에 나온 문법입니다.
기존 비동기 처리 방식인 콜백 함수와 프로미스의 단점을 보완하고 가독성과 유지보수가 쉬운 코드를 작성할 수 있게 도와줍니다.

예시는 다음과 같습니다.

// Promise를 리턴하는 함수들
const sayHello = () => {
  return new Promise((resolve, reject) => {
    setTimeout(() => {
      resolve('Hello');
    }, 500);
  })
}

const callBanseok = () => {
  return new Promise((resolve, reject) => {
    setTimeout(() => {
      resolve('Banseok!')
    }, 300);
  })
}

const greet = () => {
  return new Promise((resolve, reject) => {
    setTimeout(() => {
      resolve('Nice to meet ya!');
    }, 100);
  })
}

// 함수의 앞에 async 키워드를 써줍니다.
const result = async () => {
  const one = await sayHello(); // Promise를 리턴하는 함수 앞에 await 키워드를 써줍니다.
  console.log(one);

  const two = await callBanseok(); // await은 단어 뜻 그대로 함수가 완료될 때까지 기다렸다가, 완료되면 다음으로 넘어갑니다.
  console.log(two);

  const three = await greet();
  console.log(three);

}

result();

Promise와 같이 비동기 처리를 구현하지만, 코드의 모양새가 동기적인 처리의 모양과 비슷하면서 더 깔끔합니다. 코드를 유지 보수하는 데에도 도움이 될 것 같습니다.

좋은 웹페이지 즐겨찾기