js

javascript ํ”„๋กœ๋ฏธ์Šค (Promise)

์œถโ‰ 2022. 11. 1. 17:18

* ํ”„๋กœ๋ฏธ์Šค(Promise): 

- new Promise๋กœ ์ƒ์„ฑ, ํ•จ์ˆ˜๋ฅผ ์ „๋‹ฌ๋ฐ›๋Š”๋ฐ ์—ฌ๊ธฐ์„œ ์ธ์ˆ˜๋Š” resolve์™€ reject์— ํ•ด๋‹น. 

resolve๋Š” ์„ฑ๊ณตํ•œ ๊ฒฝ์šฐ, reject๋Š” ์‹คํŒจํ–ˆ์„ ๋•Œ ๋‚˜ํƒ€๋‚˜๋Š” ํ•จ์ˆ˜. => ์ด๋ ‡๊ฒŒ ์–ด๋–ค ์ผ์ด ์™„๋ฃŒ๋˜์–ด ์‹คํ–‰๋˜๋Š” ํ•จ์ˆ˜๋ฅผ '์ฝœ๋ฐฑ(callback)ํ•จ์ˆ˜'๋ผ๊ณ  ํ•จ.

-new Promise ์ƒ์„ฑ์ž๊ฐ€ ๋ฐ˜ํ™˜ํ•˜๋Š” ํ”„๋กœ๋ฏธ์Šค ๊ฐ์ฒด๋Š” state์™€ result๋ฅผ ํ”„๋กœํผํ‹ฐ๋กœ ๋ฐ›์Œ

state : pending(๋Œ€๊ธฐ) / result: undefined

state๋Š” ์ดˆ๊ธฐ์— pending์ด์—ˆ๋‹ค๊ฐ€ resolve(value)๋กœ ํ˜ธ์ถœ( ์ฆ‰, ์„ฑ๊ณตํ•˜๋ฉด)๋˜๋ฉด 

state: fulfilled(์ดํ–‰๋จ) / result: value ๊ฐ€ ๋จ. (์ด๋•Œ์˜ result๋Š” resolve ํ•จ์ˆ˜์—์„œ ์ „๋‹ฌ๋œ ๊ฐ’.)

๋งŒ์•ฝ reject(error)๊ฐ€ ํ˜ธ์ถœ(์ฆ‰, ์‹คํŒจํ•˜๋ฉด)๋˜๋ฉด 

state: rejected(๊ฑฐ๋ถ€๋จ) / result: error ๊ฐ€ ๋จ. (์ด๋•Œ์˜ result๋Š” rejectํ•จ์ˆ˜์—์„œ ์ „๋‹ฌ๋œ ์—๋Ÿฌ.)

 

const pr = new Promise((resolve, reject) => {
  //code
});

 

์˜ˆ์‹œ1) ํŒ๋งค์ž๊ฐ€ ์ฃผ๋ฌธ์„ ํ•˜๋ฉด 3s ํ–‰๋™ ํ›„ ์„ฑ๊ณต or ์‹คํŒจ ์•Œ๋ ค์คŒ

 

ํŒ๋งค์ž์˜ ์ฝ”๋“œ - resolve์˜ ๊ฒฝ์šฐ

- state: pending -> 3์ดˆ ํ›„-> fulfilled

- result: undefined -> 3s-> 'OK'

const pr = new Promise((resolve, reject) => {
  setTimeout(()=>{
    resolve('OK')
  },3000)
});

ํŒ๋งค์ž์˜ ์ฝ”๋“œ - reject์˜ ๊ฒฝ์šฐ

- state: pending -> 3s -> rejected(๊ฑฐ๋ถ€๋จ)

- result: undefined -> 3s -> error

const pr = new Promise((resolve, reject) => {
  setTimeout(()=>{
    reject(new Error('error,,'))
  },3000)
});

*pr.then: then์„ ์ด์šฉํ•˜์—ฌ resolve์™€ reject ์ฒ˜๋ฆฌ ๊ฐ€๋Šฅ

- function(result){} : ์ดํ–‰ ๋˜์—ˆ์„ ๋•Œ ์‹คํ–‰ํ•˜๋Š” ํ•จ์ˆ˜๋กœ OK ๊ฐ’์ด ๋“ค์–ด์˜ด

- function(err){}: ๊ฑฐ๋ถ€ ๋˜์—ˆ์„ ๋•Œ ์‹คํ–‰ํ•˜๋Š” ํ•จ์ˆ˜๋กœ err ๊ฐ’์ด ๋“ค์–ด์˜ด

const pr = new Promise((resolve, reject) => {
  setTimeout(()=>{
    resolve('OK')
  },3000)
});
pr.then(
  function(result){},
  function(err){}
);

์˜ˆ์‹œ2) ์†Œ๋น„์ž์˜ ์ฝ”๋“œ

- ์—ฌ๊ธฐ์„œ๋Š” resolve๋กœ ์‹คํ–‰๋˜์—ˆ๊ธฐ ๋•Œ๋ฌธ์— ์ด ์ƒํ™ฉ์—์„œ๋Š” ๋‘๋ฒˆ์งธ ์ฝœ๋ฐฑํ•จ์ˆ˜๋Š” ์‹คํ–‰X

const pr = new Promise((resolve, reject) => {
  setTimeout(()=>{
    resolve('OK')
  },3000)
});
pr.then(
  function(result){
    console.log(result + '๊ฐ€์ง€๋Ÿฌ ๊ฐ€๊ธฐ');
  },
  function(err){
    console.log('๋‹ค์‹œ ์ฃผ๋ฌธํ•˜๊ธฐ');
  }
);

โ—Ž then ์ด์™ธ์— ์‚ฌ์šฉํ•  ์ˆ˜ ์žˆ๋Š” ๊ฒƒ์€ catch์™€ finally 

- catch: ์—๋Ÿฌ ๋ฐœ์ƒ ์‹œ reject์ธ ๊ฒฝ์šฐ ์‹คํ–‰. ๋‘๋ฒˆ์งธ๋กœ ์ „๋‹ฌํ–ˆ๋˜ ํ•จ์ˆ˜๋ฅผ catch์— ๋„ฃ์–ด ๋™์ผํ•˜๊ฒŒ ๋™์ž‘ํ•˜๊ฒŒ ํ•จ. catch๋กœ ๋ช…ํ™•ํ•˜๊ฒŒ ๊ตฌ๋ถ„ํ•ด ์ฃผ๋Š” ๊ฒƒ์ด ๊ฐ€๋…์„ฑ์—๋„ ์ข‹๊ณ  ์ฒซ๋ฒˆ์งธํ•จ์ˆ˜ ์‹คํ–‰ํ–ˆ๋‹ค๊ฐ€ ๋ฐœ์ƒํ•˜๋Š” ์—๋Ÿฌ๋ฅผ ์žก์•„์ค„ ์ˆ˜ ์žˆ๊ธฐ ๋•Œ๋ฌธ์— ์ด ์ง€๋ฌธ ์‚ฌ์šฉํ•˜๋Š” ๊ฒƒ์ด ์œ ๋ฆฌ

pr.then(
  function(result){}
).catch(
  function(err){}
)

- finally: ํ•จ์ˆ˜ ์ดํ–‰ํ•˜๊ฑฐ๋‚˜ ๊ฑฐ๋ถ€ํ•˜๊ฑฐ๋‚˜ ์ƒ๊ด€์—†์ด ์ฒ˜๋ฆฌ๊ฐ€ ์™„๋ฃŒ๋˜๋ฉด ํ•ญ์ƒ ์‹คํ–‰. ๋กœ๋”ฉํ™”๋ฉด ์—†์•จ ์‹œ ์œ ์šฉํ•˜๊ฒŒ ์‚ฌ์šฉ ๊ฐ€๋Šฅ

pr.then(
  function(result){}
).catch(
  function(err){}
).finally(
  function(){
    console.log('์ฃผ๋ฌธ์™„๋ฃŒ')
  }
)

์˜ˆ์‹œ)

- resolve

const pr = new Promise((resolve, reject) => {
  setTimeout(()=>{
    resolve('OK')
  },3000)
});
console.log("์‹œ์ž‘")
pr.then((result) => {
  console.log(result);
})
.catch((err)=>{
  console.log(err);
})
.finally(()=>{
  console.log("๋");
});
// ์‹œ์ž‘ -> OK -> ๋

- reject

const pr = new Promise((resolve, reject) => {
  setTimeout(()=>{
    reject(new Error("err,,XD"))
  },3000)
});
console.log("์‹œ์ž‘")
pr.then((result) => {
  console.log(result);
})
.catch((err)=>{
  console.log(err);
})
.finally(()=>{
  console.log("๋");
});
//์‹œ์ž‘ -> Error: err,,XD -> ๋

=> ์ดํ–‰, ๊ฑฐ๋ถ€ ์ƒ๊ด€์—†์ด ๋งˆ๋ฌด๋ฆฌ๋Š” ํ•ญ์ƒ ๋์ด ๋‚˜์˜ด

์˜ˆ์‹œ) ์ฝœ๋ฐฑํ•จ์ˆ˜ ์‚ฌ์šฉํ•ด์„œ ๋งŒ๋“ค ๊ฒฝ์šฐ

const f1 = (callback) => {
  setTimeout(function(){
    console.log("1๋ฒˆ ์ฃผ๋ฌธ ์™„๋ฃŒ");
    callback();
  },1000);
};
const f2 = (callback) => {
  setTimeout(function(){
    console.log("2๋ฒˆ ์ฃผ๋ฌธ ์™„๋ฃŒ");
    callback();
  },2000);
};
const f3 = (callback) => {
  setTimeout(function(){
    console.log("3๋ฒˆ ์ฃผ๋ฌธ ์™„๋ฃŒ");
    callback();
  },3000);
};
console.log('์‹œ์ž‘')
f1(function(){
  f2(function(){
    f3(function(){
      console.log('๋')
    });
  });
});
//์‹œ์ž‘ -> 1๋ฒˆ ์ฃผ๋ฌธ ์™„๋ฃŒ->2๋ฒˆ ์ฃผ๋ฌธ ์™„๋ฃŒ->3๋ฒˆ ์ฃผ๋ฌธ ์™„๋ฃŒ-> ๋

์˜ˆ์‹œ) ํ”„๋กœ๋ฏธ์Šค ์ฝ”๋“œ๋กœ ๊ตฌํ˜„ํ•  ๊ฒฝ์šฐ

const f1 = () =>{
  return new Promise((res,rej)=>{
    setTimeout(()=>{
      res("1๋ฒˆ ์ฃผ๋ฌธ ์™„๋ฃŒ");
    },1000);
  });
};
const f2 = (message) =>{
  console.log(message);
  return new Promise((res,rej)=>{
    setTimeout(()=>{
      res("2๋ฒˆ ์ฃผ๋ฌธ ์™„๋ฃŒ");
    },2000);
  });
};
const f3 = (message) =>{
  console.log(message);
  return new Promise((res,rej)=>{
    setTimeout(()=>{
      res("3๋ฒˆ ์ฃผ๋ฌธ ์™„๋ฃŒ");
    },3000);
  });
};

console.log('์‹œ์ž‘');
f1()
.then((res) => f2(res))
.then((res) => f3(res))
.then((res) => console.log(res))
.catch(console.log)
.finally(()=>{
  console.log("๋")
});
//์‹œ์ž‘ -> 1๋ฒˆ ์ฃผ๋ฌธ ์™„๋ฃŒ->2๋ฒˆ ์ฃผ๋ฌธ ์™„๋ฃŒ->3๋ฒˆ ์ฃผ๋ฌธ ์™„๋ฃŒ-> ๋

=> ํ”„๋กœ๋ฏธ์Šค ์ฒด์ด๋‹(Promise chaining): ํ”„๋กœ๋ฏธ์Šค๋ผ๋ฆฌ ์—ฐ๊ฒฐ

์˜ˆ์‹œ) ์ค‘๊ฐ„์— ์‹คํŒจํ•˜๋Š” ๊ฒฝ์šฐ

- 2๋ฒˆ์—์„œ ์‹คํŒจ ๋˜์–ด xxx๊ฐ€ ๋œจ๊ณ  ๋ฐ”๋กœ finally๋กœ ๋๋‚จ

const f1 = () =>{
  return new Promise((res,rej)=>{
    setTimeout(()=>{
      res("1๋ฒˆ ์ฃผ๋ฌธ ์™„๋ฃŒ");
    },1000);
  });
};
const f2 = (message) =>{
  console.log(message);
  return new Promise((res,rej)=>{
    setTimeout(()=>{
      rej("xxx");
    },2000);
  });
};
const f3 = (message) =>{
  console.log(message);
  return new Promise((res,rej)=>{
    setTimeout(()=>{
      res("3๋ฒˆ ์ฃผ๋ฌธ ์™„๋ฃŒ");
    },3000);
  });
};

console.log('์‹œ์ž‘');
f1()
.then((res) => f2(res))
.then((res) => f3(res))
.then((res) => console.log(res))
.catch(console.log)
.finally(()=>{
  console.log("๋")
});
//์‹œ์ž‘ -> 1๋ฒˆ ์ฃผ๋ฌธ ์™„๋ฃŒ->xxx-> ๋

* Promise.all: ํ•œ๊บผ๋ฒˆ์— ์‹œ์ž‘ํ•˜๊ณ  ๋ชจ๋‘ ์ดํ–‰๋˜๋ฉด ๊ฐ’์„ ์‚ฌ์šฉํ•  ์ˆ˜ ์žˆ์–ด ์‹œ๊ฐ„ ์ ˆ์•ฝํ•  ์ˆ˜ ์žˆ์Œ. ๊ฐ ํ”„๋กœ๋ฏธ์Šค๋กœ ๋„˜๊ฒจ์ค€ ๊ฐ’์„ ๋ฐฐ์—ด๋กœ ๋ฐ›๋Š”๋ฐ ์—ฌ๊ธฐ์„œ๋Š”  3 ์ž‘์—…์ด ๋ชจ๋‘ ์™„๋ฃŒ ๋˜์–ด์•ผ then ๋ถ€๋ถ„์ด ์‹คํ–‰๋จ

const f1 = () =>{
  return new Promise((res,rej)=>{
    setTimeout(()=>{
      res("1๋ฒˆ ์ฃผ๋ฌธ ์™„๋ฃŒ");
    },1000);
  });
};
const f2 = (message) =>{
  console.log(message);
  return new Promise((res,rej)=>{
    setTimeout(()=>{
      res("2๋ฒˆ ์ฃผ๋ฌธ ์™„๋ฃŒ");
    },3000);
  });
};
const f3 = (message) =>{
  console.log(message);
  return new Promise((res,rej)=>{
    setTimeout(()=>{
      res("3๋ฒˆ ์ฃผ๋ฌธ ์™„๋ฃŒ");
    },2000);
  });
};
//Promise.all
Promise.all([f1(),f2(),f3()]).then((res)=>{
  console.log(res);
})
//(3) ['1๋ฒˆ ์ฃผ๋ฌธ ์™„๋ฃŒ', '2๋ฒˆ ์ฃผ๋ฌธ ์™„๋ฃŒ', '3๋ฒˆ ์ฃผ๋ฌธ ์™„๋ฃŒ']

- timeEnd๋ฅผ ์ด์šฉํ•ด ์ด ๊ฑธ๋ฆฐ ์‹œ๊ฐ„์„ ์•Œ์•„๋‚ผ ์ˆ˜ ์žˆ์Œ.

console.time("x");
Promise.all([f1(),f2(),f3()]).then((res)=>{
  console.log(res);
  console.timeEnd("x")
})
//(3) ['1๋ฒˆ ์ฃผ๋ฌธ ์™„๋ฃŒ', '2๋ฒˆ ์ฃผ๋ฌธ ์™„๋ฃŒ', '3๋ฒˆ ์ฃผ๋ฌธ ์™„๋ฃŒ']
//x: 3077.184814453125 ms


โ—Ž reject๋กœ ์‹คํ–‰ํ•  ๊ฒฝ์šฐ: ์—๋Ÿฌ ๋ฐœ์ƒํ•˜๊ณ  ์–ด๋– ํ•œ ๊ฐ’๋„ ์–ป์ง€ ๋ชปํ•จ. ํ”„๋กœ๋ฏธ์Šค ์˜ฌ์€ ํ•˜๋‚˜์˜ ์ •๋ณด๋ผ๋„ ๋ˆ„๋ฝ๋˜๋ฉด ํŽ˜์ด์ง€๋ฅผ ๋ณด์—ฌ์ค„ ์ˆ˜ ์—†๋Š” ๊ฒฝ์šฐ ์‚ฌ์šฉ๋จ(๋‹ค ๋ณด์—ฌ์ฃผ๊ฑฐ๋‚˜ ์•ˆ ๋ณด์—ฌ์ฃผ๊ฑฐ๋‚˜ ํ•  ๋•Œ)

const f1 = () =>{
  return new Promise((res,rej)=>{
    setTimeout(()=>{
      // res("1๋ฒˆ ์ฃผ๋ฌธ ์™„๋ฃŒ");
      rej(new Error("xxx"));
    },1000);
  });
};
const f2 = (message) =>{
  console.log(message);
  return new Promise((res,rej)=>{
    setTimeout(()=>{
      res("2๋ฒˆ ์ฃผ๋ฌธ ์™„๋ฃŒ");
    },3000);
  });
};
const f3 = (message) =>{
  console.log(message);
  return new Promise((res,rej)=>{
    setTimeout(()=>{
      res("3๋ฒˆ ์ฃผ๋ฌธ ์™„๋ฃŒ");
    },2000);
  });
};
//Promise.all
console.time("x");
Promise.all([f1(),f2(),f3()]).then((res)=>{
  console.log(res);
  console.timeEnd("x")
})
// ์—๋Ÿฌ ๋ฐœ์ƒ

*Promise.race: ์‚ฌ์šฉ๋ฐฉ๋ฒ•์€ promise.all๊ณผ ๋™์ผ. promise.all์€ ๋ชจ๋“  ์ž‘์—…์ด ์™„๋ฃŒ๋  ๋•Œ ๊นŒ์ง€ ๊ธฐ๋‹ค๋ฆฌ์ง€๋งŒ race๋Š” ๋ง ๊ทธ๋Œ€๋กœ ๊ฒฝ์ฃผ๋ผ์„œ ํ•˜๋‚˜๋ผ๋„ ๋จผ์ € ์™„๋ฃŒ๋˜๋ฉด ์ž‘์—…์„ ๋๋ƒ„. ์šฉ๋Ÿ‰์ด ํฐ ์ด๋ฏธ์ง€๋“ค์„ ๋กœ๋”ฉํ•˜๋Š”๋ฐ ๊ทธ ์ค‘ ํ•˜๋‚˜๋ผ๋„ ์™„๋ฃŒ๋˜๋ฉด ๊ทธ ์ด๋ฏธ์ง€๋ฅผ ๋ณด์—ฌ์ค„ ๋•Œ ์‚ฌ์šฉ.

const f1 = () =>{
  return new Promise((res,rej)=>{
    setTimeout(()=>{
      res("1๋ฒˆ ์ฃผ๋ฌธ ์™„๋ฃŒ");
    },1000);
  });
};
const f2 = (message) =>{
  console.log(message);
  return new Promise((res,rej)=>{
    setTimeout(()=>{
      // res("2๋ฒˆ ์ฃผ๋ฌธ ์™„๋ฃŒ");
      rej(new Error("xxx"));
    },3000);
  });
};
const f3 = (message) =>{
  console.log(message);
  return new Promise((res,rej)=>{
    setTimeout(()=>{
      res("3๋ฒˆ ์ฃผ๋ฌธ ์™„๋ฃŒ");
    },2000);
  });
};
//Promise.race
console.time("x");
Promise.race([f1(),f2(),f3()]).then((res)=>{
  console.log(res);
  console.timeEnd("x")
})
// 1๋ฒˆ ์ฃผ๋ฌธ ์™„๋ฃŒ
// x: 1058.05078125 ms

'js' ์นดํ…Œ๊ณ ๋ฆฌ์˜ ๋‹ค๋ฅธ ๊ธ€

javascript Generator  (0) 2022.11.02
javascript async, await  (0) 2022.11.01
javascript ํด๋ž˜์Šค(class)  (0) 2022.11.01
javascript ์ƒ์†, ํ”„๋กœํ† ํƒ€์ž…(Prototype)  (0) 2022.10.31
javascript ๋ฉ”์„œ๋“œ call, apply, bind  (0) 2022.10.31