React Hook Formμ React κΈ°λ°μ νΌ κ΄λ¦¬ λΌμ΄λΈλ¬λ¦¬ μ€ νλλ‘ ReactHooksλ₯Ό μ¬μ©νμ¬ νΌμ μ½κ² κ΄λ¦¬νκ³ μ ν¨μ± κ²μ¬λ₯Ό μνν μ μλλ‘ λμμ€λ€.
μ₯μ μΌλ‘λ μλ μλλ°
(λΉμ°ν μκ³ μκ² μ§λ§ γ ;) νΌ(Form)μ μΉ μ ν리μΌμ΄μ μμ μ¬μ©μλ‘λΆν° λ°μ΄ν°λ₯Ό μ λ ₯λ°λ μμλ₯Ό μλ―Ένλ€.
ex)input, button, checkbox, drop-down ...
Reactμμλ μ΄λ¬ν νΌμ λ§λ€κ³ κ΄λ¦¬νκΈ° μν΄ μν(State)μ μ΄λ²€νΈ μ²λ¦¬λ₯Ό νμ©νλλ°, μ΄λ React Hook Formκ³Ό κ°μ λΌμ΄λΈλ¬λ¦¬λ₯Ό μ¬μ©νλ©΄ νΈλ¦¬νκ² μν λ° μ΄λ²€νΈ μ²λ¦¬λ₯Ό κ΄λ¦¬ν μ μλ€.
리μ‘νΈμμ μΌλ° νΌμ μμ±νλ κ³Όμ μ κ½€ 볡μ‘ν μ μλ€.
κ° input κ°μ λν μν κ΄λ¦¬μ onChange μ΄λ²€νΈ μ²λ¦¬λ₯Ό ν΄μΌνλ©°, submitμλ λ€μν μ ν¨μ± κ²μ¬ μ½λλ₯Ό μμ±ν΄μΌ νλ€. μ¬μ©μκ° νμ μ¬νμ μ¬λ°λ₯΄κ² μ
λ ₯νλμ§, μμμ λ§κ² μμ±νλμ§ λ±μ νμΈν΄μΌ νλ€...
λν, μ ν¨μ± κ²μ¬μ μ€ν¨νμ λ 보μ¬μ€ μλ¬ λ©μμ§λ₯Ό κ΄λ¦¬νλ μνλ νμνλ€. μ΄ λͺ¨λ κ³Όμ μ κ±°μ³μΌλ§ μ¬μ©μ κ²½νμ λ§μ‘±μν€λ νΌμ λ§λ€ μ μλ€.
μλλ 리μ‘νΈμμ κ°λ¨ν μ΄λ©μΌκ³Ό λΉλ°λ²νΈλ₯Ό μ λ ₯λ°λ νΌμ μμ±ν μμμ΄λ€.
import React, { useState } from "react";
export default function Forms() {
const [email, setEmail] = useState("");
const [password, setPassword] = useState("");
const [emailError, setEmailError] = useState("");
const [passwordError, setPasswordError] = useState("");
const [formError, setFormError] = useState("");
const handleEmailChange = (e) => {
const { value } = e.currentTarget;
setEmail(value);
setEmailError("");
setFormError("");
};
const handlePasswordChange = (e) => {
const { value } = e.currentTarget;
setPassword(value);
setPasswordError("");
setFormError("");
};
const handleSubmit = (e) => {
e.preventDefault();
if (!email || !password) {
setFormError("μ΄λ©μΌκ³Ό λΉλ°λ²νΈλ νμ μ
λ ₯ μ¬νμ
λλ€.");
} else {
if (!email.includes("@")) {
setEmailError("μ ν¨ν μ΄λ©μΌ μ£Όμλ₯Ό μ
λ ₯ν΄μ£ΌμΈμ.");
}
if (password.length < 8) {
setPasswordError("λΉλ°λ²νΈλ μ΅μ 8μ μ΄μμ΄μ΄μΌ ν©λλ€.");
}
}
};
return (
<form onSubmit={handleSubmit}>
<input
type="email"
placeholder="μ΄λ©μΌ"
value={email}
onChange={handleEmailChange}
required
/>
{emailError && <div>{emailError}</div>}
<input
type="password"
placeholder="λΉλ°λ²νΈ"
value={password}
onChange={handlePasswordChange}
required
/>
{passwordError && <div>{passwordError}</div>}
<button type="submit">κ³μ μμ±</button>
{formError && <div>{formError}</div>}
</form>
);
}
μ΄ μμ μ½λλ κ°λ¨ν μ΄λ©μΌκ³Ό λΉλ°λ²νΈ μ λ ₯ νΌμ ꡬνν κ² μΈλ° νμμ λ°λΌ CSSλ₯Ό μΆκ°νκ±°λ λ€λ₯Έ μ ν¨μ± κ²μ¬ μΆκ°μ μΈ κΈ°λ₯μ ꡬννλ©΄ μ½λκ° λμ± κΈΈκ³ λ³΅μ‘ν΄μ§ μ μλ€π₯π±
νμ§λ§ μλ° κ·μ°¨λμ¦μ ν΄κ²°ν react hook fromμ μ¬μ©ν΄λ³΄μ!π
μ°μ μ μΌ μ€μν react hook from λΌμ΄λΈλ¬λ¦¬λ₯Ό μ€μΉνλ€.
npm install react-hook-form
-------------------------------
yarn add react-hook-form
μ°μ κΈ°λ³Έμ μΌλ‘ React Hook Formμ μ¬μ©νλ €λ©΄ useForm ν μ μ¬μ©νμ¬ νΌμ μμ±ν΄μΌ νλ€.
import { useForm } from "react-hook-form";
export default function Forms() {
const { register } = useForm();
return (
<form>
<input
{...register("email")}
type="email"
placeholder="Email"
required
/>
<input
{...register("password")}
type="password"
placeholder="Password"
required
/>
<input type="submit" value="Create Account" />
</form>
);
}
μ΄λ κ² νλ©΄ μμ μΌλ° νΌκ³Ό λΉκ΅νλ©΄ useFromμ μ΄μ©νμ¬ λ§€μ° κΈΈμλ state μ½λλ₯Ό μ€μΌ μ μλ€.π
λ€μ λμμ λ€λ₯Έ ν¨μλ μμλ³Όκ²Έ λ λ€λ₯Έ μμ μ½λλ₯Ό μ΄ν΄λ³΄λ©΄
import React from 'react';
import { useForm } from 'react-hook-form';
function MyForm() {
const { register, handleSubmit, watch, formState: { errors } } = useForm();
const onSubmit = (data) => {
console.log(data); // μ μΆλ νΌ λ°μ΄ν° μΆλ ₯
};
return (
<form onSubmit={handleSubmit(onSubmit)}>
{/* κ° μ
λ ₯ νλμ register ν¨μλ₯Ό μ¬μ©νμ¬ μ°κ²° */}
<input {...register('firstName', { required: 'μ΄ νλλ νμμ
λλ€.' })} />
{errors.firstName && <p>{errors.firstName.message}</p>}
<input {...register('lastName')} />
<button type="submit">μ μΆ</button>
</form>
);
}
μμ μ¬μ©λ register ν¨μλ₯Ό μ¬μ©νμ¬ κ° μ λ ₯ νλλ₯Ό νΌκ³Ό μ°κ²°νλ€.
Register ν¨μλ inputμ κ°μ κ°μ Έμ€κΈ° μν ν¨μλ‘, λ€λ₯Έ μ΅μ μ μ¬μ©νλ©΄ inputμ μ ν¨μ± κ²μ¬λ κ°νΈνκ² μνν μ μλ€.
λ€μκ³Ό κ°μ΄ {...register('μ¬μ©ν μ΄λ¦', {'κ²μ¦ν λ΄μ©'})} μ΄λΌκ³ μ μ΄μ£Όλ©΄ λμ€μ μ μ μ΄λ¦μΌλ‘ κ°μ λΆλ¬μ¬ μ μλ€.
μ΄λ μ λ ₯ νλμ name μμ±μ ν΄λΉ μ λ ₯ νλμ μλ³μ μν μ νλ€.
μλλ 미리 μμ μ¬μ©λλ ν¨μλ€μ μμ½ν΄ 보μλ€.
- register : νΌλ€μ μ ν¨μ±μ νμΈνλ ν¨μ
- handleSubmit : νΌμ μ μΆνκΈ° μν ν¨μ
- watch : μ€μκ°μΌλ‘ μ λ ₯νΌμ μ ν κ°μ νμΈνλ μ΅μ
- formState : νΌμ μν μ 보λ₯Ό λ΄κ³ μμ.
(μ£Όλ‘ μ ν¨μ± κ²μ¬ μλ¬, νΌ μ μ‘ μ¬λΆ, μ λ ₯κ° λ±μ νμΈνλ λ° μ¬μ©)
νΌ Submit μ΄λ²€νΈλ₯Ό μ²λ¦¬νκΈ° μν΄ handleSubmit ν¨μλ₯Ό μ¬μ©νλ€. μ΄ ν¨μλ Submit λ²νΌμ΄ ν΄λ¦λλ©΄ νΌ λ°μ΄ν°λ₯Ό μμ§νκ³ λ±λ‘λ onSubmit ν¨μλ₯Ό νΈμΆνλ€.
μ μμ μμλ λ¨μν νΌ λ°μ΄ν°λ₯Ό μ½μμ μΆλ ₯νλλ‘ λμ΄ μλ€.
React Hook Formμ formState κ°μ²΄λ₯Ό ν΅ν΄ νΌμ μνλ₯Ό κ΄λ¦¬νλλ° μ΄ κ°μ²΄μλ λ€μν μμ±μ΄ ν¬ν¨λμ΄ μμ§λ§, μ΄λ² μμμλ errors μμ±μ μ¬μ©νμ¬ μ ν¨μ± κ²μ¬ μλ¬λ₯Ό μ²λ¦¬νλ λ°©λ²μ μμ보μ.
μ μ½λλ₯Ό 보면
{errors.firstName && <p>{errors.firstName.message}</p>}:
μ΄ λΆλΆμ firstName νλμ λν μλ¬κ° μμ κ²½μ° ν΄λΉ μλ¬ λ©μμ§λ₯Ό μΆλ ₯νλ€. μ΄λ κ² νλ©΄ μ¬μ©μμκ² μ ν¨μ± κ²μ¬ μ€ν¨μ λν μ 보λ₯Ό μ 곡ν μ μλ€.μ΄λ κ² μ ν¨μ± κ²μ¬ μλ¬λ₯Ό μ²λ¦¬νκ³ , κ° νλμ ν΄λΉνλ μλ¬ λ©μμ§λ₯Ό μΆλ ₯ν μ μλ€.
μ°Έκ³ λ‘ λ§¨μμ μΌλ° νΌμ μ¬μ©λ μ΄λ©μΌ, λΉλ°λ²νΈ μ λ ₯νΌμ
<input
{...register('password', {
required: 'λΉλ°λ²νΈλ₯Ό μ
λ ₯ν΄μ£ΌμΈμ.',
minLength: {
value: 8,
message: 'λΉλ°λ²νΈλ 8μ μ΄μμ΄μ΄μΌ ν©λλ€.'
}
})}
type="password"
/>
{errors.password && <p>{errors.password.message}</p>}
μλ°μμΌλ‘ λνλΌ μ μλ€. κ·Έ μΈμλ μ΄λ©μΌ μμ, λλ€μ, μ΄λ¦ λ± μ¬λ¬ μ ν¨μ± κ²μ¬ νλκ² μλλ° react hook fromμ ν΅ν΄ λ κ°λ μ±μκ² μμ± ν μ μλ€.