Skip to content

UploadFieldProps

UploadFieldProps = BaseFieldProps & object

Defined in: packages/ui/src/types.ts:903

Props for the headless UploadField component.

UploadField is a controlled, multi-file upload widget built on the opinionated POST /uploads/:filetype route exposed by @cfast/storage. Unlike DropZoneProps (which only wraps a single useUpload result), UploadField is the form-friendly variant: it owns its own upload state, integrates with react-hook-form via the controlled value/onChange pair, enforces maxFiles, and surfaces per-file progress + per-file error reporting.

The field reports its current value as string[] of R2 keys — exactly the shape you would store on a Drizzle column like text("image_key").

optional accept: string

The HTML accept string passed to the underlying <input type="file"> (e.g. "image/*" or "image/png,image/webp"). This should match the MIME types declared on the corresponding storage filetype so the browser-side picker can pre-filter selections.

optional basePath: string

Mount path of the storage routes from @cfast/storage/plugin. Defaults to "/uploads". Must match the basePath used in storageRoutes() / createStorageRouteHandlers.

optional disabled: boolean

Whether the field is disabled. Disabled fields render their existing value but don’t accept new files and don’t render the drop zone in an interactive state.

filetype: string

The filetype name registered in defineStorage. Used as the last segment of the upload POST URL — ${basePath}/${filetype}.

optional maxFiles: number

Hard cap on the number of files the user is allowed to upload through this field. Files dropped or selected past the cap are rejected with an inline error and never start uploading. Defaults to 1 when multiple is false, otherwise unlimited.

optional maxSize: number

Optional client-side max size in bytes. Files larger than this are rejected before any bytes are sent. Server-side validation is still the source of truth — this is only a hint to the user.

optional multiple: boolean

Whether the field accepts multiple files. When false (default), the controlled value still flows through as string[] but only ever contains zero or one entries.

optional onChange: (keys) => void

Called with the new array of keys whenever the set of successfully uploaded files changes — after a successful upload, after a removal, etc. Wire this to your react-hook-form setValue callback or to a controlled component’s local state.

string[]

void

optional onError: (file) => void

Called whenever a per-file upload fails (network error, validation error, server-side rejection). Receives the file tracker entry — the error field on the entry is the rendered message.

UploadFieldFile

void

optional uploader: (file, options) => Promise<{ key: string; size: number; type: string; url?: string; }>

Custom uploader implementation. Defaults to a built-in XMLHttpRequest uploader that hits ${basePath}/${filetype}. Override this in tests (or in apps that wrap the upload in extra logic) — both @cfast/ui’s own tests and the Joy variant’s tests pass a mock through this prop instead of stubbing XMLHttpRequest globally.

File

(percent) => void

AbortSignal

string

Promise<{ key: string; size: number; type: string; url?: string; }>

optional value: string[]

Controlled array of R2 keys. When multiple is false, treat this as a single-element array (the first entry is the active value).