lil.dev
Published on

๐ŸŽ‰ ์ปฌ๋Ÿฌ๋ฆฌ์ŠคํŠธ ํ”„๋กœ์ ํŠธ #21 Input Component ์ถ”์ถœํ•˜๊ธฐ

๊ธ€์“ด์ด

    ๐Ÿ“Œ

    Welcome

    โœจ ์ปฌ๋Ÿฌ๋ฆฌ์ŠคํŠธ ์‚ฌ์ดํŠธ(์•„์ง ์—†์Œ

    ์ด์ „์— VerticalForm์‚ฌ์ด์— children์œผ๋กœ ๋“ค์–ด์žˆ๋˜ Input๋“ค์„ component๋กœ ์ถ”์ถœํ•ด ์ข€ ๋” ์‹ฌํ”Œํ•œ Register.tsx, Login.tsx๋ฅผ ๋งŒ๋“ค์–ด๋ณด๊ณ ์ž ํ•œ๋‹ค.

    ์ด์ „์˜ ์ฝ”๋“œ๋Š” ์•„๋ž˜์™€ ๊ฐ™์€ ๋ชจ์–‘์ด์—ˆ๋‹ค. ๊ฐ๊ฐ์˜ input๋งˆ๋‹ค label๊ณผ span, className์„ ๋ชจ๋‘ ๋”ฐ๋กœ ์ง€์ •ํ•ด์ฃผ์–ด์•ผํ–ˆ๋‹ค.

    ;<label className="flex flex-col gap-2">
      <span className="text-xl">์ด๋ฉ”์ผ</span>
      <input
        type="email"
        className="input input-bordered"
        {...register('email', {
          required: '์ด๋ฉ”์ผ์„ ์ž…๋ ฅํ•ด์ฃผ์„ธ์š”!',
        })}
      />
    </label>
    {
      errors.email && <li role="alert">{errors.email.message}</li>
    }
    ;<label className="flex flex-col gap-2">
      <span className="text-xl">๋น„๋ฐ€๋ฒˆํ˜ธ</span>
      <input
        type="password"
        className="input input-bordered"
        {...register('password', {
          required: '๋น„๋ฐ€๋ฒˆํ˜ธ๋ฅผ ์ž…๋ ฅํ•ด์ฃผ์„ธ์š”!',
        })}
      />
    </label>
    {
      errors.password && <li role="alert">{errors.password.message}</li>
    }
    

    ์ด ๋ถ€๋ถ„์„ ๋นผ์„œ Input.tsx์— ๋”ฐ๋กœ ์ปดํฌ๋„ŒํŠธ๋ฅผ ์ถ”์ถœํ–ˆ๋‹ค.

    ์ผ๋‹จ DataT๋ผ๋Š” ํƒ€์ž…์— ํ˜„์žฌ ์กด์žฌํ•˜๋Š” ๋‘ ๊ฐœ์˜ input type์ธ email๊ณผ password์˜ type์„ ์„ค์ •ํ–ˆ๋‹ค. ์ฐธ๊ณ : https://www.typescriptlang.org/docs/handbook/2/objects.html

    type DataT = {
      email: string
      password: string
    }
    

    ์ด๋ ‡๊ฒŒ ํ•˜๋ฉด ์ด๋ฉ”์ผ๊ณผ ๋น„๋ฐ€๋ฒˆํ˜ธ์— ๋ฌธ์ž์—ด์„ ๋„ฃ์—ˆ์„ ๋•Œ๋งŒ ์—๋Ÿฌ๊ฐ€ ๋œจ์ง€ ์•Š๋Š”๋‹ค.

    let a: DataT = {
      email: 'test@naver.com',
      password: 'test',
    }
    

    ๊ทธ๋ฆฌ๊ณ  DataKey๋ผ๋Š” ํƒ€์ž…์„ ์„ค์ •ํ•ด DataT์— ์žˆ๋Š” ํ‚ค๋“ค์„ ํƒ€์ž…์œผ๋กœ ์„ค์ •ํ•œ๋‹ค. ์ฐธ๊ณ : https://www.typescriptlang.org/docs/handbook/2/keyof-types.html

    type DataKeys = keyof DataT // 'email' | 'password' ์ด ๋‘๊ฐœ๋งŒ ํƒ€์ž…์œผ๋กœ ์˜ฌ ์ˆ˜ ์žˆ๋‹ค.
    
    function hello(name: DataKeys) {
      console.log(name)
    }
    
    hello('email')
    hello('password')
    // hello("test"); // <- ํƒ€์ž… ์—๋Ÿฌ!
    

    ๊ทธ ๋‹ค์Œ์€ ์—๋Ÿฌ๊ฐ€ ๋‚ฌ์„๋•Œ ์˜ฌ ์ˆ˜ ์žˆ๋Š” ๋ฐ์ดํ„ฐ๋ฅผ ์„ค์ •ํ•ด์ค€๋‹ค.

    type ErrorData = {
      [key in keyof DataT]: { message?: string }
      //์•ž์—๋Š” email์ด๋‚˜ password๋งŒ ์˜ฌ ์ˆ˜ ์žˆ๊ณ  :๋’ค์—๋Š” ๋ฉ”์‹œ์ง€๊ฐ€ ์˜ฌ ์ˆ˜๋„, ์•ˆ ์˜ฌ ์ˆ˜๋„ ์žˆ๋Š”๋ฐ, ์˜ค๋ฉด ๋ฌธ์ž์—ด์ด์–ด์•ผ ํ•œ๋‹ค.
    }
    

    ์œ„์—์„œ ๋งŒ๋“  ์—๋Ÿฌ๋ฐ์ดํ„ฐ๋ฅผ ๊ฐ€์ง€๊ณ  ์—๋Ÿฌ๊ฐ€ ๋‚ฌ์„๋•Œ ์ฝ˜์†”์— ์—๋Ÿฌ๋ฉ”์‹œ์ง€๋ฅผ ์ฐ์–ด์ฃผ๋Š” ํ•จ์ˆ˜๋ฅผ ๋งŒ๋“ค์—ˆ๋‹ค.

    function logError(errors: ErrorData) {
      console.error(errors)
    }
    // {
    //   email: {
    //       message: string;
    //   };
    //   password: {
    //       message: string;
    //   };
    // }
    
    // logError({
    //   email: "test@naver.com",
    //   password: "test",
    // }); // ๋‹ค๋ฅธ ํƒ€์ž…!
    //        ๊ฐ์ฒด๋กœ ์™€์•ผํ•ด~~
    
    logError({
      email: { message: 'test@naver.com' },
      password: {}, // message๋Š” optional ? ์ด๋‹ˆ๊นŒ
    })
    

    ํ•˜์ง€๋งŒ ์œ„์˜ ๊ฒฝ์šฐ๋Š” ๋ฌด์กฐ๊ฑด ๋‘๊ฐœ์˜ ํ‚ค๊ฐ€ ๋‹ค ์ž…๋ ฅ๋˜์–ด์•ผํ•œ๋‹ค. ํ•˜๋‚˜๋งŒ ์ž…๋ ฅํ–ˆ์„๋•Œ๋„ ์—๋Ÿฌ ๋ฉ”์‹œ์ง€๊ฐ€ ๋œจ๊ฒŒ ํ•˜๋ ค๋ฉด ์–ด๋–ป๊ฒŒ ํ•ด์•ผํ• ๊นŒ? ์ด๋Š” Partial type์„ ์ด์šฉํ•ด์„œ ํ•ด๊ฒฐํ•  ์ˆ˜ ์žˆ๋‹ค. Partial์€ ๋ถ€๋ถ„์ง‘ํ•ฉ๊ฐ™์€ ๊ฐœ๋…์œผ๋กœ, logError์•ˆ์— ์žˆ๋Š” ๋ชจ๋“  ์ •๋ณด๊ฐ€ ์™€๋„ ๋˜๊ณ , ์ผ๋ถ€๋งŒ ์™€๋„ ๋œ๋‹ค. ์ฐธ๊ณ : https://www.typescriptlang.org/docs/handbook/utility-types.html#partialtype

    type PartialE = Partial<ErrorData>
    
    // {
    //   email?: {
    //       message: string;
    //   } | undefined;
    //   password?: {
    //       message: string;
    //   } | undefined;
    // }
    

    ์ด๋ ‡๊ฒŒ PartialE๋ผ๋Š” ํƒ€์ž…์„ ์ •ํ•˜๊ณ  ์ƒˆ๋กœ์šด logError2ํ•จ์ˆ˜๋ฅผ ๋งŒ๋“ค๋ฉด email,password ๋‘˜ ์ค‘์— ํ•˜๋‚˜๋งŒ ์ž…๋ ฅํ•˜์ง€ ์•Š์•„๋„ ์—๋Ÿฌ๋ฉ”์‹œ์ง€๊ฐ€ ๋œฌ๋‹ค.

    function logError2(errors: PartialE, name: keyof DataT) {
      console.error(errors[name])
    }
    
    // logError2({}, "test");
    
    logError2(
      {
        email: { message: 'ํ•„์ˆ˜ ์ž…๋ ฅ์ž…๋‹ˆ๋‹ค!' },
      },
      'email'
    )
    
    logError2(
      {
        password: { message: 'ํ•„์ˆ˜ ์ž…๋ ฅ์ž…๋‹ˆ๋‹ค!' },
      },
      'password'
    )