본문 바로가기

JavaScript

JavaScript의 async/await, Promise의 개념

async/await 함수와 Promise, then에 관한 정리



var result=0;

function myReturnPromise(){
	return new Promise((res)=>{
		setTimeout(()=>{
			console.log(2);
			res();
		}, 3000)
})
}

async function myWait(x){
	await myReturnPromise();
	//myWaitPromise()->동시동작 되어버림
	return new Promise((resolve)=>{
		setTimeout(()=>{
			console.log(3);
			resolve();
		}, 3000)
	});
}

async function test2(){
	console.log(1);
	await myWait();
	console.log(4);
}

test2();

  • myWaitPromise 가 Promise가 아닌 일반 값을 리턴하면 myWait에서 await myReturnPromise()를 실행해도
    blocking 되지 않음


  • async function는 동시 작업을 할 수 있지만, 작업의 시작순서는 우리가 코드를 짠 대로임(완료 후 실행하는 게 아닐뿐)
     - await을 이용해서는 완료후 실행하게 할 수 있다.
     - async function이 아닌 일반 function은 callback을 이용해야 완료 후 실행을 명령할 수 있다. 

  • myWait에서
    await myReturnPromise()가 아닌
    그냥 myReturnPromise() 시에는
    myReturnPromise()의 Promise가 완전한 값으로 변화하기 전에 myWait의 return이 시작됨.
    ( 즉 3초후 2가 출력되고 3초후 3을 출력하는 것이 아니라
     3초후 2와 3이 같이 출력됨 )




//함수를 순차적으로 실행하고 완료하고 실행하고하면
//1, 2, 3, 4 순으로 출력되어야하고
//함수를 시작은 순서대로 하되, 작업은 백그라운드에 넘기면
//역순으로 출력됨

function showNum(i){
	return new Promise((res)=>{
		setTimeout(function(){
			res(console.log(i));
		}, 300*10-i*100);
	});
}

async function loop(){
    console.log('simultaneous Loop');	
	await completingLoop();	
	//or
	console.log('ordered Loop');
	for(var i=0; i<30; i++){
		await showNum(i);
    }
	console.log('finished')
}

function completingLoop(){
    var tasks=[];
	for(var i=0; i<30; i++){
		tasks.push(showNum(i));
	}
	
	return Promise.all(tasks);
}


loop();

반복문 안의 내용은 동시적으로 진행하고 반복문 밖의 내용은 순차적으로(반복문 내용 종료 후에) 진행하고 싶을 때

( ex. 여러 링크에서 이미지 다운로드는 병렬적으로 진행하되, 다운이 모두 완료되면 어떠한 작업을 수행하고 싶을 때)

위 코드의 simultaneous loop처럼 정의하면 된다.

모듈없이는 우선 for문은 함수가 아니기 때문에, await를 붙일 수 없다. 애초에 Promise를 리턴하지도 않는다.

따라서 반복문의 작업이 모두 끝났을 때 Promise를 return해줄 수 있는 function을 정의해주어야한다.

그리고 반복문 안의 내용들이 각각 끝났는지 알 수 있도록 for문 안의 실행문들도 Promise를 리턴해야하고

Promise.all을 이용해 또 다른 Promise를 리턴해주면 된다.