form-data-middleware
The formData middleware parses multipart/form-data and application/x-www-form-urlencoded request bodies. It makes the parsed FormData available to handlers and downstream middleware through the context.
Installation
The form data middleware is included with Remix. No additional installation is needed.
Import
import { formData, FormData } from 'remix/form-data-middleware'API
formData(options?)
Returns a middleware function that parses form data from the request body.
let router = createRouter({
middleware: [
formData(),
],
})FormData (Context Key)
A context key used to access the parsed form data in handlers:
import { FormData } from 'remix/form-data-middleware'
router.map(route, ({ context }) => {
let data = context.get(FormData)
let title = data.get('title')
})Options
| Option | Type | Default | Description |
|---|---|---|---|
uploadHandler | UploadHandler | Memory handler | A function that controls how uploaded files are stored. See Upload Handlers below. |
maxFileSize | number | 10 * 1024 * 1024 (10 MB) | Maximum size in bytes for a single uploaded file. |
maxFiles | number | 10 | Maximum number of file uploads per request. |
maxParts | number | 100 | Maximum total number of form fields (including files) per request. |
Accessing Parsed Form Data
After the middleware runs, use the FormData context key to access the parsed data:
import { FormData } from 'remix/form-data-middleware'
router.map(createPostRoute, async ({ context }) => {
let data = context.get(FormData)
let title = data.get('title') // string | null
let tags = data.getAll('tags') // string[]
let avatar = data.get('avatar') // File | string | null
// ...
})The returned object is a standard FormData instance. Text fields are strings, and file fields are File objects.
Upload Handlers
An upload handler is a function that receives file upload information and decides how to store it. The default handler stores files in memory.
Memory Handler (Default)
Files are stored in memory as File objects. Suitable for small files and development:
formData()Custom Upload Handler
Write a handler to store files on disk, S3, or any other storage:
import type { UploadHandler } from 'remix/form-data-middleware'
let diskUploadHandler: UploadHandler = async ({ filename, contentType, stream }) => {
let path = `./uploads/${crypto.randomUUID()}-${filename}`
let file = await Bun.write(path, stream)
return new File([await Bun.file(path).bytes()], filename, { type: contentType })
}
formData({
uploadHandler: diskUploadHandler,
})The upload handler receives:
| Property | Type | Description |
|---|---|---|
name | string | The form field name |
filename | string | The original filename |
contentType | string | The MIME type of the file |
stream | ReadableStream | A readable stream of the file contents |
Examples
Basic Form Handling
import { createRouter } from 'remix/fetch-router'
import { formData, FormData } from 'remix/form-data-middleware'
let router = createRouter({
middleware: [
formData(),
],
})
router.map(contactRoute, async ({ context }) => {
let data = context.get(FormData)
let name = data.get('name')
let email = data.get('email')
let message = data.get('message')
await sendContactEmail({ name, email, message })
return redirect('/contact/thanks')
})File Upload with Size Limits
formData({
maxFileSize: 5 * 1024 * 1024, // 5 MB per file
maxFiles: 3, // Up to 3 files per request
})If a file exceeds the limit, the middleware returns a 413 Payload Too Large response.
File Upload to Storage
import { formData, FormData } from 'remix/form-data-middleware'
let router = createRouter({
middleware: [
formData({
uploadHandler: s3UploadHandler,
maxFileSize: 50 * 1024 * 1024, // 50 MB
}),
],
})
router.map(uploadRoute, async ({ context }) => {
let data = context.get(FormData)
let file = data.get('document') // File object from upload handler
return html`<p>Uploaded: ${file.name} (${file.size} bytes)</p>`
})With Method Override
When using methodOverride, the formData middleware must come first:
let router = createRouter({
middleware: [
formData(),
methodOverride(),
],
})Related
- Middleware --- How middleware works in Remix.
- Forms & Mutations --- Working with forms in Remix.
- File Uploads Guide --- Detailed guide on handling file uploads.
- method-override-middleware --- Using form data with method override.