본문 바로가기
JavaScript

[JavaScript] Promise

by oagree0123 2021. 9. 6.

이전 글에서 비동기 처리를 위해 콜백 함수를 사용했습니다. 그런데 콜백 함수를 사용하면 비동기 처리 작업이 많아질 수록 코드가 복잡해지는 것을 볼 수 있었습니다. 이번에는 이를 해결하는 Promise 사용법에 대해 알아보겠습니다.

 

[JavaScript] 비동기 처리

아래의 그림을 보면 동기적 처리와 비동기적 처리를 간단하게 확인할 수 있습니다. 대충 이해가 가시나요? 그림만 보고 정확하게 이해하기는 힘드니 어떤 상황에 사용하는지 어떤 의미인지 알

oagree0123.tistory.com


1. Promise

Promise는 자바스크립트에서 비동기 처리를 위해 사용되는 객체입니다. Promise는 성공을 할 수도 있고, 실패를 할 수도 있습니다. 성공을 하면 resolve를 호출하고, 실패하면 reject를 호출합니다.

 

프로미스 생성, 실행

먼저 Promise를 생성하고 실행하는 예제 코드를 보겠습니다. 

// 프로미스 생성
const testPromise = function(param) {
	return new Promise(function(resolve, reject){
    	if(param){
        	resolve("성공");
        }
        else {
        	reject("실패");
        }
    });
}

// 프로미스 실행
testPromise(true)  // true or false
.then(function(result){
	console.log(result); // 성공
})
.catch(function(err) {
	console.log(err); // 실패
});

new로 Promise 객체를 생성하고, resolve(), reject() 함수로 Promise를 생성합니다. Promise를 실행하는 부분에는 then(), catch() 함수가 있습니다. 아래에서는 각각 어떤 역할을 하는지 보겠습니다.

 

2. Promise의 상태

Promise에는 3가지 상태가 있는데 이는 Promise의 처리 과정을 의미합니다. 위 코드를 세부적으로 나눠 상태를 확인해 보겠습니다.

 

Pending (대기) 비동기 처리 로직을 아직 수행하는 상태
Fulfilled (이행) 비동기 처리 로직이 완료되어 값을 반환한 상태
Rejected (실패) 비동기 처리가 어떠한 이유에서 실패한 상태

 

Pending (대기)

new Promise()로 객체를 생성하게 되면 맨 처음 대기 상태가 되고, resolve와 reject를 파라미터로 받는 익명함수를 사용합니다.

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

Fulfilled (이행)

익명 함수의 resolve를 실행하여 결과를 받게되면 Fulfilled 상태가 됩니다.


const testPromise = function(param) {
	return new Promise(function(resolve, reject){
    	if(param){
        	resolve("성공");
        }
        else {
        	reject("실패");
        }
    });
}

testPromise(true).then(function(result){
	console.log(result); // 성공
});

Rejected (실패)

익명 함수의 reject를 실행하여 어떠한 이유로 실패하게 되는 상태입니다.

const testPromise = function(param) {
	return new Promise(function(resolve, reject){
    	if(param){
        	resolve("성공");
        }
        else {
        	reject("실패");
        }
    });
}

testPromise(false)  
.then(function(result){
	console.log(result); // 성공
})
.catch(function(err) {
	console.log(err); // 실패
});

전체적인 프로세스를 설명하면, Promise를 생성하는 부분을 보면 함수를 사용하여 Promise 객체를 리턴하고,  Promise 객체는 익명함수를 파라미터로 가지며, 익명 함수는 resolve와 reject를 파라미터로 받고 있는 형태 입니다. 이때 param으로 true 나 false가 오게 되는데 성공하면 resolve를 실행, 실패하면 reject를 실행하게 됩니다.

 

아래의 그림은 Promise의 상태와 프로세스를 그림으로 나타낸 것입니다.

출처 : MDN Web Docs

 

3. Promise 체이닝

Promise는 여러 개를 연결하여 사용할 수 있다는 특징을 가집니다. then() 내부에 Promise를 다시 리턴하게 된다면 연달아 사용되는 것을 볼 수 있습니다. setTimeout()을 사용하여 결과를 확인해 보겠습니다.

function testPromise(param) {
	return new Promise(function(resolve, reject){
    	setTimeout(function() {
        	var result = param + 1;

            if(param === 3){
        		reject("초과");
        		return;
        	}
            console.log(result);
            resolve(result);
        }, 1000);
    });
}

testPromise(0)  
.then(function(param){
	return testPromise(param);
})
.then(function(param){
	return testPromise(param);
})
.then(function(param){
	return testPromise(param);
})
.catch(function(err) {
	console.log(err);
});

조금 더 정리하면 아래와 같이 작성할 수 있습니다.

function testPromise(param) {
	return new Promise(function(resolve, reject){
    	setTimeout(function() {
        	var result = param + 1;

            if(param === 3){
        		reject("초과");
        		return;
        	}
            console.log(result);
            resolve(result);
        }, 1000);
    });
}

testPromise(0)  
.then(testPromise)
.then(testPromise)
.then(testPromise)
.catch(function(err) {
	console.log(err);
});

Promise를 사용하여 여러 개의 비동기 처리를 복잡하지 않은 방법으로 작성하는 것을 알아보았습니다. 

 

그러나, Promise는 에러가 어디서 발생했는지 알기 힘들고, 특정 값을 공유하기가 힘들다는 단점을 가집니다. 이에 대해 async / awati을 사용하여 문제점을 해결할 수 있습니다.

'JavaScript' 카테고리의 다른 글

[JavaScript] 스코프 (Scope)  (0) 2021.09.08
[JavaScript] async/await  (0) 2021.09.06
[JavaScript] 비동기 처리  (0) 2021.09.03
[JavaScript] 콜백 함수 (Callback Function)  (0) 2021.09.03
[JavaScript] this  (0) 2021.09.03

댓글