[javascript] async & await

HongDuHyeon·2022년 2월 21일
0
post-thumbnail
신발이 당첨 되고 싶었는데 앱 포인트가 당첨됐다. 느슨해진 일상속에 긴장감을 주ㄴ...

async await

promise를 좀 더 간결하고 간편하게 동기적으로 실행되는 것처럼 보이게 만들어주는 기능이다.
기존에 promise.then.then.then..... 이렇게 계속 체이닝을 하는 것 보다 api로 좀 더 간결하게 async await을 사용하면 동기식으로 코드를 순서대로 작성하는 것처럼 작성할 수 있게 도와준다.

예제 1.

먼저 간단한 기능적인 예시로 이름을 가져오는 함수가 있다고 가정하고 기존에 Promise 작업하는 것과 동일하게 작업을 하면 이렇게 나온다.

function fetchUser() {
    return new Promise((resolve, reject)=>{        
        resolve('DuHyeon');
    })
}

하지만 이때 function 앞에 async를 붙혀주게 된다면 그 코드블럭은 자동으로 Promise로 바뀌게 된다.

async function fetchUser() {
    return ('DuHyeon');
}

다른 예제를 해보려 하는데 먼저 네트워크 통신을 해서 백엔드에서 데이터를 받아오는데 10초 걸리는 코드가 있다고 가정해보자 10초가 걸리는 코드 후에 그 다음에 작성된 코드들이 실행 되므로 화면엔 10초 전에 아무것도 나오지 않을 것이다. 그래서 비동기적으로 실행할 수 있게 해줘야한다.

예제 2.

사과와 바나나를 각각 시간에 맞게 가져오는 함수를 작성해보겠다.

function delay(ms) {
    return new Promise(resolve => setTimeout(resolve,ms));
}

async function getApple () {
    await delay(2000);
    return '🍎';
}

async function getBanana () {
    await delay(1000);
    return '🍌';
}

먼저 delay()으로 몇초 후에 실행 될건지 시간초를 받아서 그 시간 후에 뿌려주는 함수를 만들어 놓고 위에서 작성한 async를 통해 함수를 작성한다.
여기서 await은 함수명 앞에 async가 붙은 함수에서만 쓸 수 있다.

function pickFruits () {
    return getApple()
    .then(apple => {
        return getBanana()
        .then(banana => `${apple} + ${banana}`)
    })
}

pickFruits().then(console.log)
// 🍎 + 🍌

하지만 갯수가 2개가 아니라 더 많아지게 된다면 아무리 콜백지옥을 탈출하려 Promise를 사용했지만 코드가 난잡해질수도 있다.
좀 더 간결하게 사용할 수 있는 다른 방법으로 작성해보자.

function delay(ms) {
    return new Promise(resolve => setTimeout(resolve,ms));
}

async function getApple () {
    await delay(2000);
    return '🍎';
}

async function getBanana () {
    await delay(1000);
    return '🍌';
}

async function pickFruits () {
   const apple = await getApple();
   const banana = await getBanana();
   return `${apple} + ${banana}`;
}

pickFruits().then(console.log)
// 🍎 + 🍌

이렇게 .then대신 apple과 banana를 async await으로 다 받아와서 return하면 좀 더 간결하게 작성이 가능하다. 하지만 사과를 받는데 3초 바나나를 받는데 3초, 이렇게 순차적으로 진행하면 총 6초를 기다려야하며 비효율적이다. 서로 연관이 되어있지 않기 때문에 기다릴 필요가 있지 않다.
이를 개선하려면 apple과 banana를 병렬적인 상태로 두어야한다.

async function pickFruits () {
    const applePromise = getApple();
    const bananaPromise = getBanana();
    const apple = await applePromise;
    const banana = await bananaPromise;
    return `${apple} + ${banana}`;
}

pickFruits().then(console.log);
// 🍎 + 🍌

지금의 코드를 실행하면 6초가 아닌 3초만에 값이 나온다.
병렬적인 상태로 두려면 applePromise,bananaPromise처럼 바로 만들어 준다면 Promise안에 있는 코드블럭이 바로 실행이 된다.

하지만 이렇게 병렬적으로 기능을 수행해야한다면 다른 더 좋은 작성 방법이 있다.

function pickAllFruits() {
    return Promise.all([getApple(), getBanana()])
    .then(fruits => fruits.join(' + '))
}

pickFruits().then(console.log);
// 🍎 + 🍌

all()이라는 api인데 all()은 promise 배열을 전달하게 되면 모든 promise가 전부 받을때까지 모아주는 api이다. 그렇게 되면 fruits로 전달 받은 걸 join으로 합쳐준다면 원래 구하고자 했던 값인 🍎 + 🍌이 나오게 된다.

REFERENCE

드림코딩by 엘리 : https://www.youtube.com/watch?v=JB_yU6Oe2eE&t=1452s

profile
마음이 시키는 프론트엔드.. RN과 IOS를 곁들인..

0개의 댓글