[TIL] 0704 | React with Redux, Next.js, TypeScript

Teasanยท2022๋…„ 7์›” 4์ผ
0

TIL

๋ชฉ๋ก ๋ณด๊ธฐ
20/36
post-thumbnail

๋ชฉ์ฐจ

  • ๋กœ๋”ฉ State ๋‹ค๋ฃจ๊ธฐ
  • ์˜ค๋ฅ˜ ์ฒ˜๋ฆฌํ•˜๊ธฐ

โœง ๋กœ๋”ฉ State ๋‹ค๋ฃจ๊ธฐ

  • isLoding ์ƒํƒœ(state) ๋งŒ๋“ค๊ณ , ์ดˆ๊ธฐ๊ฐ’์„ true๋กœ ์„ค์ •ํ•˜๊ธฐ.
const [isLoding, setIsLoading] = useState(true);
  • ๋ฐ์ดํ„ฐ๋ฅผ ๋ฐ›์•„์˜ค๊ณ  ์žˆ๋Š” useEffect ๋‚ด๋ถ€์˜ fetchMeals ํ•จ์ˆ˜์—์„œ ๋ชจ๋“  ๋ฐ์ดํ„ฐ ๋กœ๋”ฉ์ด ๋๋‚˜๋ฉด setIsLoading ์ƒํƒœ ์—…๋ฐ์ดํŠธ ํ•จ์ˆ˜๋ฅผ ์‚ฌ์šฉํ•ด์„œ false๋กœ ์—…๋ฐ์ดํŠธํ•˜๊ธฐ.
useEffect(() => {
  const fetchMeals = async () => {
    const response = await fetch(
      "https://react-http2-xxxxxxxxx.firebaseio.com/meals.json"
    );
    const responseData = await response.json();

    const loadedMeals = [];

    for (const key in responseData) {
      loadedMeals.push();
    }

    setMeals(loadedMeals);
    setIsLoading(false);
  };

  fetchMeals();
}, []);
  • isLoding ์ƒํƒœ ๊ฐ’์„ ์ด์šฉํ•˜์—ฌ ๋กœ๋”ฉ ์ค‘์ž„์„ ์•Œ๋ฆฌ๋Š” ๋งˆํฌ์—… ์ฝ”๋“œ๋ฅผ mealsList ์ปดํฌ๋„ŒํŠธ ์œ„์— ์ž‘์„ฑ.
if (isLoding) {
  return (
    <section className={classes.MealsLoading}>
      <p>Loding...</p>
    </section>
  );
}

const mealsList = meals.map((item) => (
  <MealItem
    key={item.id}
    id={item.id}
    name={item.name}
    description={item.description}
    price={item.price}
  />
));
  • ๋กœ๋”ฉ ์ค‘์ž„์„ ์•Œ๋ฆฌ๋Š” <section> ์— ์Šคํƒ€์ผ์„ ์ž…ํžŒ๋‹ค.
.MealsLoading {
  text-align: center;
  color: white;
}
  • ์ €์žฅํ•˜๊ณ  ํ™•์ธํ•ด๋ณด๋ฉด,

ezgif com-gif-maker - 2022-06-29T182010 608

  • ์ƒˆ๋กœ๊ณ ์นจ์„ ํ•  ๋•Œ๋งˆ๋‹ค "Loding..." ํ…์ŠคํŠธ๊ฐ€ ์ž ๊น ๋ณด์˜€๋‹ค๊ฐ€ ์‚ฌ๋ผ์ง€๋Š” ๊ฑธ ๋ณผ ์ˆ˜ ์žˆ๋‹ค. (ํŒŒ์ด์–ด๋ฒ ์ด์Šค๊ฐ€ ๋น ๋ฅธ ๋ฐฑ์—”๋“œ๋ฅผ ๊ฐ€์ง€๊ณ  ์žˆ๊ธฐ ๋•Œ๋ฌธ์— ์•„์ฃผ ์ž ์‹œ ๋™์•ˆ๋งŒ ๊นœ๋นก์ธ๋‹ค.)

โœง ์˜ค๋ฅ˜ ์ฒ˜๋ฆฌํ•˜๊ธฐ

  • error๋ฅผ ์ฒ˜๋ฆฌํ•˜๋Š” ๋ฐฉ๋ฒ•์„ ํ•™์Šตํ•˜๊ธฐ ์œ„ํ•ด์„œ ์˜ค๋ฅ˜๋ฅผ ํ•œ ๋ฒˆ ์‹œ๋ฎฌ๋ ˆ์ด์…˜ ํ•ด๋ณผ ๊ฒƒ์ด๋‹ค. ์•„๋ž˜๋Š” ์šฐ๋ฆฌ๊ฐ€ ๋ฐ์ดํ„ฐ๋ฅผ ์„ฑ๊ณต์ ์œผ๋กœ ๋ฐ›์•„์˜ค๋„๋ก ๋งŒ๋“ค์—ˆ๋˜ useEffect ๋กœ์ง์ด๋‹ค.
useEffect(() => {
  const fetchMeals = async () => {
    const response = await fetch(
      "https://react-http2-xxxxxxxxx.firebaseio.com/meals.json"
    );
    const responseData = await response.json();

    const loadedMeals = [];

    for (const key in responseData) {
      loadedMeals.push();
    }

    setMeals(loadedMeals);
    setIsLoading(false);
  };

  fetchMeals();
}, []);
  • ํŒŒ์ด์–ด๋ฒ ์ด์Šค์—์„œ ์š”๊ตฌํ•˜๋Š” ํ˜•์‹์ธ .json์„ ์ฃผ์†Œ์—์„œ ์‚ญ์ œํ•˜๊ณ  ์ €์žฅํ•œ ๋’ค ํ™•์ธํ•ด๋ณด๋ฉด,
useEffect(() => {
  const fetchMeals = async () => {
    const response = await fetch(
      "https://react-http2-xxxxxxxxx.firebaseio.com/meals"
    );
    const responseData = await response.json();

    const loadedMeals = [];

    for (const key in responseData) {
      loadedMeals.push();
    }

    setMeals(loadedMeals);
    setIsLoading(false);
  };

  fetchMeals();
}, []);

ezgif com-gif-maker - 2022-06-29T182608 692

  • ๋ฐ์ดํ„ฐ๋ฅผ ๋กœ๋”ฉํ•˜๋Š” ๋ฐ ์‹คํŒจํ•˜๊ฒŒ ๋œ๋‹ค. ์•ฑ์—์„œ๋Š” "Loding..." ์ด๋ผ๋Š” ๋กœ๋”ฉ ์ค‘์ผ ๋•Œ ํ™”๋ฉด์— ์ถœ๋ ฅ๋˜๋Š” ํ…์ŠคํŠธ๋งŒ ํ™•์ธํ•  ์ˆ˜ ์žˆ๋‹ค. ๋ณดํ†ต์€ ์ฝ˜์†”์—์„œ ์ด ๋ฐ์ดํ„ฐ๋ฅผ ๊ฐ€์ ธ์˜ค๋Š”๋ฐ ์‹คํŒจํ–ˆ๋‹ค๋Š” ๋ฉ”์„ธ์ง€๋ฅผ ๋ณด์—ฌ์ฃผ๊ฒ ์ง€๋งŒ ์‚ฌ์šฉ์ž๋“ค์€ ์ฝ˜์†”์„ ์‚ฌ์šฉํ•ด์„œ ์—๋Ÿฌ ๋ฉ”์„ธ์ง€๋ฅผ ํ™•์ธํ• ๋ฆฌ ๋งŒ๋ฌดํ•˜๋‹ค. ๊ทธ๋ ‡๋‹ค๋ฉด ์šฐ๋ฆฌ๋Š” ์–ด๋–ป๊ฒŒ ํ•ด์•ผํ• ๊นŒ? ์–ด๋–ป๊ฒŒ ์‚ฌ์šฉ์ž๋“ค์—๊ฒŒ ์—๋Ÿฌ๋ฅผ ์•Œ๋ ค์ค„ ์ˆ˜ ์žˆ๋Š” ๊ฒƒ์ผ๊นŒ?

์˜ค๋ฅ˜๋ฅผ ํ‘œ์‹œํ•˜๋Š” ๋ฐฉ๋ฒ•

  • error๋ฅผ ํ‘œ์‹œํ•˜๋Š” ๋ฐฉ๋ฒ•์—๋Š” ์—ฌ๋Ÿฌ๊ฐ€์ง€๊ฐ€ ์žˆ๋‹ค. ์ฆ‰, ์šฐ๋ฆฌ๊ฐ€ ์„ ํƒํ•˜๊ธฐ ๋‚˜๋ฆ„์ด๋ผ๋Š” ๊ฒƒ์ด๋‹ค. ์ด๋ฒˆ์—๋Š” "Loding..." ์ฒ˜๋Ÿผ ๋ฉ”์„ธ์ง€๋กœ ์—๋Ÿฌ ๋ฉ”์„ธ์ง€๋ฅผ ํ‘œ์‹œํ•˜๋ ค๊ณ  ํ•œ๋‹ค. ๋”ฐ๋ผ์„œ ์šฐ๋ฆฌ๊ฐ€ ํ•„์š”ํ•œ ๊ฒƒ์€ ์—๋Ÿฌ๊ฐ€ ๋ฐœ์ƒํ•  ๋•Œ๋งˆ๋‹ค ์—…๋ฐ์ดํŠธ๋˜์–ด ์‚ฌ์šฉํ•  ์ˆ˜ ์žˆ๋Š” ์ƒํƒœ(state) ๊ฐ’์ด๋‹ค.
const [httpError, setHttpError] = useState(null);
  • httpError ์ƒํƒœ๋ฅผ ์ƒ์„ฑํ•˜๊ณ , ์ดˆ๊ธฐ ๊ฐ’์„ ๋น„์›Œ๋‘๊ฑฐ๋‚˜ ์•„์˜ˆ null๋กœ ์„ค์ •ํ•ด์„œ ์ฒ˜์Œ์— ๊ฐ’์„ ๊ฐ–์ง€ ์•Š๋Š”๋‹ค๋Š” ๋ชฉ์ ์„ ๋” ๋ถ„๋ช…ํžˆ ํ•ด๋‘๋Š” ๊ฒƒ๋„ ์ข‹์„ ๊ฒƒ์ด๋‹ค. ์ด์ œ ๋ฐ์ดํ„ฐ๋ฅผ ๊ฐ€์ ธ์˜ค๋Š”๋ฐ ์‹คํŒจํ–ˆ์„ ๋•Œ์˜ ์˜ค๋ฅ˜๋ฅผ ์„ค์ •ํ•˜์ž.
useEffect(() => {
  const fetchMeals = async () => {
    const response = await fetch(
      "https://react-http2-xxxxxxxxx.firebaseio.com/meals"
    );

    if (!response.ok) {
    }

    const responseData = await response.json();

    const loadedMeals = [];

    for (const key in responseData) {
      loadedMeals.push();
    }

    setMeals(loadedMeals);
    setIsLoading(false);
  };

  fetchMeals();
}, []);
  • ์ด ๊ฒฝ์šฐ, ์šฐ์„  ์‹คํŒจ ์—ฌ๋ถ€๋ฅผ ํ™•์ธํ•ด์•ผ ํ•˜๊ธฐ ๋•Œ๋ฌธ์—, if ๋ฌธ์„ ์ž‘์„ฑํ•˜๊ณ  ๋‚ด๋ถ€์— !response.ok ๋ผ๋Š” ์กฐ๊ฑด์„ ๋„ฃ๋Š”๋‹ค. ok๊ฐ€ truthy ์ธ ๊ฒฝ์šฐ๋ฅผ ๋งํ•˜๊ธฐ ๋•Œ๋ฌธ์— ๋Š๋‚Œํ‘œ๋ฅผ ๋„ฃ์–ด์„œ falsy๋กœ ๋งŒ๋“ค๊ณ , response๊ฐ€ ok ๋˜์ง€ ์•Š์•˜์„ ๋•Œ ์ฆ‰, ๋ฐ์ดํ„ฐ๋ฅผ ๋ฐ›์•„์˜ค๋Š”๋ฐ ์‹คํŒจํ–ˆ์„ ๋•Œ๋ฅผ ๊ฐ€์ •ํ•˜๊ณ  ๋กœ์ง์„ ์ž‘์„ฑํ•œ๋‹ค.
if (!response.ok) {
  throw new Error("Something went wrong!");
}

throw new Error()๋Š” ์ค„์ด ์‹คํ–‰๋˜์ง€ ์•Š๋Š”๋‹ค๋Š” ๊ฒƒ์„ ์˜๋ฏธํ•œ๋‹ค.

  • ๋งŒ์•ฝ !response.ok๋ผ๋ฉด(๋ฐ์ดํ„ฐ๋ฅผ ๋ฐ›์•„์˜ค๋Š”๋ฐ ์‹คํŒจํ–ˆ๋‹ค๋ฉด) throw new Error()๋ฅผ ์ž‘์„ฑํ•ด์„œ ์ƒˆ๋กœ์šด ์˜ค๋ฅ˜๋ฅผ ์ƒ์„ฑํ•˜๊ณ  ์ด ์—๋Ÿฌ์— ์ผ๋ฐ˜์ ์ธ ์˜ค๋ฅ˜ ๋ฉ”์„ธ์ง€("Something went wrong!")๋ฅผ ํ• ๋‹นํ•œ๋‹ค. ์ด์ œ ์ด ๋งŒ๋“ค์–ด์ง„ ์ƒˆ๋กœ์šด error๋ฅผ ๊ฐ€์ง€๊ณ  ํ•ธ๋“ค๋ง์„ ํ•ด์•ผํ•œ๋‹ค.

  • ์šฐ๋ฆฌ๋Š” ์—ฌ๊ธฐ์„œ fetch ๋กœ์ง์„ ๋žฉํ•‘ ํ•˜๊ธฐ ์œ„ํ•ด ๋ณ„๋„์˜ ํ•จ์ˆ˜(fetchMeals)๋ฅผ ์‚ฌ์šฉํ•˜๋Š” ๊ฒƒ์— ๋Œ€ํ•œ ๋˜ ๋‹ค๋ฅธ ์žฅ์ ์„ ์•Œ ์ˆ˜ ์žˆ๋‹ค. fetchMeals ํ•จ์ˆ˜๋Š” ์š”์ฒญ์„ ๋ณด๋‚ผ ๋•Œ ๋ฌธ์ œ๊ฐ€ ์ƒ๊ธฐ๋ฉด ์—๋Ÿฌ ๋ฉ”์„ธ์ง€๋ฅผ ๋ฐœ์ƒ์‹œํ‚ฌ ๊ฒƒ์ด๋‹ค. ๋”ฐ๋ผ์„œ fetchMeals๋กœ ์ด๋™ํ•ด์„œ ๋ฌด์–ธ๊ฐ€๋ฅผ ์ถ”๊ฐ€ํ•ด์•ผ๋งŒ ํ•œ๋‹ค.

useEffect(() => {
  const fetchMeals = async () => {
    const response = await fetch(
      "https://react-http2-xxxxxxxxx.firebaseio.com/meals"
    );

    if (!response.ok) {
      throw new Error("Something went wrong!");
    }

    const responseData = await response.json();
    const loadedMeals = [];

    for (const key in responseData) {
      loadedMeals.push();
    }

    setMeals(loadedMeals);
    setIsLoading(false);
  };

  try {
  } catch {}

  fetchMeals();
}, []);
  • fetchMeals() ํ•จ์ˆ˜๋ฅผ ํ˜ธ์ถœํ•˜๋Š” ์ค„์€ useEffect ์•ˆ์— ์žˆ์ง€๋งŒ fetchMeals ํ•จ์ˆ˜์˜ ์™ธ๋ถ€์— ์žˆ๋‹ค. ๊ทธ๋ฆฌ๊ณ  ์ด๊ฒƒ์„ ์šฐ๋ฆฌ๋Š” try/catch๋กœ ๋ž˜ํ•‘ํ•  ์ˆ˜ ์žˆ๊ฒŒ ๋œ๋‹ค.

try/catch ๋Š” try(์‹œ๋„ํ•˜๊ธฐ)ํ•ด์„œ catch(์žก๊ธฐ)ํ•œ๋‹ค๋Š” ์˜๋ฏธ์ด๋‹ค.

try {
  fetchMeals();
} catch {}
  • try(์‹œ๋„ํ•˜๊ธฐ) ๋กœ์ง ์•ˆ์—์„œ fetchMeals ํ•จ์ˆ˜๋ฅผ ํ˜ธ์ถœํ•˜๊ณ , fetchMeals ํ•จ์ˆ˜ ๋‚ด๋ถ€์—์„œ ์˜ค๋ฅ˜๊ฐ€ ๋ฐœ์ƒํ•œ๋‹ค๋ฉด catch(์žก๊ธฐ) ๋ธ”๋ก ์•ˆ์—์„œ ๋ฌด์–ธ๊ฐ€๋ฅผ ์ฒ˜๋ฆฌํ•˜๋„๋ก ํ•œ๋‹ค.
try {
  fetchMeals();
} catch {
  setIsLoading(false);
}
  • catch ๋ธ”๋ก ์•ˆ์—์„œ setIsLoading(false) ๋กœ ์ฒ˜๋ฆฌํ•œ๋‹ค. fetchMeals() ํ•จ์ˆ˜๋ฅผ try(์‹œ๋„) ํ–ˆ๋Š”๋ฐ, ์˜ค๋ฅ˜๊ฐ€ ๋ฐœ์ƒํ•œ๋‹ค๋ฉด ๋กœ๋”ฉ์„ ๋ฉˆ์ถ”๊ณ (setIsLoading(false)), ๋ญ”๊ฐ€์˜ ์—๋Ÿฌ ๋ฉ”์„ธ์ง€๋ฅผ ์ฒ˜๋ฆฌํ•˜๋„๋ก ํ•ด์•ผ๋˜๊ธฐ ๋•Œ๋ฌธ์ด๋‹ค.
try {
  fetchMeals();
} catch (error) {
  setIsLoading(false);
  setHttpError(error.message);
}
  • ์—๋Ÿฌ๋ฅผ ์„ค์ •ํ•˜๊ธฐ ์œ„ํ•ด setHttpError๋ฅผ ํ˜ธ์ถœํ•˜๊ณ  ์šฐ๋ฆฌ๊ฐ€ catch(์žก์€)ํ•œ ์˜ค๋ฅ˜ ๋ฉ”์„ธ์ง€(error.message)๋ฅผ ๋ณด์—ฌ์ฃผ๋„๋ก ํ•œ๋‹ค. ๊ทธ๋Ÿผ try/catch๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ์ด error์— ์ ‘๊ทผํ•  ์ˆ˜ ์žˆ๊ฒŒ ๋˜๋ฉฐ httpError ์ƒํƒœ(state)์— ์šฐ๋ฆฌ๊ฐ€ ์ด๋ฅผ ํ†ตํ•ด์„œ ์žก๊ฒŒ ๋œ error์— ๋Œ€ํ•ด ์„ค์ •ํ•  ์ˆ˜ ์žˆ๊ฒŒ ๋˜๋Š” ๊ฒƒ์ด๋‹ค. ๋” ์ •ํ™•ํ•˜๊ฒŒ๋Š” error.message์— ์ ‘๊ทผํ•˜๊ณ  ์„ค์ •ํ•  ์ˆ˜ ์žˆ๋‹ค๋Š” ๋œป์ด๋‹ค.
if (!response.ok) {
  throw new Error("Something went wrong!");
}
  • ์šฐ๋ฆฌ๋Š” catch๋ฅผ ํ†ตํ•ด์„œ error ๊ฐ์ฒด๋ฅผ ์–ป๊ฒŒ ๋˜์—ˆ๊ณ , ์ด error ๊ฐ์ฒด๋Š” ๋””ํดํŠธ๋กœ message ์†์„ฑ์„ ๊ฐ€์ง€๊ฒŒ ๋œ๋‹ค. throw new Error()๋ฅผ ํ†ตํ•ด์„œ error๋ฅผ ์ƒ์„ฑํ•˜๊ณ  ์ƒ์„ฑ์ž์— ๋ฌธ์ž์—ด("Something went wrong!")์„ ์ž…๋ ฅํ•˜๋ฉด ์ƒ์„ฑ๋œ error ๊ฐ์ฒด์˜ message ์†์„ฑ์— ํ•ด๋‹น ๋ฌธ์ž์—ด์ด ์ €์žฅ๋  ๊ฒƒ์ด๋‹ค.
if (isLoding) {
  return (
    <section className={classes.MealsLoading}>
      <p>Loding...</p>
    </section>
  );
}

if (httpError) {
  return (
    <section>
      <p></p>
    </section>
  );
}
  • ์ด์ œ httpError ์ƒํƒœ๋ฅผ ์„ค์ •ํ•ด์•ผ ํ•œ๋‹ค. if ๋ฌธ์„ ํ†ตํ•ด์„œ httpError ์ƒํƒœ ๊ฐ’์ด ๋น„์›Œ์ ธ ์žˆ์ง€ ์•Š๋‹ค๋ฉด ์ฆ‰, ์šฐ๋ฆฌ๊ฐ€ throw new Error()๋กœ ์ €์žฅํ•œ "Something went wrong!"๊ฐ€ httpError ์ƒํƒœ ์•ˆ์— ๋“ค์–ด์žˆ๋‹ค๋ฉด ๋ถ„๋ช… ์—๋Ÿฌ๊ฐ€ ๋ฐœ์ƒํ—€์„ ๊ฒฝ์šฐ์ผ ๊ฒƒ์ด๊ณ  ์ด์— ๋Œ€ํ•œ ๋กœ์ง์„ ์ž‘์„ฑํ•ด์•ผ ํ•  ๊ฒƒ์ด๋‹ค.
if (httpError) {
  return (
    <section>
      <p>{httpError}</p>
    </section>
  );
}
  • httpError ์— ์ €์žฅ๋œ ๋ฉ”์„ธ์ง€๋ฅผ ์ถœ๋ ฅํ•˜๋„๋ก <p> ํƒœ๊ทธ ์•ˆ์— httpError ์ƒํƒœ๋ฅผ ๋„ฃ์–ด๋‘๊ณ ,
if (httpError) {
  return (
    <section className={classes.MealsError}>
      <p>{httpError}</p>
    </section>
  );
}
  • ์—๋Ÿฌ ์ƒํƒœ์ž„์„ ์•Œ๋ฆฌ๋„๋ก <section> ์— ์Šคํƒ€์ผ์„ ์ž…ํžŒ๋‹ค.
.MealsError {
  text-align: center;
  color: red;
}
  • ์ €์žฅํ•˜๊ณ , ๋‹ค์‹œ ์ƒˆ๋กœ๊ณ ์นจ์„ ํ•ด๋ณด๋ฉด ์—ฌ์ „ํžˆ "Loding..." ๋งŒ ํ‘œ์‹œ๋˜๊ณ  ์žˆ๋Š” ๊ฑธ ์•Œ ์ˆ˜ ์žˆ๋‹ค. ์™œ ๊ทธ๋Ÿด๊นŒ?
try {
  fetchMeals().catch();
} catch {
  setIsLoading(false);
}
  • ์ด๋Ÿฐ ๋ถ€๋ถ„์„ ์žก์•„๋‚ด๋Š” ๊ฒƒ์€ ๊ฝค๋‚˜ ๊นŒ๋‹ค๋กœ์šธ ์ˆ˜ ์žˆ๋‹ค. ์ด์— ๊ด€ํ•œ ์ด์œ ๋ฅผ ์ดํ•ดํ•˜๊ธฐ ์œ„ํ•ด์„œ๋Š” ์šฐ๋ฆฌ๊ฐ€ try/catch๋ฅผ ์‚ฌ์šฉํ•˜๊ณ  ์žˆ์ง€๋งŒ fetchMeals ๋Š” async ํ•จ์ˆ˜ ๋ผ๋Š” ์‚ฌ์‹ค์„ ๊ธฐ์–ตํ•ด์•ผ ํ•  ๊ฒƒ์ด๋‹ค.

fetchMeals ๋Š” async ํ•จ์ˆ˜์ด๋‹ค.

useEffect(() => {
  const fetchMeals = async () => {
    const response = await fetch(
      "https://react-http2-xxxxxxxxx.firebaseio.com/meals"
    );

    if (!response.ok) {
      throw new Error("Something went wrong!");
    }

    const responseData = await response.json();
    const loadedMeals = [];

    for (const key in responseData) {
      loadedMeals.push();
    }

    setMeals(loadedMeals);
    setIsLoading(false);
  };

  try {
    fetchMeals().catch();
  } catch {
    setIsLoading(false);
  }
}, []);
  • fetchMeals ๋Š” async ํ•จ์ˆ˜์ด๋‹ค. ์ด๊ฒƒ์ด ๋ฌด์Šจ ๋œป์ด๋ƒ ํ•˜๋ฉด, ์–ธ์ œ๋‚˜ ์ด ํ•จ์ˆ˜๋Š” promise๋ฅผ ๋ฐ˜ํ™˜ํ•œ๋‹ค๋Š” ๊ฒƒ์ด๋‹ค. promise ๋Œ€์‹  error๋ฅผ ๊ฐ€์ ธ์˜ค๋Š” ๊ฒฝ์šฐ ๊ทธ ์˜ค๋ฅ˜๋กœ ์ธํ•ด ํ•ด๋‹น promise๊ฐ€ ๊ฑฐ๋ถ€ํ•˜๊ฒŒ ๋˜๊ณ , ๋”ฐ๋ผ์„œ ์šฐ๋ฆฌ์˜ try/catch๋ฅผ ์‚ฌ์šฉํ•ด์„œ ๊ทธ๊ฒƒ์„ ๋ž˜ํ•‘ํ•  ์ˆ˜ ์—†๊ฒŒ ๋˜๋Š” ๊ฒƒ์ด๋‹ค. ๊ทธ๋ ‡๋‹ค๋ฉด ์šฐ๋ฆฌ๋Š” ์–ด๋–ป๊ฒŒ ํ•ด๊ฒฐํ•ด์•ผ ํ• ๊นŒ? ๋ฐฉ๋ฒ•์€ ๊ฐ„๋‹จํ•˜๋‹ค.
try {
  fetchMeals().catch(() => {});
} catch {
  setIsLoading(false);
  setHttpError(error.message);
}
  • ๋ฐ”๋กœ try/catch๋กœ ๋ž˜ํ•‘ํ•œ ๊ฒƒ์„ ๋ณ„๋„์˜ ํ•จ์ˆ˜์— ์ž…๋ ฅํ•˜๋Š” ๊ฒƒ์ด๋‹ค. promise์— catch ๋ฉ”์„œ๋“œ์— ์ถ”๊ฐ€ํ•˜๋Š” ๊ฒƒ์ด๋‹ค. fetchMeals()๊ฐ€ promise๋ฅผ ๋ฐ˜ํ™˜ํ•˜๋ฏ€๋กœ then()์„ ์ถ”๊ฐ€ํ•ด์„œ ์„ฑ๊ณตํ•  ์ˆ˜ ์žˆ์—ˆ๋Š”๋ฐ, ์ด๋Š” promise๊ฐ€ ์„ฑ๊ณต์ ์œผ๋กœ ์ดํ–‰ํ–ˆ์„ ๋•Œ๋ฅผ ๊ฐ€์ •ํ•ด์„œ ์‚ฌ์šฉํ•ด์•ผ ํ•œ๋‹ค. ์•„๋ฌดํŠผ fetchMeals()์— catch ๋ฉ”์„œ๋“œ๋ฅผ ์ถ”๊ฐ€ํ•˜์—ฌ, erorr๋ฅผ ๋‹ค๋ฃฐ ์ˆ˜ ์žˆ๊ฒŒ ๋˜์—ˆ๋‹ค. ๊ทธ๋ฆฌ๊ณ  ์ด error๋Š” promise ๋‚ด๋ถ€์—์„œ ๋ฐœ์ƒํ•œ๋‹ค.
fetchMeals().catch((error) => {});
  • ๋”ฐ๋ผ์„œ try/catch๋ฅผ ์‚ฌ์šฉํ•˜๋Š” ๋Œ€์‹  ์šฐ๋ฆฌ๊ฐ€ ์–ป๋Š” error์— ๋Œ€ํ•ด catch()๋ฅผ ์ ์šฉํ•  ์ˆ˜ ์žˆ์„ ๊ฒƒ์ด๋‹ค.
fetchMeals().catch((error) => {
  setIsLoading(false);
  setHttpError(error.message);
});
  • ๊ทธ๋ฆฌ๊ณ  try/catch ๋ธ”๋ก(catch{}) ์•ˆ์—์„œ ํ˜ธ์ถœํ•˜๋˜ setIsLoading์™€ setHttpError ์ƒํƒœ ๋กœ์ง๋„ catch() ์•ˆ์œผ๋กœ ์˜ฎ๊ธฐ๋„๋ก ํ•œ๋‹ค.
fetchMeals().catch((error) => {
  setIsLoading(false);
  setHttpError(error.message);
});
  • ์ด๊ฒƒ์ด promise ๋‚ด๋ถ€์˜ error๋ฅผ ๋‹ค๋ฃฐ ์ˆ˜ ์žˆ๋Š”, ๊ทธ๋ฆฌ๊ณ  promise ๋งŒ์ด ๊ฐ€๋Šฅํ•œ ๋ฐฉ๋ฒ•์ด๋‹ค. ์ด์ œ ๋‹ค์‹œ ์ €์žฅํ•˜๊ณ  ๋กœ๋”ฉํ•ด๋ณด๋ฉด,

ezgif com-gif-maker - 2022-06-29T211212 035

  • ์ž ๊น ๋™์•ˆ๋งŒ ๋กœ๋”ฉ์ด ํ‘œ์‹œ๋˜๊ณ  error ๋ฉ”์„ธ์ง€ "Failed to fetch" ๊ฐ€ ํ‘œ์‹œ๋˜๋Š” ๊ฑธ ํ™•์ธํ•  ์ˆ˜ ์žˆ๋‹ค.

โœฆ ์ถœ์ฒ˜


๐Ÿšจ ํ•ด๋‹น ํฌ์ŠคํŒ…์€ Udemy์˜ โŒœReact ์™„๋ฒฝ ๊ฐ€์ด๋“œโŒŸ ๊ฐ•์˜๋ฅผ ๋ฒ ์ด์Šค๋กœ ํ•œ ๊ธฐ๋ก์ž…๋‹ˆ๋‹ค.
โœ๐Ÿป ๊ฐ•์˜ git repo ๋ฐ”๋กœ๊ฐ€๊ธฐ

profile
์ผ๋‹จ ๊ณต๋ถ€๊ฐ€ '์ ์„ฑ'์— ๋งž๋Š” ๊ฐœ๋ฐœ์ž. ๊ทผ์„ฑ์žˆ์Šต๋‹ˆ๋‹ค.

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