โœ๐Ÿป [Code Camp_TIL] 30์ผ์ฐจ: Callback ํ•จ์ˆ˜, callback-promise-async/await, ๋งคํฌ๋กœ ํƒœ์Šคํฌ ํ & ๋งˆ์ดํฌ๋กœ ํƒœ์Šคํฌ ํ, await์™€ ๋งˆ์ดํฌ๋กœ ํ์˜ ๊ด€๊ณ„

code_Jยท2023๋…„ 5์›” 1์ผ
0

TIL

๋ชฉ๋ก ๋ณด๊ธฐ
37/41
post-thumbnail

Callback ํ•จ์ˆ˜


Callback ํ•จ์ˆ˜๋ž€

function aaa(qqq){
	// ํ•จ์ˆ˜ ๋กœ์ง
}

aaa(function(){})

์šฐ๋ฆฌ๋Š” ํ•จ์ˆ˜๋„ ์ธ์ž๋กœ ์ „๋‹ฌํ•  ์ˆ˜ ์žˆ๋‹ค. ์—ฌ๊ธฐ์„œ ์ธ์ž๋กœ ์ „๋‹ฌ๋˜๋Š” ํ•จ์ˆ˜๋ฅผ callback ํ•จ์ˆ˜๋ผ๊ณ  ํ•œ๋‹ค. ์œ„ ์ฝ”๋“œ์—์„œ function(){}์ด callback ํ•จ์ˆ˜๋‹ค.


["์ฒ ์ˆ˜", "์˜ํฌ", "ํ›ˆ์ด"]. map((el) => {})

map ๊ด„ํ˜ธ ์•ˆ์—๋„ ํ™”์‚ดํ‘œ ํ•จ์ˆ˜ ํ˜•ํƒœ์˜ callback ํ•จ์ˆ˜๊ฐ€ ์กด์žฌํ•œ๋‹ค!


Callback ํ•จ์ˆ˜๋ฅผ ์“ฐ๋Š” ์ด์œ 


๊ทธ๋ ‡๋‹ค๋ฉด ์™œ callback ํ•จ์ˆ˜๋ฅผ ์‚ฌ์šฉํ•˜๋Š” ๊ฑธ๊นŒ?

async/await ๋‚˜์˜ค๊ธฐ ์ „์—๋Š”, api ์š”์ฒญ์ด ๋๋‚˜๋ฉด ๊ทธ ๊ฒฐ๊ณผ๊ฐ’์„ ๊ฐ€์ง€๊ณ  ๋‹ค๋ฅธ ์š”์ฒญ์„ ์‹คํ–‰์‹œํ‚ค๊ธฐ ์œ„ํ•ด callback ํ•จ์ˆ˜๋ฅผ ์“ฐ๊ณค ํ–ˆ๋‹ค.

function aaa(qqq){
	// ์™ธ๋ถ€ API์— ๋ฐ์ดํ„ฐ ์š”์ฒญํ•˜๋Š” ๋กœ์ง
	// ...
	// ...
	// ์š”์ฒญ ๋!
	const result = "์š”์ฒญ์œผ๋กœ ๋ฐ›์•„์˜จ ๋ฐ์ดํ„ฐ ๊ฒฐ๊ณผ๊ฐ’"
	qqq(result) // ์š”์ฒญ ๋๋‚˜๋ฉด qqq ์‹คํ–‰์‹œํ‚ค๊ธฐ
}

aaa(result) => {
	console.log("์š”์ฒญ์ด ๋๋‚ฌ์Šต๋‹ˆ๋‹ค.")
	console.log("์š”์ฒญ์œผ๋กœ ๋ฐ›์•„์˜จ ๋ฐ์ดํ„ฐ๋Š”" + result + "์ž…๋‹ˆ๋‹ค")
}

์šฐ๋ฆฌ๋Š” ์ด๋ฏธ async/await๋ฅผ ์ต์ˆ™ํ•˜๊ฒŒ ์“ฐ๊ณ  ์žˆ์ง€๋งŒ, ๋‹ค์–‘ํ•œ ์ž๋ฐ”์Šคํฌ๋ฆฝํŠธ ๋น„๋™๊ธฐ ์ฒ˜๋ฆฌ ๋ฐฉ๋ฒ•์„ ์•Œ๊ณ  ์‚ฌ์šฉํ•˜๋Š” ๊ฒƒ๋„ ์ค‘์š”ํ•˜๋‹ค.


๋น„๋™๊ธฐ ์‹ค์Šต(callback-promise-async/await)


Callback

<!DOCTYPE html>
<html lang="en">
	<head>
		<title> ์ฝœ๋ฐฑ๊ณผ ์นœ๊ตฌ๋“ค </title>
		<script>
			const myCallback = ()=>{
				// 1.๋žœ๋คํ•œ ์ˆซ์ž๋ฅผ ๊ฐ€์ง€๊ณ  ์˜ค๋Š” API
				// 2.posts/๋žœ๋ค์ˆซ์ž
				// 3.๋žœ๋ค์ˆซ์ž ๋ฒˆ ๊ฒŒ์‹œ๊ธ€ ์ž‘์„ฑํ•œ ์œ ์ €๊ฐ€ ์“ด ๋‹ค๋ฅธ ๊ธ€
			}
			const myPromise = ()=>{

			}
			const myAsyncAwait = ()=>{

			}

		</script>
	</head>
	<body>
			<button onclick={onClickCallback}>Callback ์š”์ฒญํ•˜๊ธฐ</button>
      <button onclick={onClickPromise}>Promise ์š”์ฒญํ•˜๊ธฐ</button>
      <button onclick={onClickAsyncAwait}>AsyncAwait ์š”์ฒญํ•˜๊ธฐ</button>
	</body>
</html>

์œ„์— myCallback ํ•จ์ˆ˜ ๋‚ด๋ถ€์—์„œ๋Š” 1๋ฒˆ ๋กœ์ง์„ ์™„๋ฃŒํ•œ ํ›„ ๋ฐ›์•„์˜จ ๋ฐ์ดํ„ฐ๋ฅผ ๊ธฐ๋ฐ˜์œผ๋กœ 2๋ฒˆ ๋กœ์ง์„ ๊ทธ๋ฆฌ๊ณ , 2๋ฒˆ ๋กœ์ง ์™„๋ฃŒ ํ›„ ๋ฐ›์•„์˜จ ๋ฐ์ดํ„ฐ๋ฅผ ๊ธฐ๋ฐ˜์œผ๋กœ 3๋ฒˆ ๋กœ์ง์„ ์‹คํ–‰ํ•œ๋‹ค.


nyCallback ํ•จ์ˆ˜๋Š” ๋‹ค์Œ๊ณผ ๊ฐ™์ด ์ ์–ด์ค„ ์ˆ˜ ์žˆ๋‹ค.

const myCallback = ()=>{
// newXMLHTTPRequest๋Š” ์ž๋ฐ”์Šคํฌ๋ฆฝํŠธ์— ๋‚ด์žฅ๋˜์–ด์žˆ๋Š” ๊ธฐ๋Šฅ
	const aa = newXMLHTTPRequest()
	aa.open("get",`http://numbersapi.com/random?min=1&max=200`)
	aa.send()
	aa.addEventListener("load",function(res){
		console.log(res)
	})
}

XMLHttpRequest๋Š” ์„œ๋ฒ„์™€ ์ƒํ˜ธ ์ž‘์šฉํ•˜๊ธฐ ์œ„ํ•ด ์‚ฌ์šฉ๋˜๋Š” ๊ฐ์ฒด๋‹ค. ์ „์ฒด ํŽ˜์ด์ง€์˜ ์ƒˆ๋กœ๊ณ ์นจ ์—†์ด๋„ URL๋กœ๋ถ€ํ„ฐ ๋ฐ์ดํ„ฐ๋ฅผ ๋ฐ›์•„์˜ฌ ์ˆ˜ ์žˆ๋‹ค. Ajax ํ”„๋กœ๊ทธ๋ž˜๋ฐ์— ์ฃผ๋กœ ์‚ฌ์šฉ๋˜๊ณ , XHR์ด๋ผ๊ณ  ์ค„์—ฌ ๋ถ€๋ฅด๊ธฐ๋„ ํ•œ๋‹ค.


์ฒซ ๋ฒˆ์งธ์˜ response(res)๋ฅผ ๊ฐ€๊ณตํ•ด์„œ ๋‘ ๋ฒˆ์งธ API ์š”์ฒญ์„ ๋ณด๋‚ด๋ ค๋ฉด ๋‹ค์Œ๊ณผ ๊ฐ™์ด ์ฝ”๋“œ๋ฅผ ์ž‘์„ฑํ•˜๋ฉด ๋œ๋‹ค.

const myCallback = () => {
  const aa = new XMLHttpRequest();
  aa.open("get", "http://numbersapi.com/random?min=1&max=200");
  aa.send();
  aa.addEventListener("load", (res: any) => {
    const num = res.target.response.split(" ")[0]; // ๋žœ๋ค ์ˆ˜ ์ถ”์ถœ

		// ๋‘๋ฒˆ์งธ api ์š”์ฒญ
    const bb = new XMLHttpRequest();
    bb.open("get",            `https://koreanjson.com/posts/${num}`);
    // num์— ์ถ”์ถœํ•œ ๋žœ๋ค ์ˆ˜๊ฐ€ ๋“ค์–ด๊ฐ
    bb.send();
    bb.addEventListener("load", (res: any) => {
     console.log(res)
		 const userId = JSON.parse(res.target.response).UserId 
    });
  });
};

console์„ ํ†ตํ•ด ๋žœ๋ค ์ˆ˜์— ํ•ด๋‹นํ•˜๋Š” ๊ฒŒ์‹œ๊ธ€ ๋ฐ์ดํ„ฐ๊ฐ€ res์— ๋“ค์–ด์˜จ ๊ฒƒ์„ ํ™•์ธํ•  ์ˆ˜ ์žˆ๋‹ค. ํ•˜์ง€๋งŒ ์‘๋‹ต๋ฐ›์€ ๋ฐ์ดํ„ฐ๋Š” ๋ฌธ์ž์—ด๋กœ ๋˜์–ด์žˆ์–ด์„œ ๊ฐ€๊ณต ๋ฐ ํ™œ์šฉ์ด ์–ด๋ ต๋‹ค.

JSON.parse()๋ฅผ ์ด์šฉํ•ด์„œ ๋ฌธ์ž์—ด์„ ๊ฐ์ฒด๋กœ ๋ฐ”๊ฟ”์ฃผ๊ณ , ํ•ด๋‹น ๋ฐ์ดํ„ฐ์˜ ์ž‘์„ฑ์ž ์ •๋ณด(UserId)๋ฅผ ์ด์šฉํ•ด์„œ ์„ธ ๋ฒˆ์งธ ์š”์ฒญ์„ ๋ณด๋‚ด์ค€๋‹ค.

const onClickCallback = () => {
	// ์ฒซ๋ฒˆ์งธ ๋žœ๋ค์ˆซ์ž api ์š”์ฒญ
  const aaa = new XMLHttpRequest();
  aa.open("get", "http://numbersapi.com/random?min=1&max=200");
  aa.send();
  aa.addEventListener("load", (res: any) => {
    const num = res.target.response.split(" ")[0];

		 // ๋‘๋ฒˆ์งธ posts api ์š”์ฒญ
	   const bbb = new XMLHttpRequest();
			bb.open("get", `https://koreanjson.com/posts/${num}`);
	    bb.send();
	    bb.addEventListener("load", (res: any) => {
	      const userId = JSON.parse(res.target.response).UserId;
   
			 // ์„ธ๋ฒˆ์งธ UserId api ์š”์ฒญ   
		   const ccc = new XMLHttpRequest();
		    cc.open("get", `https://koreanjson.com/posts?userId=${userId}`);
		    cc.send();
		    cc.addEventListener("load", (res: any) => {
					console.log(res)
		      console.log("์ตœ์ข… ๊ฒฐ๊ณผ๊ฐ’ !");
		 console.log(JSON.parse(res.target.response));
      });
    });
  });
};

๋‘ ๋ฒˆ์งธ ์š”์ฒญ๊ณผ ๋งˆ์ฐฌ๊ฐ€์ง€๋กœ JSON.parse()๋ฅผ ์ด์šฉํ•ด์„œ ๋ฌธ์ž์—ด์„ ๊ฐ์ฒด๋กœ ๋ฐ”๊ฟ”์ค€๋‹ค.


์š”์ฒญ์ด ๋ฐ˜๋ณต๋ ์ˆ˜๋ก ์˜ค๋ฅธ์ชฝ ๋ฐฉํ–ฅ ๋Œ€๊ฐ์„ ์œผ๋กœ ์‘ฅ ํŒŒ์ด๋Š” ํ˜•ํƒœ๋ฅผ ๋ณผ ์ˆ˜ ์žˆ๋‹ค. API ์š”์ฒญ์ด ๊ฑฐ๋“ญ๋œ๋‹ค๋ฉด ์ฝ”๋“œ์˜ ๊ฐ€๋…์„ฑ์ด ์‹ฌํ•˜๊ฒŒ ๋–จ์–ด์งˆ ๊ฒƒ์ด๋‹ค. ์ด๋Ÿฌํ•œ ํ˜„์ƒ์„ ์ฝœ๋ฐฑ์ง€์˜ฅ์ด๋ผ๊ณ  ํ•œ๋‹ค.


Promise

์ฝœ๋ฐฑ์ง€์˜ฅ์„ ๋ง‰๊ณ ์ž ๋‚˜์˜จ ๊ฒƒ์ด Promise๋‹ค. ์œ„์— callback์—์„œ ํ–ˆ๋˜ ์ž‘์—…์„ Promise ๊ฐ์ฒด์—๋„ ์ ์šฉํ•ด๋ณด์•˜๋‹ค.

Promise๋Š” ์ž๋ฐ”์Šคํฌ๋ฆฝํŠธ์˜ ๋น„๋™๊ธฐ ์ฒ˜๋ฆฌ, ๊ทธ ์ค‘์—์„œ๋„ ํŠนํžˆ ์™ธ๋ถ€์—์„œ ๋งŽ์€ ๋ฐ์ดํ„ฐ๋ฅผ ๋ถˆ๋Ÿฌ์˜ค๋Š” ์ž‘์—…์— ์‚ฌ์šฉ๋œ๋‹ค. promise ๊ฐ์ฒด๋ฅผ ์ด์šฉํ•ด์„œ ๋งŒ๋“  ๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ๊ฐ€ axios์ด๊ธฐ ๋•Œ๋ฌธ์—, axios๋ฅผ ์‹ค์Šต์— ์‚ฌ์šฉํ–ˆ๋‹ค.

๋งŒ์•ฝ axios๋ฅผ ์‚ฌ์šฉํ•˜์ง€ ์•Š๊ณ  Promise ๊ฐ์ฒด๋ฅผ ์ง์ ‘ ์‚ฌ์šฉํ•˜๋ ค๋ฉด ๋‹ค์Œ๊ณผ ๊ฐ™์ด ํ•˜๋ฉด ๋œ๋‹ค.

const result = await new Promise((resolve, reject) => {
	const aaa = new XMLHttpRequest();
  aaa.open("get", "http://numbersapi.com/random?min=1&max=200");
  aaa.send();
  aaa.addEventListener("load", (res: any) => {
		resolve(res)
  });
})
// resolve : ์š”์ฒญ์ด ์„ฑ๊ณตํ–ˆ์„ ๊ฒฝ์šฐ
// reject : ์š”์ฒญ์ด ์‹คํŒจํ–ˆ์„ ๊ฒฝ์šฐ

async/await๊ฐ€ ๋“ฑ์žฅํ•˜๊ธฐ ์ „์—๋Š” promise ๊ฐ์ฒด์— ์ œ๊ณต๋˜๋Š” .then์ด๋ผ๋Š” ๊ธฐ๋Šฅ์„ ์‚ฌ์šฉํ–ˆ๋‹ค. ๋‹ค์Œ๊ณผ ๊ฐ™์ด ์จ์ค„ ์ˆ˜ ์žˆ๋‹ค.

const onClickPromise = () => {
  axios
    .get("http://numbersapi.com/random?min=1&max=200")
    .then((res) => {
      const num = res.data.split(" ")[0];
      return axios.get(`https://koreanjson.com/posts/${num}`);
    })
    .then((res) => {
      const userId = res.data.UserId;
      // prettier-ignore
      return axios.get(`https://koreanjson.com/posts?userId=${userId}`)
    })
    .then((res) => {
      console.log(res.data);
    });
};

callback์— ๋น„ํ•ด ํ›จ์”ฌ ์ฝ”๋“œ๊ฐ€ ๊ฐ„๋‹จํ•ด์กŒ๋‹ค. promise๋ฅผ ์‚ฌ์šฉํ•  ๊ฒฝ์šฐ ๊ฐ ์š”์ฒญ๋“ค์ด ์ฒด์ธ์œผ๋กœ ์—ฐ๊ฒฐ๋˜๋Š”๋ฐ, ์ด๊ฒƒ์„ Promise Chain ๋˜๋Š” Promise Chaining์ด๋ผ๊ณ  ํ•œ๋‹ค.


ํ•˜์ง€๋งŒ, promise๋Š” ์ง๊ด€์ ์ด์ง€ ๋ชปํ•˜๋‹ค. ๋‹ค์Œ๊ณผ ๊ฐ™์ด ํ˜ธ์ถœ์— ๋Œ€ํ•œ ๊ฒฐ๊ณผ๊ฐ’์„ ์ƒ์ˆ˜์— ๋‹ด์•„ ์‚ฌ์šฉํ•˜๋Š” ๊ฒƒ์ด ๋ถˆ๊ฐ€๋Šฅํ•˜๋‹ค.

const result = axios.get // === ์ƒ๋žต ====

ํ•จ์ˆ˜๋ฅผ ์‹คํ–‰ํ•˜๋ฉด ๊ฒฐ๊ณผ ๊ฐ’์ด ์™„์ „ํ•œ ๋ฐ์ดํ„ฐ๊ฐ€ ์•„๋‹ˆ๋ผ Promise์˜ ํ˜•ํƒœ๋กœ ๋“ค์–ด์˜จ๋‹ค.

๋˜ํ•œ, Promise๋Š” ์ฝ”๋“œ์˜ ์‹คํ–‰ ์ˆœ์„œ๊ฐ€ ์ง๊ด€์ ์ด์ง€ ๋ชปํ•˜๋‹ค. axios๋ฅผ ์ด์šฉํ•œ ๋น„๋™๊ธฐ ์ž‘์—…์ด TaskQueue ์•ˆ์— ๋“ค์–ด๊ฐ€, ์‹คํ–‰ ์ˆœ์„œ๊ฐ€ ๋’ค๋กœ ๋ฐ€๋ฆฌ๊ฒŒ ๋œ๋‹ค.


Async/Await ์‹ค์Šต

async/await๋ฅผ ์ด์šฉํ•˜๋ฉด ์ฝ”๋“œ๊ฐ€ ์ง๊ด€์ ์ด๊ณ  ์‹ฌํ”Œํ•ด์ง„๋‹ค!

const onClickAsyncAwait = async () => {
  // prettier-ignore
  const res1 = await axios.get("http://numbersapi.com/random?min=1&max=200");
  const num = res1.data.split(" ")[0];

  const res2 = await axios.get(`https://koreanjson.com/posts/${num}`);
  const userId = res2.data.UserId;
  
  // prettier-ignore
  const res3 = await axios.get(`https://koreanjson.com/posts?userId=${userId}`)
  console.log(res3.data);
};
์ฐธ๊ณ ! async/await๋Š” promise์—๋งŒ ๋ถ™์ผ ์ˆ˜ ์žˆ๋‹ค. axios๊ฐ€ promise ๊ฐ์ฒด๋ฅผ ์ด์šฉํ•ด ๋งŒ๋“ค์–ด์ง„ ๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ์ด๊ธฐ ๋•Œ๋ฌธ์— async/await๋ฅผ ์‚ฌ์šฉํ•  ์ˆ˜ ์žˆ๋‹ค.



๋งคํฌ๋กœ ํƒœ์Šคํฌ ํ vs ๋งˆ์ดํฌ๋กœ ํƒœ์Šคํฌ ํ


Promise ์‹ค์Šต์„ ํ•˜๋ฉด์„œ, Promise๋กœ ์‹คํ–‰ํ•˜๋Š” ํ•จ์ˆ˜๋Š” ํƒœ์Šคํฌ ํ์— ๋“ค์–ด๊ฐ„๋‹ค๋Š” ๊ฒƒ์„ ๋– ์˜ฌ๋ ค๋ณด์ž. ํƒœ์Šคํฌ ํ๋Š” ๋”ฑ ํ•˜๋‚˜๋งŒ ์žˆ๋Š” ๊ฒƒ์ด ์•„๋‹ˆ๋ผ, ์—ฌ๋Ÿฌ ๊ฐœ๊ฐ€ ๋™์‹œ์— ์กด์žฌํ•œ๋‹ค. ๊ทธ ์ค‘ ๋Œ€ํ‘œ์ ์ธ ๋‘ ๊ฐ€์ง€ ํƒœ์Šคํฌ ํ๋ฅผ ๊ณต๋ถ€ํ–ˆ๋‹ค.

๋งคํฌ๋กœ ํƒœ์Šคํฌ ํ (MacroTaskQueue): setTimeout, setInterval ๋“ฑ์ด ๋“ค์–ด๊ฐ€๋Š” ํ
๋งˆ์ดํฌ๋กœ ํƒœ์Šคํฌ ํ (MicroTaskQueue): Promise ๋“ฑ์ด ๋“ค์–ด๊ฐ€๋Š” ํ


ํƒœ์Šคํฌ ํ๋“ค ๊ฐ„์˜ ์‹คํ–‰ ์šฐ์„ ์ˆœ์œ„

๋งคํฌ๋กœ ํƒœ์Šคํฌ ํ์™€ ๋งˆ์ดํฌ๋กœ ํƒœ์Šคํฌ ํ๊ฐ€ ๋ถ€๋”ชํž ๊ฒฝ์šฐ์—๋Š” ๋งˆ์ดํฌ๋กœ ํƒœ์Šคํฌ ํ๊ฐ€ ์šฐ์„ ํ•œ๋‹ค.


await์™€ ๋งˆ์ดํฌ๋กœ ํ์˜ ๊ด€๊ณ„


isSubmitting์„ ํ™œ์šฉํ•œ ์ค‘๋ณต mutation ๋ฐฉ์ง€

์‹ค์ˆ˜๋กœ mutation api ์š”์ฒญ์„ ์—ฌ๋Ÿฌ ๋ฒˆ ๋ณด๋‚ด๊ฒŒ ๋  ๊ฒฝ์šฐ๋ฅผ ๋Œ€๋น„ํ•ด์„œ isSubmitting์„ ํ™œ์šฉํ•ด ๋‘ ๋ฒˆ์งธ ์š”์ฒญ๋ถ€ํ„ฐ๋Š” ๋ง‰์•„์ค„ ์ˆ˜ ์žˆ๋‹ค.

import axoios from 'axios'

export default function IsSubmitting(){
	const [isSubmitting,setIsSubmitting] = useState(false)

	const onClickSubmit = async ()=>{
		// ๋“ฑ๋กํ•˜๋Š” ๋™์•ˆ์€ ๋“ฑ๋ก๋ฒ„ํŠผ์ด ์ž‘๋™ํ•˜์ง€ ์•Š๋„๋ก ํ•จ
		setIsSubmitting(true)

		const result = await axios.get("https://koreanjson.com/posts/1")
		
		// ๋“ฑ๋ก์ด ์™„๋ฃŒ๋˜์—ˆ๋‹ค๋ฉด ๋‹ค์‹œ ๋ฒ„ํŠผ์ด ๋™์ž‘ํ•˜๋„๋ก ํ•จ
		setIsSubmitting(false)

	}
	
	return(
		<button onClick={onClickSubmit} disabled={isSubmitting}> ๋“ฑ๋กํ•˜๊ธฐ ๋“ฑ์˜ API ์š”์ฒญ๋ฒ„ํŠผ </button>
	) 
}

๊ทธ๋Ÿฐ๋ฐ ์—ฌ๊ธฐ์„œ setState๋Š” ์ตœ์ข…์ ์œผ๋กœ ๋ฐ”๋€ ๊ฒฐ๊ณผ๊ฐ’์œผ๋กœ ๋ฐ˜์˜๋œ๋‹ค๊ณ  ์•Œ๊ณ  ์žˆ๋‹ค. ์œ„์— ์ฝ”๋“œ์ฒ˜๋Ÿผ setState๋ฅผ ์—ฌ๋Ÿฌ ๋ฒˆ ๋ฐ”๊ฟ”๋„ ๋งจ ๋งˆ์ง€๋ง‰ ๊ฐ’๋งŒ ๋ฐ˜์˜๋˜์ง€ ์•Š๋‚˜?

์ด ๋ถ€๋ถ„์€ await์™€ ๋งˆ์ดํฌ๋กœ ํ์˜ ๊ด€๊ณ„๋ฅผ ์•Œ๊ณ  ์žˆ์–ด์•ผ ํ•œ๋‹ค.


await์™€ ๋งˆ์ดํฌ๋กœ ํ์˜ ๊ด€๊ณ„

<!DOCTYPE html>
<html lang="ko">
  <head>
    <title>์ด๋ฒคํŠธ๋ฃจํ”„</title>
    <script>
      function onClickLoop() {
        console.log("=======์‹œ์ž‘!!!!=======");

        function aaa() {
          console.log("aaa-์‹œ์ž‘");
          bbb();
          console.log("aaa-๋");
        }

        async function bbb() {
          console.log("bbb-์‹œ์ž‘");
          const friend = await "์ฒ ์ˆ˜";
          console.log(friend);
        }

        aaa();

        console.log("=======๋!!!!=======");
      }
    </script>
  </head>
  <body>
    <button onclick="onClickLoop()">์‹œ์ž‘ํ•˜๊ธฐ</button>
  </body>
</html>

์ฝ˜์†”์ฐฝ์„ ์—ด์–ด์„œ ํ™•์ธํ•ด๋ณด๋ฉด ๊ฒฐ๊ณผ๋Š” ๋‹ค์Œ๊ณผ ๊ฐ™์ด ๋‚˜์˜จ๋‹ค.

๊ตฌ์ฒด์ ์ธ ํ•จ์ˆ˜ ์‹คํ–‰ ๊ณผ์ •
1. callstack์— onClickLoop ๋“ค์–ด์˜ด
2. ====์‹œ์ž‘!!!!==== ์ฝ˜์†”์— ์ฐํž˜
3. aaa ํ•จ์ˆ˜๊ฐ€ callstack์— ์Œ“์ž„
4. aaa-์‹œ์ž‘ ์ฝ˜์†”์— ์ฐํž˜
5. bbb ํ•จ์ˆ˜๊ฐ€ callstack์— ์Œ“์ž„
6. bbb-์‹œ์ž‘์ด ์ฝ˜์†”์— ์ฐํž˜
7. await์—์„œ bbb ํ•จ์ˆ˜ ์•ˆ ์‹คํ–‰ ์ค‘๋‹จํ•˜๊ณ , async ํ•จ์ˆ˜๊ฐ€ ๋งˆ์ดํฌ๋กœ ํ์— ๋“ค์–ด๊ฐ(๋Œ€๊ธฐ)
8. bbb ํ•จ์ˆ˜ callstack์—์„œ ์—†์–ด์ง
9. aaa-๋ ์ฝ˜์†”์— ์ฐํž˜. aaa ํ•จ์ˆ˜ callstack์—์„œ ์—†์–ด์ง
10. ====๋!!!!==== ์ฝ˜์†”์— ์ฐํž˜. onClickLoop ํ•จ์ˆ˜ callstack์—์„œ ์—†์–ด์ง
11. bbb await callstack์— ๊ฐ€์ ธ์™€์„œ ์‹คํ–‰. ์ฒ ์ˆ˜ ์ฝ˜์†”์— ์ฐํž˜

์ž๋ฐ”์Šคํฌ๋ฆฝํŠธ๋Š” await๊ฐ€ ๋‚˜์˜ค๋ฉด async๋ฅผ ๊ฐ์‹ธ๊ณ  ์žˆ๋Š” ํ•จ์ˆ˜๊ฐ€ ํ•˜๋˜ ์ผ์„ ์ค‘๋‹จํ•˜๊ณ  ๋งˆ์ดํฌ๋กœ ํ์— ๋“ค์–ด๊ฐ„๋‹ค!

๊ทธ๋ฆฌ๊ณ  async๊ฐ€ ๊ฐ์‹ธ๊ณ  ์žˆ๋Š” ํ•จ์ˆ˜๊ฐ€ ๋งˆ์ดํฌ๋กœ ํ์— ๋“ค์–ด๊ฐˆ ๋•Œ์—๋Š” ์‹คํ–‰ํ•˜๋˜ ์œ„์น˜๋ฅผ ๊ธฐ์–ตํ•œ๋‹ค.

๋”ฐ๋ผ์„œ ๋งˆ์ดํฌ๋กœ ํ์—์„œ ๋‚˜์™€ ์‹คํ–‰๋  ๋•Œ์—๋Š” ๊ธฐ์–ตํ•œ ์œ„์น˜๋ถ€ํ„ฐ ์‹คํ–‰๋œ๋‹ค.


๋˜ ๋‹ค๋ฅธ ๋ฌธ์ œ๋ฅผ ํ’€์–ด๋ณด์ž.

<!DOCTYPE html>
<html lang="ko">
  <head>
    <title>์ด๋ฒคํŠธ๋ฃจํ”„</title>
    <script>
      function onClickLoop() {
        console.log("=======์‹œ์ž‘!!!!=======");

        function aaa() {
          console.log("aaa-์‹œ์ž‘");
          bbb();
          console.log("aaa-๋");
        }

        async function bbb() {
          console.log("bbb-์‹œ์ž‘");
          await ccc();
          console.log("bbb-๋");
        }

        async function ccc() {
          console.log("ccc-์‹œ์ž‘");
          const friend = await "์ฒ ์ˆ˜";
          console.log(friend);
        }

        aaa();

        console.log("=======๋!!!!=======");
      }
    </script>
  </head>
  <body>
    <button onclick="onClickLoop()">์‹œ์ž‘ํ•˜๊ธฐ</button>
  </body>
</html>

์ฝ˜์†”์— ์ฐํžˆ๋Š” ์ˆœ์„œ
=======์‹œ์ž‘!!!!=======
aaa-์‹œ์ž‘
bbb-์‹œ์ž‘
ccc-์‹œ์ž‘
aaa-๋
=======๋!!!!=======
์ฒ ์ˆ˜
bbb-๋

๊ตฌ์ฒด์ ์ธ ์‹คํ–‰ ๊ณผ์ •
1. onClickLoop callstack์— ์Œ“์ž„
2. =======์‹œ์ž‘!!!!======= ์ฝ˜์†”์— ์ฐํž˜
3. aaa ํ•จ์ˆ˜ callstack์— ์Œ“์ž„
4. aaa-์‹œ์ž‘ ์ฝ˜์†”์— ์ฐํž˜
5. bbb ํ•จ์ˆ˜ ์‹คํ–‰(callstack), bbb-์‹œ์ž‘ ์ฝ˜์†”์— ์ฐํž˜
6. ccc ํ•จ์ˆ˜ ์‹คํ–‰(callstack), ccc-์‹œ์ž‘ ์ฝ˜์†”์— ์ฐํž˜
7. ccc ํ•จ์ˆ˜ ์•ˆ ํ•˜๋˜๊ฑฐ ์ค‘๋‹จํ•˜๊ณ , await ๋ถ€๋ถ„์ด ๋งˆ์ดํฌ๋กœํ์— ๋“ค์–ด๊ฐ
8. bbb ํ•จ์ˆ˜ ์•ˆ await ๋ถ€๋ถ„๋„ ๋งˆ์ดํฌ๋กœํ์— ๋“ค์–ด๊ฐ
9. aaa-๋ ์ฝ˜์†”์— ์ฐํž˜
10. =======๋!!!!======= ์ฐํž˜. onClickLoop ์ข…๋ฃŒ
11. ccc ํ•จ์ˆ˜(await ๋ถ€๋ถ„) callstack์— ๊ฐ€์ ธ์˜ด
12. ์ฒ ์ˆ˜ ์ฐํž˜. ccc ํ•จ์ˆ˜ ์ข…๋ฃŒ
13. bbb ํ•จ์ˆ˜(await ๋ถ€๋ถ„) callstack์œผ๋กœ ๊ฐ€์ ธ์˜ด
14. bbb-๋ ์ฐํž˜. bbb ํ•จ์ˆ˜ ์ข…๋ฃŒ



profile
Web FE ๊ฐœ๋ฐœ์ž ์ทจ์ค€์ƒ

0๊ฐœ์˜ ๋Œ“๊ธ€