--- description: Writing Forms with Shadcn UI, Server Actions, Zod globs: apps/**/*.tsx,packages/**/*.tsx alwaysApply: false --- # Forms - Use React Hook Form for form validation and submission. - Use Zod for form validation. - Use the `zodResolver` function to resolve the Zod schema to the form. Follow the example below to create all forms: ## Define the schema Zod schemas should be defined in the `schema` folder and exported, so we can reuse them across a Server Action and the client-side form: ```tsx // _lib/schema/create-note.schema.ts import { z } from 'zod'; export const CreateNoteSchema = z.object({ title: z.string().min(1), content: z.string().min(1), }); ``` ## Create the Server Action ```tsx // _lib/server/server-actions.ts 'use server'; import { z } from 'zod'; import { enhanceAction } from '@kit/next/actions'; import { CreateNoteSchema } from '../schema/create-note.schema'; const CreateNoteSchema = z.object({ title: z.string().min(1), content: z.string().min(1), }); export const createNoteAction = enhanceAction( async function (data, user) { // 1. "data" has been validated against the Zod schema, and it's safe to use // 2. "user" is the authenticated user // ... your code here return { success: true, }; }, { auth: true, schema: CreateNoteSchema, }, ); ``` ## Create the Form Component Then create a client component to handle the form submission: ```tsx // _components/create-note-form.tsx 'use client'; import { zodResolver } from '@hookform/resolvers/zod'; import { useForm } from 'react-hook-form'; import { z } from 'zod'; import { Form, FormControl, FormField, FormItem, FormLabel, FormMessage } from '@kit/ui/form'; import { CreateNoteSchema } from '../_lib/schema/create-note.schema'; export function CreateNoteForm() { const [pending, startTransition] = useTransition(); const form = useForm({ resolver: zodResolver(CreateNoteSchema), defaultValues: { title: '', content: '', }, }); const onSubmit = (data) => { startTransition(async () => { try { await createNoteAction(data); } catch { // handle error } }); }; return (
); } ``` Always use `@kit/ui` for writing the UI of the form.