코드스테이츠 7주차 / 비동기 Promise , async, await

support·2021년 12월 6일
0
post-thumbnail

✏️ Achievement Goals

✅ 어떤 경우에 중첩된 callback이 발생하는지 이해할 수 있다.
✅ 중첩된 callback의 단점, Promise의 장점을 이해할 수 있다.
✅ Promise 사용 패턴을 이해할 수 있다.
✅ resolve, reject의 의미와, then, catch와의 관계를 이해할 수 있다.
✅ Promise에서 인자를 넘기는 방법을 이해할 수 있다.
✅ Promise의 세 가지 상태를 이해할 수 있다.
✅ Promise.all 의 사용법을 이해할 수 있다.
✅ async/await keyword에 대해 이해하고, 작동 원리를 이해할 수 있다.
✅ Node.js의 fs 모듈의 사용법을 이해할 수 있다.

📝summary

자바스크립트는 동기식처리를 한다
그 반대 되는 개념은 비동기식 처리 이다
오늘은 비동기에 대해서 배워보자!

비동기식 처리란?
오래걸리는 작업을 만났을때 그 작업을 미뤄두고 다른 것부터 처리하는 방식

// 동기

console.log(1)
console.log(2)
console.log(3)
// 1 2 3 순서대로 출력되게 된다 

// 비동기
console.log(1)

setTimeout(()=> {console.log(2)}, 1000)
element.addEventListener('click', function(){})
// 비동기식 처리를 도와주는 함수

console.log(3)

코드를 순서대로 실행하다가 오래걸리는 코드를 만났을때 그 코드를 Web API 라는 공간으로 보낸다
코드가 해결이 되기를 (1초가 지나기를) 기다렸다가 다시 내보내며 실행한다
js는 오래걸리는 작업을 만나면 그 작업이 해결 될 때까지 그 자리에 머무르지만
Web API 덕분에 오래걸리는 작업이 있을 때 다른 것부터 처리하는 비동기식 처리가 가능하다

순차적으로 실행하고 싶다면?

콜백함수(함수안에 들어가는 함수)를 사용한다

함수1을 실행하고 2를 뒤에 실행하고 싶을 때 순서대로 쓴다고 해서 그렇게 실행되는건 아니다
함수1이 더 오래 걸리는 경우가 있을 수 있기 때문이다
이때 콜백함수를 사용해서 순서를 제어해 줄 수 있다

콜백함수는 함수 디자인 패턴일 뿐이고 js에서 비동기적으로 함수를 처리하고 싶다면
위의 settimeout 이나 클릭이벤트같은 문법을 써야 비동기적 처리가 가능하다

console.log(1);
setTimeout(function() {console.log(2)},1000)
addEventListener('click', function(){})

예)

function first(콜백){
  console.log(1) // 일단 먼저 실행
  콜백() // second 함수 실행
}

function second(){
  console.log(2)
}
first()
second()

first(second)
// 1, 2

콜백함수의 문제점

대체적으로 함수 이름을 짓지 않고 사용하기 때문에
콜백함수로 계속 사용하게 되면 코드가 길어지고 읽기가 힘들어 진다

first(function(){
  second(function(){
    third(function(){
    })
   })
 })

이때 사용할 수 있는게 promise 이다

📔 1. promise

new Promise() 문법으로 프로미스라는 변수 오브젝트를 하나 생성하고
프로미스라는 변수에 then(), catch()를 붙여서 실행 할 수 있다

let promise = new promise(function(resolve, reject){
  let sum = 1 + 1; // sum 연산이 끝난뒤 특정코드를 실행하고 싶을 때 사용방법
  resolve(sum) // 성공 -> then 실행
  // 위의 연산결과를 then 함수까지 전달이 가능하다 
  reject() // 실패 -> catch 실행
}); // 성공 , 실패 판정하는 기계 

promise.then(function(result){
  // 프로미스가 성공했을 경우 실행할 코드
  console.log(result) // 2
}).catch(function(){ 
  // 프로미스가 실패했을 경우 실행할 코드
})

promise.finally(function(){
  // 성공 or 실패 둘 중 아무거나 일어났을때 실행할 코드
})

1초후에 성공하는 promise
성공시 특정코드 실행

let promise = new promise(function(resolve, reject){
  setTimeout(function(){
    resolve();
  }, 1000);
}); 

promise.then(function(result){
  console.log('성공')
}).catch(function(){ 
  console.log('실패')
})

1. promise의 장점

  1. 코드가 옆으로 길어지지 않는다
  2. 순서 뿐만 아니라 성공, 실패 경우에 맞춰 다른 코드 실행가능

2. promise 특징 - 3가지 상태

프로미스를 하나 만든 뒤 출력해보면 태그박스안에 resolved가 있는 것을 확인 할 수 있다
promise에는 3가지 상태가 있다

pending 아직 성공 실패 판정을 안했을때
resolved 성공했을때
rejected 실패했을때

console.log(promise)
// promise { <resolved> : undefined }

3. promise 헷갈리는 상식

프로미스는비 동기처리가 가능하게 바꿔주는 문법이 아니라
안에서 비동기 처리가 가능한 함수를 쓸 수 있는 것이다
그냥 콜백함수 디자인의 대체품이다

📕 2. async

promise대신 쓸 수 있는 문법
async를 function앞에 붙이면 함수가 promise역할을 할 수 있다
함수 실행 후에 sum()자리에 promise 오브젝트가 남는다
그러면 그 자리에 promise와 같이 then을 사용 할 수 있다

단점은 성공했을때만 사용 할 수 있다

async function sum(콜백){
  return 1 + 1
  return promise.reject('실패')
  // 이런 방식으로 강제로 실패를 보내줄 수 있다
  // then 안의 것이 실행되지 않는다
}

sum().then(function(result){
  console.log('성공')
  console.log('result') // 2
})

📗 3. await

async function 안에서 await은 then 대신 사용 가능하다

async function sum (){
  let promise = new Promise(function(resolve,reject){
    let plus = 1 + 1
    resolve(100);
    reject(100);
  })

  try{
    let result = awail promise;
    // promise 가 해결 될 때까지 기다린다, 밑의 코드와 같은 역할을 한다
    console.log(result) // reslove - 100, reject - err
  } catch {
    console.log()
  }  
  // promise 실패시 에러가 나고 멈춘다 방지하기 위해서 try catch를 사용한다
  // try{먼저 실행후 에러가 나면} catch { 이부분을 실행해주세요 }
  
 // promise.then(function(){
 //   console.log(result)
 // });
  
}

0개의 댓글