자바스크립트에서 비동기 처리를 하기 위한 객체
비동기 작업이 맞이할 미래의 완료 또는 실패와 그 결과 값을 나타낸다
callback 패턴으로도 비동기 처리를 할 수 있는데 왜 굳이 promise를 사용할까🤔?
그 이유는 callback 패턴의 단점 때문이다
콜백지옥 (중첩으로 인한 가독성 저하)
callback이 중첩될 때마다 코드가 점점 안으로 들어가면서 닫는태그 }); 가 반복된다
이때 닫는태그와 여는태그의 한쌍을 한눈에 파악하기 어렵다
에러처리
callback 패턴은 하나하나 에러처리를 해줘야 한다
이러한 단점을 모두 보완한 것이 바로 Promise 이다!
사용해보자
let p = new Promise(function(resolve, reject) {
// 실행할 코드
});
// resolve(value) — 작업이 성공적으로 마무리되면 호출, 결과는 value에 담김
// reject(error) — 작업이 실패시 호출, error는 error에 담김
Promise를 생성하고 → new Promise( )
매개변수로 2개의 실행함수를 받는다 → (resolve, reject)
let p = new Promise(function(resolve, reject) {
resolve('hello world');
reject('ERROR!!!');
}).then(value => {
alert(value);
// 작업 성공시 실행 alert('hello world')
}).catch(error => {
alert(error);
// 작업 실패시 실행 alert('hello world')
});
작업이 성공한 경우 : resolve에 'hello world' 메세지가 담기고 then 코드로 넘어간다
작업이 실패한 경우 : reject에 'ERROR!!!' 메세지가 담기고 catch 코드로 넘어간다
작업 성공 | 작업 실패 |
---|---|
resolve | reject |
then | catch |
promise는 코드 분리가 가능하며 then을 자유롭게 사용할 수 있다
// 방법1
let p = new Promise(function(resolve, reject) {
resolve('hello world');
reject('ERROR!!!');
});
p.then((value) => {
alert(value)
}).catch((error) => {
alert(error)
});
// 방법2
let p = new Promise(function(resolve, reject) {
resolve('hello world');
reject('ERROR!!!');
});
p.then((value) => {
alert(value)
});
p.catch((error) => {
alert(error)
});
let p = new Promise(function(resolve, reject) {
resolve(10);
}).then(value => {
console.log(value); //10
return value + 10;
}).then(value => {
console.log(value); //20
return value + 20;
}).then(value => {
console.log(value); //40
return value + 30;
});
Q. 어떤 순서대로 어떻게 console창에 나타날까?
const promise = new Promise((resolve, reject) => {
setTimeout(() => {
resolve('작업 성공!');
}, 2000);
});
promise.then((value) => {
console.log('console1 : ', value); // 작업 성공!
});
console.log('console2 : ', promise);
정답
이유
Promise 코드를 살펴보면
setTimeout에 의해 2초가 지나야 '작업 성공!' 이라는 텍스트가 resolve에 담긴다
console1은 Promise 요청이 성공적으로 이루어졌을 때 실행되는 코드이기 때문에 2초뒤에 출력 된다
console2는 Promise가 아직 실행되지 않은 상태에서 출력되었기 때문에 PromiseState가 fulfilled(대기중) 상태인 것을 알 수 있다
때문에 console2가 먼저 출력되고, 2초가 지난 뒤 console1이 출력된다
병렬적으로 모든 Promise를 한번에 실행
성공하든 실패하든 모든 결과를 배열로 반환
주어진 Promise중에 제일 빨리 수행되는 것을 반환
ex)
function getApple(){
return new Promise((resolve)=>{
setTimeout(() => {
resolve('사과');
},1000);
});
};
function getOrange(){
return new Promise((resolve)=>{
setTimeout(() => {
resolve('오렌지');
},3000);
});
};
function getGrape(){
return Promise.reject(new Error('Grape is not find'));
};
// Promise.all()
Promise.all([getApple(), getOrange()])
.then((fruits) => console.log('Promise.all : ', fruits));
// Promise.all : ['사과', '오렌지']
// Promise.allSettled()
Promise.allSettled([getApple(), getOrange(), getGrape()])
.then((fruits) => console.log('Promise.allSettled : ', fruits))
.catch(console.log);
// all-settle : [
// { status: 'fulfilled', value: '사과' },
// { status: 'fulfilled', value: '오렌지' },
// {
// status: 'rejected',
// reason: Error: Grape is not find
// }
// ]
// Promise.race()
Promise.race([getApple(), getOrange()])
.then((fruit) => console.log('Promise.race : ', fruit));
// Promise.race : 사과
참고
https://developer.mozilla.org/ko/docs/Web/JavaScript/Reference/Global_Objects/Promise
https://developer.mozilla.org/ko/docs/Web/JavaScript/Reference/Global_Objects/Promise/Promise