ABOUT ME

-

Today
-
Yesterday
-
Total
-
  • Asynchronous & Promise
    Note 2020. 11. 10. 21:48

    동기(synchronous)와 비동기(Asynchronous)

    커피 주문의 예제로 알아보는 동기와 비동기의 차이

    출처: PoiemaWeb

     

     

    커피숍의 대기열에 줄을 서 있는 손님이라고 생각해보자. 앞 손님이 커피를 주문하고, 주문한 커피를 받을 때까지, 줄에 서 있는 손님은 주문조차 할 수 없다면 그 커피숍은 가지 않을 것이다. 이를 blocking이라고 부른다. 동기적(a)인 작업에 따라 이후 작업이 "막히게 된 것"을 말한다. 반면 비동기적(b)인 작업은 앞 손님이 커피를 주문하고, 주문한 커피를 받기 전에도 이후에 온 손님이 주문을 할 수 있는 것을 말한다. 앞에 작업이 처리되지 않더라도 그 이후 작업들이 처리될 수 있는 것을 말하는 것이다.

     

    동기(synchronous)

    동기는 요청을 보낸 후 응답을 받아야 다음 동작이 이루어지는 방식.

    모든 일은 순차적으로 실행이 되고 어떤 작업이 실행 중이면 다음 작업은 대기하게 된다.

     

    비동기(Asynchronous)

    서버로부터 데이터를 받아오는 앱을 만든다고 하면, 서버에서 데이터를 받아 처리해야 할 것이다. 하지만 비동기로 처리하지 않고 동기적으로 이를 처리한다면 데이터를 받아오기까지 기다린 다음에 앱이 실행이 될 것이고 서버에서 가져오는 데이터의 양이 늘어나면 늘어날수록 앱의 속도는 느려지게 되는 것이다. 데이터를 가져오기까지 앱이 대기하는 상태가 되는 것이다. 이런 사용자들의 불편함을 없애기 위해 데이터를 수신하는 코드와 페이지를 표시하는 것 등을 비동기적으로 처리해야 하는 것이다. 

     

    Promise

    프로미스는 자바스크립트 비동기 처리에 사용되는 객체이다. 비동기 작업이 맞이할 미래의 완료 또는 실패와 그 결과 값을 나타낸다.

     

    Promise states

    • pending(대기): 이행하거나 거부되지 않은 초기 상태

    • fulfilled(이행): 연산이 성공적으로 완료된 상태

    • rejected(거부): 연산이 실패한 상태

     

    Pending(대기)

    아래와 같이 메서드를 호출하면 대기 상태가 된다.

    new Promise()

     

    메서드를 호출할 때 콜백 함수를 선언할 수 있고, 콜백 함수의 인자는 resolve, reject이다.

    new Promise(function(resolve, reject) {
     ..
     
     ..
    })

     

    Fulfilled(이행)

    콜백 함수의 인자를 실행하면 이행 상태가 된다.

    new Promise(function(resolve, reject) {
      resolve()
    })

    이행 상태가 되면 then()을 사용하여 결과 값을 받을 수 있다.

    const lucky = () => {
      return new Promise(function(resolve, reject) {
        let number = 77
        resolve(number)
      })
    }
    
    lucky().then((luckyNumber) => {
      console.log(luckyNumber) 
    })
    
    
    77
    
    Promise {<fulfilled>: undefined}

     

    Rejected(거부)

    프로미스 객체를 생성하고 콜백 함수 인자로 reject를 호출하면 거부 상태가 된다.

    new Promise(function(resolve, reject) {
      reject()
    })

    거부 상태가 되면 거부된 이유를 catch()로 받을 수 있다.

    const lucky = () => {
      return new Promise(function(resolve, reject) {
        reject(new Error("failed!!!"))
      })
    }
    
    lucky().then().catch((error) => { 
      console.log(error) 
    })
    
    
    Error: failed!!!
        at <anonymous>:3:12
        at new Promise (<anonymous>)
        at lucky (<anonymous>:2:10)
        at <anonymous>:7:1
        
    Promise {<fulfilled>: undefined}

     

    Promise.all

    순회 가능한 객체에 주어진 모든 프로미스가 이행한 후 Promise를 반환한다.

    const promise1 = Promise.resolve(22);
    const promise2 = 33;
    const promise3 = new Promise((resolve, reject) => {
      setTimeout(resolve, 500, 'hello');
    });
    
    Promise.all([promise1, promise2, promise3]).then((value) => {
      console.log(value);
    });
    
    
    (3) [22, 33, "hello"]

     

    aync / await

    함수 정의 앞에 async 키워드를 사용하면 함수 내에 await를 사용할 수 있다. 프로미스를 await 할 때 함수는 프로미스가 결정될 때까지 방해하지 않는 방식으로 일시 중지된다. 프로미스가 이행되면 값을 돌려받고, 프로미스가 거부되면 거부된 값이 반환된다. 프로미스에 익숙하지 않은 사람으로서는 훨씬 더 읽기 쉬워진다.

    function lucky() {
      return new Promise(function(resolve, reject) {
        let number = [77]
        resolve(number)
      });
    }
    
    async function luckyNumber() {
      let result = await lucky()
      console.log(result)
    }
    
    
    luckyNumber()
    [77]
    Promise {<fulfilled>: undefined}

     

    URL을 가져와서 응답을 텍스트로 로그 하려는 경우

     

    1) 프로미스를 사용하는 방법

    function logFetch(url) {
      return fetch(url)
        .then(response => response.text())
        .then(text => {
          console.log(text);
        }).catch(err => {
          console.error('fetch failed', err);
        });
    }

     

    2) 비동기 함수를 사용하는 방법

    async function logFetch(url) {
      try {
        let response = await fetch(url);
        console.log(await response.text());
      }
      catch (err) {
        console.log('fetch failed', err);
      }
    }

    'Note' 카테고리의 다른 글

    node.js, module  (0) 2020.11.16
    HTTP 프로토콜  (0) 2020.11.12
    Ajax, SPA  (0) 2020.11.09
    undefined, null, undeclared  (0) 2020.10.29
    OOP(Object Oriented Programming)  (0) 2020.10.28

    댓글