Interactive demoDataCore
Validated forms
One Zod schema shared by the browser and the server, with field-level errors and a real submission lifecycle.
Built withServer ActionsZoduseActionState
Before you try it
What it needs
Nothing to configure. It runs the same everywhere.
Mode right now
ReadyThe provider is configured here; nobody has watched the real path succeed on this deployment yet.
A safe failure to try
Type a slug with spaces: the field is refused before submit, and the same schema refuses it again on the server.
New project
Every field below is validated twice. Try submitting the slug admin to see a rule the schema cannot express reject it on the server.
What to try
Each of these exercises a different validation layer.
Client
Blur the name field while empty — instant feedback, no request.
Server
Set the slug to “admin” — only the server knows it is reserved.
Schema
Type “My Project!” as the slug — the pattern rejects it on both sides.
Required
Untick every environment and submit — the array minimum fires.
What this demonstrates
- A single schema is the contract for both sides of the wire
- Client validation is a convenience; server validation is the security boundary
- Errors attach to fields, announced via aria-describedby
- Pending UI driven by useActionState rather than a manual boolean
Where the code lives
src/experiments/forms/demo.tsxRegistered in src/experiments/registry.ts and loaded on demand by loader.tsx.