#[request] attribute works with both JSON and form-urlencoded data, making it suitable for REST APIs and HTML forms alike.
Overview
Requests combine three concerns into a single, declarative struct:- Data parsing - Automatically parse JSON or form-urlencoded data
- Validation - Validate fields using the
validatorcrate - Authorization - Optionally check if the request is authorized
The #[handler] Attribute
All controller methods in Kit use the #[handler] attribute. This enables automatic extraction and validation of request data:
Defining a Request
The#[request] attribute automatically adds Deserialize and Validate derives:
Validation Rules
Kit uses thevalidator crate for validation. Here are common validation rules:
String Validations
Numeric Validations
Nested and Collection Validations
Common Validation Attributes
| Attribute | Description | Example |
|---|---|---|
email | Valid email format | #[validate(email)] |
url | Valid URL format | #[validate(url)] |
length | String/collection length | #[validate(length(min = 1, max = 100))] |
range | Numeric range | #[validate(range(min = 0, max = 100))] |
regex | Regex pattern match | #[validate(regex(path = "PATTERN"))] |
contains | String contains substring | #[validate(contains(pattern = "@"))] |
does_not_contain | String doesn’t contain | #[validate(does_not_contain(pattern = "admin"))] |
nested | Validate nested struct | #[validate(nested)] |
Validation Error Response
When validation fails, Kit automatically returns a 422 response with Laravel/Inertia-compatible error format:Complete Example
Here’s a complete example of a user registration endpoint: Define the request:Authorization
You can override theauthorize method to add authorization checks:
authorize returns false, the request is rejected with a 403 Forbidden response:
Request Content Types
Requests automatically detect and parse the content type:application/json- Parsed as JSONapplication/x-www-form-urlencoded- Parsed as form data
Content-Type header.
Using Request with Validated Data
If you need access to both the validated data and the original request (for headers, params, etc.), you can still access request information in your controller:File Organization
The standard structure for requests:End-to-End Type Safety with Inertia
Requests can also deriveInertiaProps to generate TypeScript types, enabling end-to-end type safety from your Rust backend to your React frontend.
Generating TypeScript Types for Requests
AddInertiaProps derive alongside #[request]:
frontend/src/types/inertia-props.ts:
Type-Safe Forms with Inertia
Use Inertia’s<Form> component for the cleanest form handling:
<Form> with the useForm hook and your generated types:
Benefits of End-to-End Type Safety
- Compile-time checks: TypeScript catches field name typos and type mismatches
- IDE autocomplete: Full IntelliSense for form fields in your editor
- Validation alignment: Your TypeScript types match your Rust validation rules
- Refactoring safety: Rename a field in Rust, TypeScript errors show where to update
Workflow
- Define request with validation in Rust
- Add
#[derive(InertiaProps)]to the struct - Run
kit generate-typesto generate TypeScript - Use the generated type with
useForm<RequestType> - Get full type safety and validation error handling
For more information on TypeScript type generation, see TypeScript Types.
Summary
| Feature | Description |
|---|---|
| Define request | #[request] attribute |
| Handler attribute | #[handler] on all controller methods |
| Validation | Use #[validate(...)] attributes |
| Error format | Laravel/Inertia-compatible 422 JSON |
| Authorization | Override authorize() method |
| Auto content-type | Detects JSON vs form-urlencoded |
| TypeScript types | Add #[derive(InertiaProps)] for type generation |
| Type-safe forms | Use generated types with useForm<T> |