ABOUT ME

-

Today
-
Yesterday
-
Total
-
  • [JavaScript] ๋” ๋‚˜์€ ๋น„๋™๊ธฐ ํ†ต์‹ 
    TECH 2022. 3. 27. 15:02

    ํ”„๋ฆฌ์˜จ๋ณด๋”ฉ ํŒ€์›๋“ค๊ณผ ํ•จ๊ป˜ ๋ฉด์ ‘ ์Šคํ„ฐ๋””๋ฅผ ์‹œ์ž‘ํ–ˆ๋‹ค! ์ด๋ฒˆ ์ฃผ ์ฃผ์ œ ์ค‘ ํ•˜๋‚˜์ธ Promise, callback hell, async/await, fetch ๋“ฑ์— ๋Œ€ํ•ด ์ž์„ธํžˆ ์•Œ์•„๋ณด๋Š” ์‹œ๊ฐ„์„ ๊ฐ€์กŒ๋‹ค. API๋ฅผ ํ†ตํ•ด ๋ฐ์ดํ„ฐ๋ฅผ ๊ฐ€์ ธ์˜ฌ ๋•Œ async/await๋‚˜ fetch๋ฅผ ์‚ฌ์šฉํ•˜๋ฉด์„œ๋„ ๋‚ด๋ถ€์ ์œผ๋กœ ์–ด๋–ป๊ฒŒ ๋™์ž‘ํ•˜๋Š”์ง€๋Š” ์ž˜ ๋ชจ๋ฅด๊ณ  ์žˆ์—ˆ๋Š”๋ฐ ์ด๋ฒˆ ๊ธฐํšŒ์— ๋‚ด๋ถ€ ๋™์ž‘์ด ์–ด๋–ป๊ฒŒ ์ด๋ฃจ์–ด์ง€๋Š”์ง€ ๊ณต๋ถ€ํ•ด ๋ณผ ์ˆ˜ ์žˆ์—ˆ๋‹ค.

     

    ๊ทธ๋Ÿผ ๋ฐ”๋กœ ์‹œ์ž‘~

     

     

    โœ”๏ธ ์ฝœ๋ฐฑ ํ•จ์ˆ˜

    ํ•จ์ˆ˜์˜ ๋งค๊ฐœ๋ณ€์ˆ˜๋ฅผ ํ†ตํ•ด ๋‹ค๋ฅธ ํ•จ์ˆ˜์˜ ๋‚ด๋ถ€๋กœ ์ „๋‹ฌ๋˜๋Š” ํ•จ์ˆ˜๋ฅผ ์ฝœ๋ฐฑ ํ•จ์ˆ˜(callback function)๋ผ๊ณ  ํ•œ๋‹ค. ๋งค๊ฐœ๋ณ€์ˆ˜๋ฅผ ํ†ตํ•ด ํ•จ์ˆ˜์˜ ์™ธ๋ถ€์—์„œ ์ฝœ๋ฐฑ ํ•จ์ˆ˜๋ฅผ ์ „๋‹ฌ๋ฐ›์€ ํ•จ์ˆ˜๋Š” ๊ณ ์ฐจ ํ•จ์ˆ˜(Higher-Order Function, HOF)๋ผ๊ณ  ํ•œ๋‹ค.

     

    ํŠน์ • ์ž‘์—…์„ n ๋ฒˆ ๋ฐ˜๋ณต์‹œํ‚ค๋Š” ํ•จ์ˆ˜๊ฐ€ ์žˆ๋‹ค๊ณ  ํ•˜์ž.

    function repeat(n) {
      for (let i = 0; i < n; i++) {
        console.log(i);
      }
    }
    
    repeat(5); // 0 1 2 3 4
    

     

    console.log(i) ๋Œ€์‹  ๋‹ค๋ฅธ ์ž‘์—…์„ n๋ฒˆ ๋ฐ˜๋ณต์‹œํ‚ค๊ณ  ์‹ถ์„ ์ˆ˜๋„ ์žˆ์„ ๊ฒƒ์ด๋‹ค. ๊ทธ๋Ÿด ๋•Œ ํ•จ์ˆ˜๋กœ n๊ณผ ๊ฐ™์ด ์ฝœ๋ฐฑ ํ•จ์ˆ˜๋ฅผ ๋„˜๊ฒจ ์ค€๋‹ค๋ฉด ์šฐ๋ฆฌ๊ฐ€ ์›ํ•˜๋Š” ๋Œ€๋กœ ํŠน์ • ์ž‘์—…์„ ๋ฐ˜๋ณต์‹œํ‚ฌ ์ˆ˜ ์žˆ๋‹ค.

    function repeat(n, callback) {
      for (let i = 0; i < n; i++) {
        callback(i);
      }
    }
    
    const logAll = (i) => {
      console.log(i);
    };
    
    repeat(5, logAll); // 0 1 2 3 4
    
    const logOdds = (i) => {
      if (i % 2) console.log(i);
    };
    
    repeat(5, logOdds); // 1 3
    

     

    โœ”๏ธ callback hell

    ๋น„๋™๊ธฐ ์ฒ˜๋ฆฌ๋ฅผ ์œ„ํ•ด ์ฝœ๋ฐฑ ํ•จ์ˆ˜๋ฅผ ์—ฐ์†ํ•ด์„œ ์‚ฌ์šฉํ•  ๋•Œ ์ค‘์ฒฉ๋˜๋ฉด์„œ ์ƒ๊ธฐ๋Š” ๋ฌธ์ œ๋ฅผ ๋ณดํ†ต ์ฝœ๋ฐฑ ์ง€์˜ฅ(callback hell)์ด๋ผ๊ณ  ๋ถ€๋ฅธ๋‹ค.

    $.get("<https://api.test.com/proudcts>", function (response) {
      var firstProductId = response.products[0].id;
      $.get(
        "<https://api.test.com/proudct/comments?id=>" + firstProductId,
        function (response) {
          var firstCommentId = response.comments[0].id;
          $.get(
            "<https://api.test.com/proudct/comment/likes?id=>" + firstCommentId,
            function (response) {
              var likes = response.likes;
              var likesCount = likes.length;
            }
          );
        }
      );
    });
    

    ์ด๋ ‡๊ฒŒ ์ฝœ๋ฐฑ์ด ์ค‘์ฒฉ๋˜์–ด ์žˆ๋Š” ์ฝ”๋“œ๋Š” ๊ฐ€๋…์„ฑ๋„ ์ข‹์ง€ ์•Š์„๋ฟ๋”๋Ÿฌ ์œ ์ง€ ๋ณด์ˆ˜ ํ•˜๊ธฐ๋„ ์–ด๋ ต๋‹ค๋Š” ๋‹จ์ ์ด ์žˆ๋‹ค.

     

    โ• ์ฝœ๋ฐฑ ์ง€์˜ฅ ๊ฐœ์„ 

    ์ฝœ๋ฐฑ ์ง€์˜ฅ์€ Promise ์‚ฌ์šฉ, Async/Await ์‚ฌ์šฉ, ์ฝ”๋”ฉ ํŒจํ„ด ๊ฐœ์„ ์œผ๋กœ ํ•ด๊ฒฐํ•  ์ˆ˜ ์žˆ๋‹ค.

     

    ์ฝ”๋”ฉ ํŒจํ„ด์œผ๋กœ ๊ฐœ์„ ํ•˜๋Š” ๋ฐฉ๋ฒ•์€ ๋‹ค์Œ๊ณผ ๊ฐ™์ด ์ค‘์ฒฉ๋˜์–ด ์žˆ๋Š” ์ฝœ๋ฐฑ์„ ๋”ฐ๋กœ ๋ถ„๋ฆฌํ•˜์—ฌ ์ž‘์„ฑํ•˜๋Š” ๋ฐฉ๋ฒ•์ด๋‹ค.

    function fetchCommentLikes(commentId) {
      $.get(
        "<https://api.test.com/proudct/comment/likes?id=>" + commentId,
        function (response) {
          var likes = response.likes;
          var likesCount = likes.length;
        }
      );
    }
    
    function fetchComments(productId) {
      $.get(
        "<https://api.test.com/proudct/comments?id=>" + productId,
        function (response) {
          var firstCommentId = response.comments[0].id;
    
          fetchCommentLikes(firstCommentId);
        }
      );
    }
    
    $.get("<https://api.test.com/proudcts>", function (response) {
      var firstProductId = response.products[0].id;
    
      fetchComments(firstProductId);
    });
    

    ๊ทธ๋Ÿฌ๋‚˜ ์ด๋งˆ์ €๋„ ํ๋ฆ„์„ ์ซ“์•„๊ฐ€๋ฉฐ ์ฝ์–ด์•ผ ํ•˜๊ธฐ ๋•Œ๋ฌธ์— ๋ˆˆ์— ์ฉ ์ž˜ ๋“ค์–ด์˜ค์ง€๋Š” ์•Š๋Š”๋‹ค.

     

     

    โœ”๏ธ Promise๋ž€?

    ํ”„๋กœ๋ฏธ์Šค๋Š” ์ค‘์ฒฉ๋˜๋Š” ๋น„๋™๊ธฐ ํ†ต์‹  ๋กœ์ง๊ณผ ์ฝœ๋ฐฑ ์ง€์˜ฅ์˜ ๋ฌธ์ œ๋ฅผ ํ•ด๊ฒฐํ•˜๊ธฐ ์œ„ํ•œ ๊ธฐ๋ฒ•์ด๋‹ค.

    ๐Ÿ’ก ์ธํ„ฐ๋„ท ์ต์Šคํ”Œ๋กœ๋Ÿฌ๋Š” ํ”„๋กœ๋ฏธ์Šค๋ฅผ ์ง€์›ํ•˜์ง€ ์•Š๊ธฐ ๋•Œ๋ฌธ์— ์ธํ„ฐ๋„ท ์ต์Šคํ”Œ๋กœ๋Ÿฌ ํ˜ธํ™˜์„ฑ์ด ํ•„์š”ํ•˜๋‹ค๋ฉด ํ”„๋กœ๋ฏธ์Šค ๋Œ€์‹  AJAX๋ฅผ ์‚ฌ์šฉํ•ด์•ผ ํ•œ๋‹ค.

     

    โœ”๏ธ ํ”„๋กœ๋ฏธ์Šค ๊ฐ์ฒด์˜ ์ƒํƒœ

    ํ”„๋กœ๋ฏธ์Šค ์ธ์Šคํ„ด์Šค๋Š” ์ง„ํ–‰ ์ค‘์ธ ๋น„๋™๊ธฐ ์ž‘์—…, ๊ทธ์— ๋”ฐ๋ฅธ ๊ฒฐ๊ณผ ์ฒ˜๋ฆฌ ๋ฐฉ๋ฒ•, ์ƒํƒœ ์ •๋ณด๋ฅผ ๊ฐ€์ง€๊ณ  ์žˆ๋‹ค.

    ํ”„๋กœ๋ฏธ์Šค ์ธ์Šคํ„ด์Šค๋Š” Pending, Fulfilled, Rejected 3๊ฐœ์˜ ์ƒํƒœ ์ •๋ณด๋ฅผ ๊ฐ€์ง„๋‹ค. ๊ทธ๋ฆฌ๊ณ  ์ƒํƒœ์— ๋”ฐ๋ฅธ 2๊ฐœ์˜ ๋ฉ”์†Œ๋“œ resolve์™€ reject๋ฅผ ๊ฐ€์ง„๋‹ค.

    ๋Œ€๊ธฐ ์ค‘(Pending) ํ”„๋กœ๋ฏธ์Šค ๊ฐ์ฒด์˜ ๊ธฐ๋ณธ ์ƒํƒœ, ๋น„๋™๊ธฐ ์ฒ˜๋ฆฌ ๊ฒฐ๊ณผ๊ฐ€ ๋‚˜์˜ค์ง€ ์•Š์€ ์ƒํƒœ
    ์ดํ–‰ ์™„๋ฃŒ(Fulfilled) ๋น„๋™๊ธฐ ์ฒ˜๋ฆฌ๊ฐ€ ์™„๋ฃŒ๋˜์–ด ๊ฒฐ๊ณผ๋ฅผ ์–ป์€ ์ƒํƒœ. resolve() ํ•จ์ˆ˜๋ฅผ ํ˜ธ์ถœํ•จ
    ๊ฑฐ๋ถ€๋จ(Rejected) ๋น„๋™๊ธฐ ์ฒ˜๋ฆฌ๋Š” ์™„๋ฃŒ๋˜์—ˆ์ง€๋งŒ ์‹คํŒจํ•œ ์ƒํƒœ. reject() ํ•จ์ˆ˜๋ฅผ ํ˜ธ์ถœํ•จ

     

    โœ”๏ธ ํ”„๋กœ๋ฏธ์Šค ๊ธฐ๋ณธ ์‚ฌ์šฉ๋ฒ•

    let myPromise = new Promise((resolve, reject) => {
      setTimeout(() => {
        let result = "promise fulfilled";
        resolve(result);
      }, 1000);
    });
    
    myPromise
      .then((successMessage) => {
        console.log(successMessage);
      })
      .catch((failMessage) => {
        console.log(failMessage);
      });
    

    ์ƒˆ๋กœ์šด ํ”„๋กœ๋ฏธ์Šค ๊ฐ์ฒด๋ฅผ ์ž‘์„ฑํ•  ๋•Œ๋Š” ํŒŒ๋ผ๋ฉ”ํ„ฐ 2๊ฐœ๋ฅผ ๊ฐ€์ง€๋Š” ๋น„๋™๊ธฐ ์ฒ˜๋ฆฌ ํ•จ์ˆ˜๋ฅผ ์ž‘์„ฑํ•œ๋‹ค.

    ์ฒซ ๋ฒˆ์งธ ํŒŒ๋ผ๋ฏธํ„ฐ๋Š” ์„ฑ๊ณตํ–ˆ์„ ๋•Œ ํ˜ธ์ถœํ•˜๋Š” ์ดํ–‰ ์™„๋ฃŒ ํ•จ์ˆ˜๋ช…์ด๊ณ , ๋‘ ๋ฒˆ์งธ ํŒŒ๋ผ๋ฏธํ„ฐ๋Š” ์‹คํŒจํ–ˆ์„ ๋•Œ ํ˜ธ์ถœํ•˜๋Š” ๊ฑฐ๋ถ€ ํ•จ์ˆ˜๋ช…์ด๋‹ค.

    ๊ด€์Šต์ ์œผ๋กœ ์ดํ–‰ ์™„๋ฃŒ ํ•จ์ˆ˜๋ช…์€ resolve, ๊ฑฐ๋ถ€ ํ•จ์ˆ˜๋ช…์€ reject๋กœ ์ž‘์„ฑํ•˜์ง€๋งŒ success, fail ๋“ฑ์œผ๋กœ ์ž‘์„ฑํ•ด๋„ ๊ดœ์ฐฎ๋‹ค.

    ํŒŒ๋ผ๋ฉ”ํ„ฐ์—์„œ ์ •ํ•œ ํ•จ์ˆ˜๋ช…์„ ํ˜ธ์ถœํ•˜๋ฉด then()๊ณผ catch() ์ค‘ ํ•˜๋‚˜๋ฅผ ํ˜ธ์ถœํ•œ๋‹ค. resolve()๊ฐ€ ํ˜ธ์ถœ๋˜๋ฉด then() ๋ฉ”์„œ๋“œ์˜ ํŒŒ๋ผ๋ฉ”ํ„ฐ์— ์ •์˜ํ•œ ์ฝœ๋ฐฑ ํ•จ์ˆ˜๊ฐ€ ์‹คํ–‰๋˜๊ณ , reject()๊ฐ€ ํ˜ธ์ถœ๋˜๋ฉด catch() ๋ฉ”์„œ๋“œ์˜ ํŒŒ๋ผ๋ฉ”ํ„ฐ์— ์ •์˜ํ•œ ์ฝœ๋ฐฑ ํ•จ์ˆ˜๊ฐ€ ์‹คํ–‰๋œ๋‹ค.

     

    โœ”๏ธ ๋‹ค์ค‘ ํ”„๋กœ๋ฏธ์Šค ์ฒ˜๋ฆฌ

    function asyncWork(value) {
      return new Promise((resolve, reject) => {
        setTimeout(() => {
          value -= 20;
          if (value > 50) {
            resolve(value);
          } else {
            reject(value);
          }
        });
      });
    }
    
    asyncWork(100)
      .then((value) => {
        console.log(value);
        return asyncWork(value);
      })
      .then((value) => {
        console.log(value);
        return asyncWork(value);
      })
      .then((value) => {
        console.log(value);
        return asyncWork(value);
      })
      .catch((error) => {
        console.log("catch: " + error);
      });
    

    asyncWork ํ•จ์ˆ˜๋Š” ํ”„๋กœ๋ฏธ์Šค ์ธ์Šคํ„ด์Šค๋ฅผ ๋ฐ˜ํ™˜ํ•œ๋‹ค. ๋”ฐ๋ผ์„œ ํ•จ์ˆ˜๋ฅผ ํ˜ธ์ถœํ•˜๋ฉฐ ๋ฉ”์„œ๋“œ ์ฒด์ธ์œผ๋กœ then()์„ ์‹คํ–‰ํ•  ์ˆ˜ ์žˆ๋‹ค. ์˜ˆ์ œ์—์„œ๋„ then()์„ ์—ฐ๋‹ฌ์•„ ์ฒด์ธ ๋ฐฉ์‹์œผ๋กœ ์—ฌ๋Ÿฌ ๊ฐœ ํ˜ธ์ถœํ•œ๋‹ค.

     

    ๋‹ค์ค‘ ํ”„๋กœ๋ฏธ์Šค๋Š” ์ฒด์ธ์œผ๋กœ ํ˜ธ์ถœํ•˜๋Š” then() ๋ฉ”์„œ๋“œ์˜ ์ฝœ๋ฐฑ ํ•จ์ˆ˜์˜ ๋ฆฌํ„ด ๊ฐ’์œผ๋กœ ํ”„๋กœ๋ฏธ์Šค ์ธ์Šคํ„ด์Šค๋ฅผ ์ƒ์„ฑํ•˜๋Š” ํ•จ์ˆ˜๋ฅผ ๋‹ค์‹œ ํ˜ธ์ถœํ•œ๋‹ค๋Š” ๊ฒƒ์ด๋‹ค. ๋ฐ˜ํ™˜๋œ ํ”„๋กœ๋ฏธ์Šค ์ธ์Šคํ„ด์Šค๋Š” ๋‹ค์Œ then()์˜ ํ”„๋กœ๋ฏธ์Šค ์ธ์Šคํ„ด์Šค๊ฐ€ ๋œ๋‹ค. then() ๋ฉ”์„œ๋“œ๋Š” ์ฝœ๋ฐฑ ํ•จ์ˆ˜์—์„œ ๋ฐ˜ํ™˜ํ•˜๋Š” asyncWork() ํ”„๋กœ๋ฏธ์Šค ์ธ์Šคํ„ด์Šค์˜ ๋น„๋™๊ธฐ ์ฒ˜๋ฆฌ๊ฐ€ ์™„๋ฃŒ๋˜๊ธฐ ์ „๊นŒ์ง€ ๋‹ค์Œ then()์„ ํ˜ธ์ถœํ•˜์ง€ ์•Š๊ณ  ๋Œ€๊ธฐํ•œ๋‹ค.

    ๋”ฐ๋ผ์„œ ๋ชจ๋“  ๋น„๋™๊ธฐ ์ฒ˜๋ฆฌ ์ž‘์—…์€ then์˜ ์ฝœ๋ฐฑ ํ•จ์ˆ˜ ์ˆœ์„œ๋Œ€๋กœ ํ•˜๋‚˜์”ฉ ์‹คํ–‰๋˜๊ณ , ์ฝœ๋ฐฑ ํ•จ์ˆ˜์˜ ํŒŒ๋ผ๋ฉ”ํ„ฐ๋ฅผ ํ†ตํ•ด ๊ฒฐ๊ณผ ๊ฐ’์„ ์ˆœ์ฐจ์ ์œผ๋กœ ์ „๋‹ฌํ•œ๋‹ค.

     

    ๋งˆ์ง€๋ง‰์œผ๋กœ ํ”„๋กœ๋ฏธ์Šค ์ธ์Šคํ„ด์Šค ์ƒํƒœ๊ฐ€ ๊ฑฐ์ ˆ ์ƒํƒœ๊ฐ€ ๋˜๋ฉด ๋‹ค์Œ then()์ด ์•„๋‹Œ catch()๋ฅผ ์‹คํ–‰ํ•˜๋ฉฐ ์—๋Ÿฌ ๋ฉ”์‹œ์ง€๋ฅผ ์ถœ๋ ฅํ•˜๊ณ  ์ข…๋ฃŒํ•œ๋‹ค. ์ƒ๋‹จ์˜ ์ฝ”๋“œ๋Š” value๋ฅผ 20์”ฉ ์ฐจ๊ฐํ•˜๋ฉฐ ๋‹ค์Œ then()์„ ํ˜ธ์ถœํ•˜๊ณ , ๊ฐ’์ด 50๋ณด๋‹ค ์ž‘์œผ๋ฉด ๊ฑฐ์ ˆ ์ƒํƒœ๋กœ ๋ณ€๊ฒฝํ•œ ํ›„ catch()๋ฅผ ํ˜ธ์ถœํ•˜๋ฉด์„œ ๋น„๋™๊ธฐ ์ฒ˜๋ฆฌ ์ฒด์ธ์„ ์ข…๋ฃŒํ•œ๋‹ค.

     

    ํ”„๋กœ๋ฏธ์Šค๋ฅผ ์‚ฌ์šฉํ•œ๋‹ค๋ฉด ์ˆœ์„œ๋Œ€๋กœ then() ๋ฉ”์„œ๋“œ๋ฅผ ๋ถ™์—ฌ ๋‚˜์—ดํ•˜๊ธฐ ๋•Œ๋ฌธ์— ์ฝœ๋ฐฑ ์ง€์˜ฅ์—์„œ์ฒ˜๋Ÿผ ๋น„๋™๊ธฐ ์ฒ˜๋ฆฌ๋ฅผ ์œ„ํ•ด ์ฝ”๋“œ๋ฅผ ์ค‘์ฒฉํ•  ํ•„์š”๊ฐ€ ์—†๋‹ค. ๋น„๋™๊ธฐ ์ฒ˜๋ฆฌ ์ž‘์—…์„ ์ค‘๋ณต ์ž‘์„ฑํ•  ํ•„์š”๊ฐ€ ์—†๊ธฐ ๋•Œ๋ฌธ์— ์ฒ˜๋ฆฌ ๊ตฌ์กฐ์˜ ํšจ์œจ์ด ์ข‹์•„์ง€๊ณ  ์ฝ”๋“œ ๋Ÿ‰๋„ ์ค„์ผ ์ˆ˜ ์žˆ๋‹ค. ๋˜ํ•œ ๋น„๋™๊ธฐ ์ฒ˜๋ฆฌ ํ๋ฆ„์ด ํ•œ๋ˆˆ์— ๋“ค์–ด์˜ค๊ณ  ์‹คํ–‰ ๊ตฌ์กฐ์™€ ์ˆœ์„œ๋ฅผ ๋ช…ํ™•ํ•˜๊ฒŒ ํŒŒ์•…ํ•  ์ˆ˜ ์žˆ๋‹ค.

     

    ๐Ÿ“Œ callback๊ณผ promise์˜ ์ฐจ์ด

    callback ํ•จ์ˆ˜๋Š” ๋น„๋™๊ธฐ ์ฒ˜๋ฆฌ๋งŒ์„ ์œ„ํ•œ ๊ฒƒ์€ ์•„๋‹ˆ๋‹ค. ๋น„๋™๊ธฐ ์ฒ˜๋ฆฌ๋ฅผ ํ•  ๋•Œ๋Š” ์ฝœ๋ฐฑ ํŒจํ„ด์ด ์“ฐ์ธ๋‹ค. ์ฝœ๋ฐฑ ํŒจํ„ด์„ ์‚ฌ์šฉํ–ˆ์„ ๊ฒฝ์šฐ์—๋Š” ์ž์œ ๋„๊ฐ€ ๋†’๋‹ค๋Š” ์žฅ์ ์ด ์žˆ์ง€๋งŒ, ์ค‘์ฒฉ๋  ๊ฒฝ์šฐ ์ฝ”๋“œ๊ฐ€ ๋ณต์žกํ•ด์ ธ ๊ฐ€๋…์„ฑ์ด ๋–จ์–ด์งˆ ์ˆ˜ ์žˆ์œผ๋ฉฐ, ์—๋Ÿฌ ์ฒ˜๋ฆฌ๊ฐ€ ๊นŒ๋‹ค๋กญ๋‹ค.

     

    ํ”„๋กœ๋ฏธ์Šค๋Š” ์ฝœ๋ฐฑ ์ง€์˜ฅ์˜ ๋ฌธ์ œ๋ฅผ ํ•ด๊ฒฐํ•  ์ˆ˜ ์žˆ๋Š” ๋น„๋™๊ธฐ ์ฒ˜๋ฆฌ๋งŒ์„ ์œ„ํ•œ ๊ธฐ๋ฒ•์ด๊ธฐ ๋•Œ๋ฌธ์— ์ฝœ๋ฐฑ ํŒจํ„ด๋ณด๋‹ค ์‚ฌ์šฉ๋ฒ•์ด ๋” ํŽธ๋ฆฌํ•˜๊ณ  ๊ฐ„ํŽธํ•˜๋‹ค๊ณ  ํ•  ์ˆ˜ ์žˆ๋‹ค. ํ”„๋กœ๋ฏธ์Šค ๋‚ด์— ์ดํ–‰ ์™„๋ฃŒ ์ƒํƒœ์ผ ๋•Œ ์‹คํ–‰ํ•˜๋Š” ํ•จ์ˆ˜, ๊ฑฐ๋ถ€๋˜์—ˆ์„ ๋•Œ ์‹คํ–‰ํ•˜๋Š” ํ•จ์ˆ˜๋ฅผ ์‚ฌ์šฉํ•œ๋‹ค๋ฉด ์—๋Ÿฌ ์ฒ˜๋ฆฌ๋„ ์ฝœ๋ฐฑ ํŒจํ„ด์„ ์‚ฌ์šฉํ–ˆ์„ ๋•Œ๋ณด๋‹ค ๊ฐ„ํŽธํ•˜๋‹ค.

     

     

     

    โœ”๏ธ ๊ฐ„ํŽธํ•œ Promise ๊ตฌํ˜„์„ ์œ„ํ•œ Fetch

    fetch๋Š” ํ”„๋กœ๋ฏธ์Šค๋ฅผ ์žฌํฌ์žฅํ•ด ๊ตฌ๋ฌธ์„ ์กฐ๊ธˆ ๋” ๊ฐ„๊ฒฐํ•˜๊ฒŒ ์‚ฌ์šฉํ•  ์ˆ˜ ์žˆ๋„๋ก ๋งŒ๋“  ๋ž˜ํผ์ด๋‹ค. ๊ธฐ์ˆ ์ ์œผ๋กœ ํ”„๋กœ๋ฏธ์Šค์™€ ๋™์ผํ•˜๋‹ค.
    ํ”„๋กœ๋ฏธ์Šค ์ธ์Šคํ„ด์Šค๋ฅผ ๋งŒ๋“ค ํ•„์š” ์—†์ด fetch ๋ฉ”์†Œ๋“œ์— ๋น„๋™๊ธฐ ์š”์ฒญ์„ ํ•  URL๋งŒ ๋„˜๊ธฐ๋ฉด ๋ฆฌํ„ด ๊ฐ’์œผ๋กœ ํ”„๋กœ๋ฏธ์Šค ์ธ์Šคํ„ด์Šค๋ฅผ ๋ฐ˜ํ™˜ํ•˜๊ธฐ ๋•Œ๋ฌธ์— then~catch๋กœ ์ˆœ์ฐจ ์ฒ˜๋ฆฌ ํ•˜๋Š” ๊ฒƒ๋„ ๊ฐ€๋Šฅํ•˜๋‹ค.

    fetch("https://www.request.com/api/data.json")
      .then((response) => {
        console.log(response);
      })
      .catch((error) => {
        console.log(error);
      });
     

    fetch๋Š” ๋น„๋™๊ธฐ ์š”์ฒญ์ด ์‹คํŒจํ–ˆ์„ ๊ฒฝ์šฐ๋งŒ catch() ๋‚ด ๊ตฌ๋ฌธ์„ ์‹คํ–‰ํ•œ๋‹ค. 404 ์—๋Ÿฌ(ํŽ˜์ด์ง€ ์—†์Œ)๋‚˜ 500 ์—๋Ÿฌ(HTTP ์ƒํƒœ)๋Š” ์‹คํ–‰์ด ์™„๋ฃŒ๋œ ๊ฒƒ์œผ๋กœ ๊ฐ„์ฃผํ•˜๊ธฐ ๋•Œ๋ฌธ์— ์ด๋Ÿฌํ•œ ์—๋Ÿฌ๋ฅผ ํ™•์ธํ•˜๊ธฐ ์œ„ํ•ด์„œ๋Š” then() ์•ˆ์—์„œ ์ƒํƒœ๋ฅผ ํ™•์ธํ•ด ๋ณ„๋„๋กœ ๊ทธ์— ๋งž๋Š” ์ฒ˜๋ฆฌ๋ฅผ ํ•ด์•ผ ํ•œ๋‹ค.

    if (response.status >= 200 && response.state <= 299) {
      // ์ •์ƒ์ ์œผ๋กœ ์™„๋ฃŒ
    } else {
      // ์—๋Ÿฌ ๋ฐœ์ƒ
    }

     

     

    โœ”๏ธ Async/Await๋ž€?

    Async/Await๋Š” ํ”„๋กœ๋ฏธ์Šค์˜ ์‚ฌ์šฉ ๋ฐฉ๋ฒ•์„ ๊ฐœ์„ ํ•˜๊ธฐ ์œ„ํ•ด ES8์—์„œ ์ƒˆ๋กญ๊ฒŒ ์†Œ๊ฐœ๋œ ๋น„๋™๊ธฐ ์ฒ˜๋ฆฌ ๋ฌธ๋ฒ•์ด๋‹ค.

    โš ๏ธ ๋”ฐ๋ผ์„œ ๊ตฌ ๋ฒ„์ „ ์›น ๋ธŒ๋ผ์šฐ์ €์—์„œ๋Š” ์ง€์›๋˜์ง€ ์•Š์œผ๋ฏ€๋กœ ์‚ฌ์šฉ ์ „ ํ˜ธํ™˜์„ฑ ํ™•์ธ์ด ํ•„์š”ํ•˜๋‹ค.

    Async ํ•จ์ˆ˜ ๋‚ด๋ถ€์—์„œ ํ”„๋กœ๋ฏธ์Šค๋ฅผ ์‚ฌ์šฉํ•ด ๋น„๋™๊ธฐ ์š”์ฒญ ๊ฒฐ๊ณผ๋ฅผ ๋ฐ˜ํ™˜ํ•œ๋‹ค.

     

    Promise์˜ ๋‹ค์ค‘ ํ”„๋กœ๋ฏธ์Šค ์ฒ˜๋ฆฌ๋ฅผ Async/Await๋ฅผ ์‚ฌ์šฉํ•ด ๋ฐ”๊ฟ” ๋ณด์ž.

    function asyncWork(value) {
      return new Promise((resolve, reject) => {
        setTimeout(() => {
          value -= 20;
          if (value > 50) {
            resolve(value);
          } else {
            reject(value);
          }
        });
      });
    }
    
    let asyncFunc = async () => {
      try {
        let res = await asyncWork(100);
        console.log("resolve1: " + res);
        res = await asyncWork(res);
        console.log("resolve2: " + res);
        res = await asyncWork(res);
        console.log("resolve3: " + res);
      } catch (error) {
        console.log("catch: " + error);
      }
    };
    
    asyncFunc();
    resolve1: 80
    resolve2: 60
    catch: 40

    Async์™€ Await๋Š” ํ•ญ์ƒ ์Œ์œผ๋กœ ์‚ฌ์šฉํ•ด์•ผ ํ•œ๋‹ค. ํ•จ์ˆ˜ ๋‚ด๋ถ€์— await๋ฅผ ์‚ฌ์šฉํ•œ๋‹ค๋ฉด ํ•จ์ˆ˜๋ฅผ ์„ ์–ธํ•  ๋•Œ async ํ•จ์ˆ˜๋กœ ์„ ์–ธํ•ด์•ผ ํ•œ๋‹ค.

    async ํ•จ์ˆ˜๋ฅผ ์‹คํ–‰ํ•˜๋ฉด async ํ•จ์ˆ˜ ์•ˆ์— ์„ ์–ธ๋œ ํ”„๋กœ๋ฏธ์Šค๊ฐ€ ์‹คํ–‰๋˜๋Š”๋ฐ, await ํ‚ค์›Œ๋“œ๊ฐ€ ์žˆ๋Š” ํ”„๋กœ๋ฏธ์Šค๋Š” ์ดํ–‰ ์™„๋ฃŒ ์ƒํƒœ๊ฐ€ ๋  ๋•Œ๊นŒ์ง€ ๋‹ค์Œ ํ–‰์˜ ์ฝ”๋“œ๋ฅผ ์‹คํ–‰ํ•˜์ง€ ์•Š๊ณ  ๋Œ€๊ธฐํ•œ๋‹ค. ์ดํ–‰ ์™„๋ฃŒ๊ฐ€ ๋˜๋ฉด ์ฝ˜์†”์— ์‘๋‹ต ๋‚ด์šฉ์„ ์ถœ๋ ฅํ•˜๊ณ  ๋‹ค์Œ ์ฝ”๋“œ๋ฅผ ์‹คํ–‰ํ•œ๋‹ค.

    ํ”„๋กœ๋ฏธ์Šค ๋น„๋™๊ธฐ ์ฝ”๋“œ์—์„œ ๊ฑฐ๋ถ€(reject)๊ฐ€ ๋ฐœ์ƒํ•˜๋ฉด try ~ catch ์ฒ˜๋ฆฌ์— ๋”ฐ๋ผ catch() ์˜ˆ์™ธ ์ฒ˜๋ฆฌ๋ฅผ ์‹คํ–‰ํ•˜๊ณ  ๋น„๋™๊ธฐ ์ฒ˜๋ฆฌ๋ฅผ ์ข…๋ฃŒํ•œ๋‹ค.

    โœ”๏ธ Async/Await์˜ ์žฅ์ 

    • ์ผ๋ฐ˜ ์ž๋ฐ”์Šคํฌ๋ฆฝํŠธ ์ฝ”๋“œ๊ฐ€ ๋™๊ธฐ์ ์œผ๋กœ ์‹คํ–‰๋˜๋Š” ๊ฒƒ๊ณผ ๊ฐ™์€ ํ˜•ํƒœ๋กœ ๋น„๋™๊ธฐ ์ฒ˜๋ฆฌ๋ฅผ ์ˆœ์ฐจ์ ์œผ๋กœ ์‹คํ–‰
    • ์ž๋ฐ”์Šคํฌ๋ฆฝํŠธ์˜ ๋™๊ธฐ์  ํ•จ์ˆ˜/์ฝ”๋“œ์™€ ์ด์งˆ๊ฐ์ด ์žˆ๋Š” ํ”„๋กœ๋ฏธ์Šค์˜ ์ฒด์ธ ๋ฐฉ์‹ ๋น„๋™๊ธฐ ์ฒ˜๋ฆฌ์™€ ์ฝœ๋ฐฑ ํ•จ์ˆ˜๋ฅผ ์ผ์ผ์ด ์ž‘์„ฑํ•ด์•ผ ํ•˜๋Š” ๋ถˆํŽธํ•จ์ด ์‚ฌ๋ผ์ง
    • Fetch๋ณด๋‹ค ๊ฐ€๋…์„ฑ์ด ์ข‹์Œ

     

    โœ”๏ธ Promise.all()

    Promise.all ๋ฉ”์†Œ๋“œ๋Š” Array์™€ ๊ฐ™์ด ์ˆœํšŒ ๊ฐ€๋Šฅํ•œ ๊ฐ์ฒด์˜ ๋ชจ๋“  ํ”„๋กœ๋ฏธ์Šค๊ฐ€ ์ดํ–‰ ์™„๋ฃŒํ•œ ํ›„ ์ดํ–‰ํ•œ ํ”„๋กœ๋ฏธ์Šค๋ฅผ ๋ฐ˜ํ™˜ํ•œ๋‹ค. ๋งŒ์ผ ํ”„๋กœ๋ฏธ์Šค ์ค‘ ํ•˜๋‚˜๊ฐ€ ๊ฑฐ๋ถ€๋œ๋‹ค๋ฉด, ์ฒซ ๋ฒˆ์งธ๋กœ ๊ฑฐ๋ถ€๋œ ํ”„๋กœ๋ฏธ์Šค๋ฅผ ์ฆ‰์‹œ ๋ฐ˜ํ™˜ํ•œ๋‹ค.

     

    Promise.all()์€ ์—ฌ๋Ÿฌ ๊ฐœ์˜ ๋น„๋™๊ธฐ ์ž‘์—…์„ ๋ณ‘๋ ฌ๋กœ ์ฒ˜๋ฆฌํ•˜๊ณ  ์‹ถ์„ ๋•Œ ์‚ฌ์šฉํ•œ๋‹ค. ์ˆœ์ฐจ์ ์œผ๋กœ ์ง„ํ–‰ํ•ด์•ผ ํ•˜๋Š” ๋น„๋™๊ธฐ ์ž‘์—…์ด ์•„๋‹ˆ๋ผ๋ฉด Promise.all()์„ ์‚ฌ์šฉํ•˜์—ฌ ํ•œ๊บผ๋ฒˆ์— ์ฒ˜๋ฆฌํ•˜๊ณ , ์‹œ๊ฐ„์„ ๋‹จ์ถ•ํ•  ์ˆ˜ ์žˆ๋‹ค.

     

     

    async function display(text, time) {
      return new Promise((resolve, reject) => {
        setTimeout(
          () =>
            typeof text === "string"
              ? resolve("string์ž…๋‹ˆ๋‹ค")
              : reject("string์ด ์•„๋‹™๋‹ˆ๋‹ค"),
          time
        );
      });
    }
    
    /* await๋ฅผ ์‚ฌ์šฉํ–ˆ์„ ๋•Œ */
    
    console.time("์†Œ์š” ์‹œ๊ฐ„");
    await display("ํƒœ๋ฆผ", 3000);
    await display("ttaerrim", 2000);
    await display("LTR", 1000);
    console.timeEnd("์†Œ์š” ์‹œ๊ฐ„");
    
    // ์†Œ์š” ์‹œ๊ฐ„: 6011.14306640625 ms
    
    /* Promise.all ์‚ฌ์šฉํ–ˆ์„ ๋•Œ */
    console.time("์†Œ์š” ์‹œ๊ฐ„");
    await Promise.all([
      display("ํƒœ๋ฆผ", 3000),
      display("ttaerrim", 2000),
      display("LTR", 1000),
    ]);
    console.timeEnd("์†Œ์š” ์‹œ๊ฐ„");
    
    // ์†Œ์š” ์‹œ๊ฐ„: 3001.381103515625 ms
    

     

    ์—๋Ÿฌ๋ฅผ ์ฒ˜๋ฆฌํ•˜๋Š” ๊ฒฝ์šฐ์—๋„ Promise.all()์˜ ๊ฒฝ์šฐ๊ฐ€ ๊ฑธ๋ฆฌ๋Š” ์‹œ๊ฐ„์ด ๋” ์งง๋‹ค.

    /* await๋ฅผ ์‚ฌ์šฉํ–ˆ์„ ๋•Œ */
    
    console.time("์†Œ์š” ์‹œ๊ฐ„");
    try {
      await display(1, 3000);
      await display(2, 2000);
      await display(3, 1000);
    } catch (error) {
      console.log(error);
    }
    console.timeEnd("์†Œ์š” ์‹œ๊ฐ„");
    
    // ์†Œ์š” ์‹œ๊ฐ„: 3002.85791015625 ms
    
    /* Promise.all ์‚ฌ์šฉํ–ˆ์„ ๋•Œ */
    console.time("์†Œ์š” ์‹œ๊ฐ„");
    try {
      await Promise.all([display(1, 3000), display(2, 2000), display(3, 1000)]);
    } catch (error) {
      console.log(error);
    }
    console.timeEnd("์†Œ์š” ์‹œ๊ฐ„");
    
    // ์†Œ์š” ์‹œ๊ฐ„: 1002.778076171875 ms
    

    ๊ฐ™์€ ๋น„๋™๊ธฐ ์ฒ˜๋ฆฌ๋ฅผ ํ•˜๋Š” ๊ฒฝ์šฐ์ด์ง€๋งŒ, await๋กœ ๊ฐ๊ฐ ์‹คํ–‰์‹œ์ผฐ์„ ๊ฒฝ์šฐ ์ฒซ ๋ฒˆ์งธ ํ•จ์ˆ˜๊ฐ€ ์‹คํ–‰๋˜๋Š” ๋ฐ ๊ฑธ๋ฆฌ๋Š” ์‹œ๊ฐ„์ธ 3์ดˆ๋ฅผ ๋ชจ๋‘ ๋‹ค ์ฑ„์šฐ๊ณ  ๋ฐ˜ํ™˜๋œ๋‹ค. Promise.all()์„ ์‚ฌ์šฉํ–ˆ์„ ๊ฒฝ์šฐ์—๋Š” ๊ฐ€์žฅ ๋นจ๋ฆฌ ์—๋Ÿฌ๋ฅผ ๋ฐ˜ํ™˜ํ•˜๋Š” ํ•จ์ˆ˜๋ฅผ ๊ธฐ์ค€์œผ๋กœ ๋™์ž‘ํ•ด ๊ฐ€์žฅ ์งง์€ ์‹œ๊ฐ„์ธ 1์ดˆ๋งŒ์— ์—๋Ÿฌ๋ฅผ ๋ฐ˜ํ™˜ํ•œ๋‹ค.

     

     

     

     

    ๐Ÿšฉ ์ฐธ๊ณ 

    ES6๋กœ ๊ธฐ์ดˆ๋ถ€ํ„ฐ ๋‹ค์‹œ ๋ฐฐ์šฐ๋Š” ์ž๋ฐ”์Šคํฌ๋ฆฝํŠธ ํŒŒ์›Œ๋ถ

    Promise.all()

    ์–ธ์ œ Promise.all์„ ์‚ฌ์šฉํ•ด์•ผ ๋ ๊นŒ?

     

    ๋Œ“๊ธ€

Designed by Tistory.