Upload field components provide file upload functionality with preview and management features.
Button-style upload component for file uploads.
Import
import { ProFormUploadButton } from '@ant-design/pro-components' ;
Usage
Basic
Image Upload
Custom Upload
< ProFormUploadButton
name = "attachments"
label = "Attachments"
title = "Click to Upload"
action = "/api/upload"
max = { 5 }
/>
< ProFormUploadButton
name = "images"
label = "Images"
title = "Upload Image"
action = "/api/upload/image"
accept = "image/*"
listType = "picture-card"
max = { 3 }
fieldProps = { {
maxCount: 3 ,
beforeUpload : ( file ) => {
const isImage = file . type . startsWith ( 'image/' );
if ( ! isImage ) {
message . error ( 'You can only upload image files!' );
}
return isImage || Upload . LIST_IGNORE ;
}
} }
/>
< ProFormUploadButton
name = "documents"
label = "Documents"
title = "Upload"
icon = { < UploadOutlined /> }
fieldProps = { {
customRequest : async ({ file , onSuccess , onError }) => {
const formData = new FormData ();
formData . append ( 'file' , file );
try {
const response = await fetch ( '/api/upload' , {
method: 'POST' ,
body: formData ,
});
const data = await response . json ();
onSuccess ?.( data );
} catch ( error ) {
onError ?.( error );
}
}
} }
/>
Props
Extends ProFormText props and Ant Design Upload props.
Upload endpoint URL. Required unless using customRequest.
title
ReactNode
default: "'Click to Upload'"
Text displayed on the upload button.
icon
ReactNode
default: "<UploadOutlined />"
Icon displayed on the upload button.
Maximum number of files allowed. When limit is reached, upload button becomes disabled.
Accepted file types. Uses HTML input accept attribute:
image/*: All image types
image/png,image/jpeg: Specific image types
.pdf,.doc,.docx: File extensions
video/*,audio/*: Multiple media types
listType
'text' | 'picture' | 'picture-card' | 'picture-circle'
default: "'picture'"
Upload list display style:
text: Show as text list with file icon
picture: Show as list with thumbnail
picture-card: Show as card grid with large thumbnail
picture-circle: Show as circular thumbnails
Props passed to the upload button. Accepts all Ant Design Button props: buttonProps = {{
type : 'primary' ,
size : 'large' ,
danger : true
}}
Whether the upload button is disabled.
Props for image preview component. Accepts Ant Design Image props: imageProps = {{
preview : {
toolbarRender : () => null ,
maskClassName : 'custom-mask'
}
}}
Controlled file list value. File object structure: interface UploadFile {
uid : string ;
name : string ;
status ?: 'uploading' | 'done' | 'error' | 'removed' ;
url ?: string ;
thumbUrl ?: string ;
response ?: any ;
}
Field name for file parameter in upload request.
HTTP headers for upload request: headers = {{
Authorization : `Bearer ${ token } ` ,
'X-Custom-Header' : 'value'
}}
fieldProps.data
object | ((file: UploadFile) => object)
Additional data sent with upload request: data = {{ userId : '123' , type : 'document' }}
// or
data = {(file) => ({ fileName : file . name })}
fieldProps.withCredentials
Whether to send cookies with upload request.
Whether to allow selecting multiple files at once.
Maximum number of files in the list. When limit is reached, new uploads replace old files.
Whether to support uploading entire directories.
fieldProps.beforeUpload
(file: File, fileList: File[]) => boolean | Promise<File> | Upload.LIST_IGNORE
Hook before uploading. Return false or reject Promise to prevent upload: beforeUpload = {(file) => {
const isLt2M = file . size / 1024 / 1024 < 2 ;
if ( ! isLt2M ) {
message . error ( 'File must be smaller than 2MB!' );
}
return isLt2M || Upload . LIST_IGNORE ;
}}
fieldProps.customRequest
(options: UploadRequestOption) => void
Custom upload implementation. Override default upload behavior: interface UploadRequestOption {
file : File ;
onProgress ?: ( event : { percent : number }) => void ;
onSuccess ?: ( body : any , xhr ?: XMLHttpRequest ) => void ;
onError ?: ( error : Error ) => void ;
}
fieldProps.onChange
(info: { file: UploadFile, fileList: UploadFile[] }) => void
Callback when upload state changes. Triggered on start, progress, success, and error.
fieldProps.onRemove
(file: UploadFile) => boolean | Promise<boolean>
Callback before removing file. Return false to prevent removal.
fieldProps.onPreview
(file: UploadFile) => void
Callback when file preview is clicked. Default behavior shows image preview.
fieldProps.onDownload
(file: UploadFile) => void
Callback when download button is clicked.
fieldProps.itemRender
(originNode: ReactNode, file: UploadFile, fileList: UploadFile[], actions: { download: Function, preview: Function, remove: Function }) => ReactNode
Custom render function for each file item in the list.
fieldProps.showUploadList
boolean | ShowUploadListInterface
Whether to show upload list. Can be boolean or detailed configuration: showUploadList = {{
showPreviewIcon : true ,
showRemoveIcon : true ,
showDownloadIcon : false ,
removeIcon : < DeleteOutlined /> ,
downloadIcon : < DownloadOutlined />
}}
Drag-and-drop upload component with drop zone.
Import
import { ProFormUploadDragger } from '@ant-design/pro-components' ;
Usage
Basic
Custom Content
Image Upload
< ProFormUploadDragger
name = "files"
label = "Files"
title = "Click or drag files to this area to upload"
description = "Support single or bulk upload"
action = "/api/upload"
/>
< ProFormUploadDragger
name = "documents"
label = "Documents"
icon = { < InboxOutlined /> }
title = "Upload Documents"
description = "Supports PDF, DOC, DOCX files up to 10MB"
action = "/api/upload/documents"
accept = ".pdf,.doc,.docx"
max = { 10 }
fieldProps = { {
beforeUpload : ( file ) => {
const isValidSize = file . size / 1024 / 1024 < 10 ;
if ( ! isValidSize ) {
message . error ( 'File must be smaller than 10MB!' );
}
return isValidSize || Upload . LIST_IGNORE ;
}
} }
>
< p > Additional instructions or help text </ p >
</ ProFormUploadDragger >
< ProFormUploadDragger
name = "images"
label = "Product Images"
icon = { < CameraOutlined /> }
title = "Upload Images"
description = "Click or drag images here"
action = "/api/upload/images"
accept = "image/*"
max = { 5 }
fieldProps = { {
multiple: true ,
listType: 'picture' ,
onChange : ( info ) => {
const { status } = info . file ;
if ( status === 'done' ) {
message . success ( ` ${ info . file . name } uploaded successfully.` );
} else if ( status === 'error' ) {
message . error ( ` ${ info . file . name } upload failed.` );
}
}
} }
/>
Props
Extends ProFormUploadButton props and Ant Design Upload.Dragger props.
title
ReactNode
default: "'Click or drag file to this area to upload'"
Main text displayed in the upload area.
icon
ReactNode
default: "<InboxOutlined />"
Large icon displayed at the top of the upload area.
description
ReactNode
default: "'Support single or bulk upload'"
Description text displayed below the title.
Additional content displayed at the bottom of the upload area. Can include help text or links.
Maximum number of files allowed. When limit is reached, dragger area is hidden.
Controlled file list value.
onChange
(info: { file: UploadFile, fileList: UploadFile[] }) => void
Callback when upload state changes.
All props from Upload.Dragger are supported through fieldProps. Refer to ProFormUploadButton props for detailed fieldProps options.
Common Features
Validate files before uploading using beforeUpload: const validateFile = ( file : File ) => {
// Check file type
const validTypes = [ 'image/jpeg' , 'image/png' , 'application/pdf' ];
if ( ! validTypes . includes ( file . type )) {
message . error ( 'Invalid file type!' );
return Upload . LIST_IGNORE ;
}
// Check file size (5MB limit)
const isLt5M = file . size / 1024 / 1024 < 5 ;
if ( ! isLt5M ) {
message . error ( 'File must be smaller than 5MB!' );
return Upload . LIST_IGNORE ;
}
return true ;
};
< ProFormUploadButton
fieldProps = { {
beforeUpload: validateFile
} }
/>
Show Custom Upload Request
Implement custom upload logic with full control: < ProFormUploadButton
fieldProps = { {
customRequest : async ( options ) => {
const { file , onProgress , onSuccess , onError } = options ;
const formData = new FormData ();
formData . append ( 'file' , file );
formData . append ( 'folder' , 'documents' );
try {
const xhr = new XMLHttpRequest ();
// Track upload progress
xhr . upload . addEventListener ( 'progress' , ( e ) => {
if ( e . lengthComputable ) {
const percent = ( e . loaded / e . total ) * 100 ;
onProgress ?.({ percent });
}
});
xhr . addEventListener ( 'load' , () => {
if ( xhr . status === 200 ) {
const response = JSON . parse ( xhr . responseText );
onSuccess ?.( response , xhr );
} else {
onError ?.( new Error ( 'Upload failed' ));
}
});
xhr . addEventListener ( 'error' , () => {
onError ?.( new Error ( 'Upload failed' ));
});
xhr . open ( 'POST' , '/api/upload' );
xhr . setRequestHeader ( 'Authorization' , `Bearer ${ token } ` );
xhr . send ( formData );
} catch ( error ) {
onError ?.( error as Error );
}
}
} }
/>
Show Controlled File List
Manage file list with controlled state: const [ fileList , setFileList ] = useState < UploadFile []>([
{
uid: '-1' ,
name: 'existing-file.png' ,
status: 'done' ,
url: 'https://example.com/file.png' ,
},
]);
< ProFormUploadButton
value = { fileList }
fieldProps = { {
onChange : ( info ) => {
let newFileList = [ ... info . fileList ];
// Limit to most recent 3 files
newFileList = newFileList . slice ( - 3 );
// Update file status
newFileList = newFileList . map (( file ) => {
if ( file . response ) {
// Set url from response
file . url = file . response . url ;
}
return file ;
});
setFileList ( newFileList );
},
onRemove : ( file ) => {
// Confirm before removing
return new Promise (( resolve ) => {
Modal . confirm ({
title: 'Delete file?' ,
onOk : () => resolve ( true ),
onCancel : () => resolve ( false ),
});
});
}
} }
/>
Customize image preview behavior: const [ previewOpen , setPreviewOpen ] = useState ( false );
const [ previewImage , setPreviewImage ] = useState ( '' );
const handlePreview = async ( file : UploadFile ) => {
if ( ! file . url && ! file . preview ) {
file . preview = await getBase64 ( file . originFileObj );
}
setPreviewImage ( file . url || file . preview );
setPreviewOpen ( true );
};
< ProFormUploadButton
listType = "picture-card"
imageProps = { {
preview: {
visible: previewOpen ,
onVisibleChange: setPreviewOpen ,
toolbarRender : ( originalNode , info ) => (
< Space >
{ originalNode }
< DownloadOutlined onClick = { () => downloadImage ( info . current ) } />
</ Space >
)
}
} }
fieldProps = { {
onPreview: handlePreview
} }
/>
Show Transform Value for Submission
Transform file list for form submission: < ProFormUploadButton
name = "attachments"
// Transform for submission - extract URLs or IDs
transform = { ( value : UploadFile []) => {
return value
?. filter ( file => file . status === 'done' )
?. map ( file => ({
uid: file . uid ,
name: file . name ,
url: file . response ?. url || file . url ,
id: file . response ?. id
}));
} }
// Convert stored data back to UploadFile format
convertValue = { ( value : any []) => {
return value ?. map ( item => ({
uid: item . uid || item . id ,
name: item . name ,
status: 'done' as const ,
url: item . url
}));
} }
/>
In read-only mode, upload components display file list without upload controls: < ProFormUploadButton
readonly
name = "documents"
label = "Documents"
/>
< ProFormUploadDragger
proFieldProps = { { mode: 'read' } }
name = "files"
label = "Files"
/>