Promise
비동기의 시작
우선 우리는 자바스크립트가 하나의 Call Stack을 가지고 있어 싱글 스레드 인 것을 알고 있다. 그래서 코드를 순차적으로 처리를 하게 되는 동기식 언어이다. 하지만 Callback Queue와 Event Loop을 활용을 하여 비동기식 처리를 할 수 있는 것을 알게 되었다. 비동기를 처리하는 객체들이 여러가지 있지만 그중 Promise 객체에 대해 알아보려 한다.
자바스크립트의 비동기 처리를 알아보자면 특정 코드의 연산이 끝날 때까지 코드의 실행을 멈추지 않고 다음 코드를 먼저 실행하는 자바스크립트의 특성을 의미한다.
즉, Call Stack에 비동기 처리의 컨텍스트가 담겨져 있다면, Web API에 보내 ‘난 다른 컨텍스트를 처리할 태니 너는 이걸 처리해줘’ 라고 보내주고, Call Stack은 다른 컨텍스트를 처리한다.
그동안 Web API는 Call Stack에서 받은 컨텍스트를 처리를 한 뒤, 처리한 컨텍스트의 콜백 함수를 Callback Queue에 보낸다. 이때 바로 처리를 완료한 콜백 함수를 Call Stack에 보내지 않는다. 그 이유는 단일 스레드 언어라는 것을 보장해주기 위해서 이다. 그래서 Event Loop가 Call Stack이 다 비워졌는지 확인을 한 뒤 콜백 함수를 Call Stack에 보내는 과정이다.
Promise의 객체
Promise와 같은 비동기 처리는 주로 fetch, ajax와 같은 서버에 네트워크 요청을 보낼때 많이 사용한다.
프로미스는 3가지의 상태로 되어있다. 상태는 프로미스의 처리 과정을 의미한다.
- Pending(대기) : 비동기 처리 로직이 아직 완료되지 않은 상태
- Fulfiled(이행) : 비동기 처리가 완료되어 프로미스가 결과 값을 반환해준 상태
- Rejected(실패) : 비동기 처리가 실패하거나 오류가 발생한 상태
그래서 Promise는 마치 ‘내가 이 코드를 실행 시켜줄게 성공하면 resolve로 처리 해주고, 실패하면 reject로 처리 해줄게 사용 하려면 불러줘’와 같다.
프로미스 생성
프로미스를 생성할 때에는, Class를 생성 하듯이 new를 붙여 사용한다.
new Promise();
이때, 프로미스의 상태는 대기(Pending) 상태가 된다.
Pending(대기)
아직 프로미스를 처리하지 않은 상태이다. 이때 콜백 함수로 resolve와 reject를 사용할 수 있다.
new Promise((resolve, reject) => {
///
});
Fulfilled(이행)
여기서 콜백 함수의 인자 resolve를 아래와 같이 실행하면 이행(Fulfilled) 상태가 된다.
new Promise((resolve, reject) => {
resolve();
});
// Promise {<fulfilled>: undefined}
그렇다면 결과 값을 어떻게 받을 수 있을까? then()을 이용하여 결과값을 받을 수 있다.
function Add(num1, num2) {
const result = num1 + num2;
return new Promise((resolve, reject) => {
if (result) {
resolve(result);
}
});
}
Add(1, 3).then((result) => console.log(result));
// 4
Rejected(실패)
reject를 호출을 한다면 실패(Rejected) 상태가 된다.
new Promise((resolve, reject) => {
reject();
});
// Promise {<rejected>: undefined}
실패 상태가 되면 실패한 결과 값을 catch()로 받을 수 있다.
function Add(num1, num2) {
const result = num1 + num2;
return new Promise((resolve, reject) => {
if (result) {
resolve(result);
} else {
reject(err);
}
});
}
Add(1)
.then((result) => console.log(result))
.catch((err) => console.log(err));
// Fail
프로미스의 동작 방식을 사진으로 알아보자면 이렇게 동작을 한다.
- Add 함수에 전달 인자로 1, 3을 보낸다.
- 변수 result에 1 과 3의 합이 담긴다.
- 콜백 함수로 프로미스가 반환이 된다.
-
이때 프로미스의 성공과 실패에 따라 다르게 실행이 된다.
- 성공 성공 한다면(result의 값이 존재가 한다면) resolve 함수를 반환한다.
- 실패 실패 한다면(result의 값이 존재하지 않으면) reject 함수를 반환한다.
- 성공 시 함수 호출 코드에서 then() 구문으로 resolve의 결과값을 받을 수 있다.
- 실패 시 함수 호출 코드에서 catch() 구문으로 reject의 결과값을 받을 수 있다.
Promise의 단점
프로미스는 콜백 지옥을 벗어나기 위해 나온 등장한 비동기 객체이다. 하지만 이 프로미스도 결국 then과 catch로 프로미스의 결과값을 얻어내야 함으로 코드가 복잡 해질 수 있다.
이를 개선하기 위해 async / await 방식이 나타났다. 다음 시간에 알아보도록 하자.
댓글남기기