한 작업이 완전히 끝나야 다음 작업으로 넘어갑니다.
순차적, 직렬적 테스크를 수행합니다.
JavaScript는 동기식 언어입니다. (싱글 스레드)
한 작업이 끝나지 않고 다음 작업으로 넘어갑니다.
병렬적 테스크를 수행합니다.
Ex) setTimeout, ajax
/* setTimeout */
console.log('1');
setTimeout(function() {
console.log('2')
}, 3000);
console.log('3')
// 1->3->2 순으로 출력
/* ajax */
function getData() {
var tableData;
$.get('url', (response)=> {
tableData = response;
})
// $.get()로 데이터를 요청하고 받아올 때까지 기다리지 않고 return
return tableData;
}
console.log(tableData) // 따라서 undefined
위와 같이 비동기처리를 하면 비동기로 받아온 데이터를 처리하는데 문제가 발생할 수 있습니다. 이를 해결하기 위한 방법에는 어떤 것들이 있을까요?
함수 안에서 어떤 특정한 시점에 호출되는 함수입니다.
아래 예시처럼 하나의 콜백 함수만 호출하는 경우 문제없지만, 계속해서 호출하면 콜백 지옥에 빠질 수 있습니다.
function getData(callback) {
$.get('url', (response)=> {
callback(response) // calllback 함수에 인자 response 넘겨줌
})
}
getData(function (tableData) {
console.log(tableData)
}) // callback
Promise의 상태 및 처리 흐름
Promise 메서드
// 프로미스의 생성 방법은 new Promise((resolve, reject){...}) 로 생성하는 방법
function getData(callback) {
return new Promise((resolve, reject)=> {
$.get('~ api url 주소 ~', (response)=> {
if(response){
resolve(response); //비동기 처리 성공
}else{
reject(new Error('fail')); //비동기 처리 실패
}
});
});
}
// resolve 시 then 메소드, reject 시 catch 메소드의 인자로 넘어간다.
// finally()는 실패, 성공 상관 없이 무조건 실행되는 함수이다.
getData().then((tableData)=> {
console.log(tableData);
})
.catch((err)=> {
console.log(err)
})
.finally((final)=> {
console.log('finally')
});
// .all() 예제
let p1 = new Promise((resolve, reject){...})
let p2 = new Promise((resolve, reject){...})
Promise.all([p1,p2]).then( (values) =>{
console.log('모두 완료');
})
funcion 키워드 앞에 async를 붙여주고, 함수 내부의 promise를 반환하는 비동기 처리 함수 앞에 await을 붙여 호출합니다.
Promise가 처리될 때까지 기다렸다가 다음 로직을 수행합니다.
/*기본 문법
async function 함수명() {
await 비동기_처리_메서드_명();
}
*/
function getData(callback) {
return new Promise((resolve, reject)=> {
$.get('~ api url 주소 ~', (response)=> {
resolve(response);
});
});
}
async function callData() {
try{
let result = await getData(); // promise 결과를 기다림
console.log(result)
}catch(error){
console.log(error)
}
}