Yupのようなバリデーションライブラリを使わずとも、React Hook Form (RHF)で基本的なバリデーションは可能ですので、その方法を解説します。なお、UIライブラリとして、MUIを使っています。
シンプルなバリデーション
まずはログインや会員登録を想定したフォームを作成し、そこにバリデーションを実装していきます。
なお、RHFやMUIのインストールは、こちらの記事を参照してください。
コード全体はこんな感じです。
<App.tsx> import { useForm } from 'react-hook-form' import { Button, Checkbox, Container, FormControlLabel, FormGroup, FormHelperText, Stack, TextField } from '@mui/material' type formType = { name: string, email: string, agreement: boolean } export default function App() { const { register, handleSubmit, formState: { errors } } = useForm<formType>() const submit = (data: formType) => { console.log(data) } return ( <Container maxWidth="sm" sx={{ pt: 5 }}> <form onSubmit={handleSubmit(submit)}> <Stack spacing={3}> {/* TextField */} <TextField label="Name" {...register("name", { required: "error" })} error={errors.name ? true : false} helperText={errors.name?.message} /> <TextField label="Email" {...register("email", { required: "error" })} error={"email" in errors} helperText={errors.email?.message} /> {/* CheckBox */} <FormGroup> <FormControlLabel control={ <Checkbox {...register("agreement", { required: "error" })} /> } label="Agree to Terms and Conditions" /> <FormHelperText error={errors.agreement ? true : false}> {errors.agreement?.message} </FormHelperText> </FormGroup> <Button type="submit" color="primary" variant="contained"> Sign Up </Button> </Stack> </form> </Container> ) }
簡単にポイントを解説します。
// register内でエラー時のメッセージを指定し、 {...register("name", { required: "error" })} // helperTextでそれを表示 helperText={errors.name?.message} // 以下は結果に違いはないので、どちらで表記するかは好みかと。 error={errors.name ? true : false} error={"email" in errors}
ブラウザで確認
空の状態でボタンをクリックすると、エラーが表示されます。
関数化する
続いて、関数化して別ファイルから呼びます。
まずは下記のように register
の中を書き換えて、インポート文も追加しましょう。
<App.tsx> import { emailValidation, textValidation } from './Validation' <TextField label="Name" {...register("name", { validate: textValidation })} error={errors.name ? true : false} helperText={errors.name?.message} /> <TextField label="Email" {...register("email", { validate: emailValidation })} error={"email" in errors} helperText={errors.email?.message} />
次に、Appt.tsxと同じ階層にValidation.tsというファイルを作成し、下記の通り記述します。入力されたデータを受け取って、エラーを返したりする関数ですね。
<Validation.ts> const errorText = "error" const maxLength = 255 // Validation for Text export const textValidation = (value: string | null) => { if (!value) { return errorText } else if (value && value.length > maxLength) { return `Please enter within ${maxLength} characters.` } } // Validation for Email export const emailValidation = (value: string | null) => { const regex = /^[a-zA-Z0-9_.+-]+@[a-zA-Z0-9-]+\.[a-zA-Z0-9-.]+$/ if (!value) { return errorText } else if (!regex.test(value)) { return "Please enter a valid Email." } }
ブラウザで確認
このように、条件に当てはまらない場合はエラーが表示できました。
おわりに
RHFのregisterのオプションはこれ以外にもあって、min(最小文字数)などももちろん設定可能です。詳しくは公式ドキュメントを見てくださいな。
複雑な条件でもない限り、RHFでバリデーションが可能なことはお判りいただけたかと思います。また、タイプミスを避けたりメンテナンス性を高めるために、関数化して読み込む方法は有効ですので、ぜひ試してみてください。