728x90
Promise
- 원격에서 스크립트를 불러오는 것과 같이 시간이 걸리는 일을 비동기로 처리할 수 있도록 해주는 자바스크립트 객체.
구성
const promise = new Promise((resolve, reject) => {
// executor
});
new Promise
에 전달되는 함수는 executor(실행자, 실행 함수). 인자로 resolve와 reject를 받음.resolve(value)
- executor가 정상적으로 끝난 경우, 그 결과를 나타내는 value와 함께 호출reject(error)
- 에러 발생 시 에러 객체를 나타내는 error와 함께 호출
new Promise
생성자가 반환하는 promise 객체는 다음과 같은 내부 프로퍼티를 갖는다.
state
- pending(보류) 로 시작해서resolve
가 호출되면 fulfilled,reject
가 호출되면 rejected 로 변함.result
- undefined로 시작해서resolve
가 호출되면 value로,reject(error)
가 호출되면 error로 변함.
특징
- Promise는 반드시 resolve나 reject 중 하나를 호출해야한다. 만약 둘 중 하나가 호출된 상황이라면, 그 뒤에 코드는 무시된다.
- resolve나 reject는 인수를 최대 하나만 받고, 그 외의 인수는 무시한다.
then, catch, finally
1. then
const promise = new Promise((resolve, reject) => {
setTimeout(() => resolve("done!"), 1000);
});
// resolve 함수는 .then의 첫 번째 함수(인수)를 실행합니다.
promise.then(
result => alert(result), // 1초 후 "done!"을 출력
error => alert(error) // 실행되지 않음
);
.then
의 첫 번째 인수는 resolve
로 Promise가 정상적으로 수행되었을 때 실행되는 함수이고, 두 번째 인수는 reject
의 역할을 한다.
작업이 성공적으로 처리된 경우만 다루고 싶다면 .then
에 인수를 하나만 전달하면 된다.
2. catch
에러가 발생한 경우만 다루고 싶다면 .then(null, errorHandlingFunction)
과 같이 null 을 첫 번째 인수로 전달하면 된다. .catch(errorHandlingFunction)
은 위의 방법과 동일하게 에러가 발생한 경우만 다룰 수 있게 해주는 내부 메서드이다.
let promise = new Promise((resolve, reject) => {
setTimeout(() => reject(new Error("에러 발생!")), 1000);
});
// .catch(f)는 promise.then(null, f)과 동일하게 작동합니다
promise.catch(alert); // 1초 뒤 "Error: 에러 발생!" 출력
3. finally
try {...} catch {...}
에 finally 절이 있는 것처럼, Promise에도 finally
가 있다. Promise는 처리 후에 반드시 resolve 혹은 reject가 실행된다는 점에서 .finally(f)
의 호출은 .then(f, f)
와 유사하지만, 완전히 같지는 않다.
finally
핸들러에는 인수가 없다. finally에서는 Promise가 이행되었는지 거부되었는지 알 수 없다. 그래서 보통 절차를 마무리하는 '보편적' 동작을 수행한다.finally
핸들러는 자동으로 다음 핸들러에 결과와 에러를 전달한다.
new Promise((resolve, reject) => {
setTimeout(() => resolve("결과"), 2000)
})
.finally(() => alert("프라미스가 준비되었습니다."))
.then(result => alert(result)); // <-- .then에서 result를 다룰 수 있음
new Promise((resolve, reject) => {
throw new Error("에러 발생!");
})
.finally(() => alert("프라미스가 준비되었습니다."))
.catch(err => alert(err)); // <-- .catch에서 에러 객체를 다룰 수 있음
콜백과의 차이점
- 프라미스
- 코드의 흐름이 자연스럽다.
- 원하는 만큼
.then
을 호출할 수 있다.
- 콜백
- 콜백을 사용하는 함수가 있을 경우, 콜백이 먼저 준비되어 있어야 한다. 따라서 해당 함수가 호출하기 이전에 호출 결과로 무엇을 할지, 그리고 콜백이 어떻게 동작하는지 미리 알고 있어야 한다.
- 콜백은 하나만 호출이 가능하다.
728x90
댓글