Skip to content

複雑なフォームバリデーションをClaudeと設計する

Claude Codeにバリデーション要件を自然言語で伝える

Section titled “Claude Codeにバリデーション要件を自然言語で伝える”

複雑なフォームバリデーションを一から実装するのは骨が折れる作業です。「パスワード確認フィールドが一致しているか」「メールアドレスが特定ドメインか」「入力値によって必須項目が変わる」——こうした条件が重なると、コードはあっという間に複雑になります。

Claude Codeを使えば、要件を自然言語で伝えるだけでzodスキーマの雛形を生成できます。たとえば次のようにプロンプトを入力してみましょう。

ユーザー登録フォームのzodスキーマを作成してください。
要件:
- メールアドレス(必須、形式チェック)
- パスワード(必須、8文字以上、英数字混在)
- パスワード確認(パスワードと一致すること)
- 会社名(法人プランを選択した場合のみ必須)

このプロンプトに対してClaudeはsuperRefinediscriminatedUnionを活用したスキーマを提案してくれます。「なぜこの実装を選んだか」も説明してくれるので、知識の習得にもつながります。

プロンプト: AIへの指示文。Claude Codeへの指示の質がそのまま出力の質に影響する。スキーマ: データベースのテーブル構造や型定義のこと。

react-hook-formとの統合コードを一気に生成する

Section titled “react-hook-formとの統合コードを一気に生成する”

zodスキーマができたら、次はreact-hook-formとの接続です。useFormの型引数やresolver設定など、毎回調べてしまいがちな定型コードも、Claudeに任せてしまいましょう。

// Claude Codeが生成するコードの例
import { useForm } from "react-hook-form";
import { zodResolver } from "@hookform/resolvers/zod";
import { z } from "zod";
const schema = z.object({
email: z.string().email("有効なメールアドレスを入力してください"),
password: z.string().min(8).regex(/^(?=.*[a-zA-Z])(?=.*\d)/),
confirmPassword: z.string(),
}).refine((data) => data.password === data.confirmPassword, {
message: "パスワードが一致しません",
path: ["confirmPassword"],
});
type FormValues = z.infer<typeof schema>;
export function RegisterForm() {
const { register, handleSubmit, formState: { errors } } = useForm<FormValues>({
resolver: zodResolver(schema),
});
// ...
}

生成されたコードに「エラーメッセージをコンポーネントに表示する部分も追加して」と続けて指示すれば、実装が次々と肉付けされていきます。

条件分岐バリデーションの壁をClaudeと乗り越える

Section titled “条件分岐バリデーションの壁をClaudeと乗り越える”

最も厄介なのが「他のフィールドの値に依存するバリデーション」です。たとえば「法人プランを選択したときだけ会社名が必須になる」といったケース。これをClaudeに相談するときは、具体的なフィールド名と条件をセットで伝えると精度が上がります。

planTypeが"business"のとき、companyNameを必須にするバリデーションを
zodのdiscriminatedUnionで実装してください。
react-hook-formのwatchと組み合わせてUIの切り替えも行いたいです。

条件分岐の多いフォームも、Claudeと対話しながら少しずつ要件を追加していくアプローチを取れば、無理なく実装を進められます。まずは「シンプルなスキーマを作る→統合コードを生成→条件を足す」という順番で試してみてください。

API: Application Programming Interface の略。外部サービスとプログラム間でデータをやりとりするための接続口。