0
# rc-upload
1
2
React Upload component with support for AJAX uploads, drag-and-drop, directory uploads, and multiple upload methods. Provides comprehensive file upload functionality with extensive customization options and backward compatibility.
3
4
## Package Information
5
6
- **Package Name**: rc-upload
7
- **Package Type**: npm
8
- **Language**: TypeScript
9
- **Installation**: `npm install rc-upload`
10
11
## Core Imports
12
13
```typescript
14
import Upload, { UploadProps } from "rc-upload";
15
```
16
17
For CommonJS:
18
19
```javascript
20
const Upload = require("rc-upload");
21
const { UploadProps } = require("rc-upload"); // Type only available in TypeScript
22
```
23
24
## Basic Usage
25
26
```typescript
27
import Upload from "rc-upload";
28
29
// Basic file upload
30
<Upload
31
action="https://jsonplaceholder.typicode.com/posts/"
32
accept=".jpg,.png,.gif"
33
multiple
34
onStart={(file) => {
35
console.log('Upload started:', file.name);
36
}}
37
onSuccess={(response, file) => {
38
console.log('Upload successful:', file.name, response);
39
}}
40
onError={(error, response, file) => {
41
console.log('Upload failed:', error);
42
}}
43
>
44
<button>Click to Upload</button>
45
</Upload>
46
47
// Advanced usage with custom request
48
<Upload
49
customRequest={({ file, onSuccess, onError, onProgress }) => {
50
const formData = new FormData();
51
formData.append('file', file);
52
53
fetch('/api/upload', {
54
method: 'POST',
55
body: formData
56
})
57
.then(response => response.json())
58
.then(data => onSuccess(data, file))
59
.catch(error => onError(error));
60
}}
61
directory
62
onStart={(file) => console.log('Started:', file.name)}
63
>
64
<div>Drag files or folders here</div>
65
</Upload>
66
```
67
68
## Capabilities
69
70
### Upload Component
71
72
The main React component that provides file upload functionality with drag-and-drop support, AJAX uploads, and extensive customization options.
73
74
```typescript { .api }
75
/**
76
* Main Upload component providing comprehensive file upload functionality
77
*/
78
class Upload extends React.Component<UploadProps> {
79
/**
80
* Abort upload for a specific file
81
* @param file - The file to abort upload for
82
*/
83
abort(file: RcFile): void;
84
}
85
86
export default Upload;
87
```
88
89
### Upload Configuration
90
91
Core configuration properties for controlling upload behavior, validation, and customization.
92
93
```typescript { .api }
94
interface UploadProps extends Omit<React.InputHTMLAttributes<HTMLInputElement>, 'onError' | 'onProgress'> {
95
/** Upload URL - can be string or function returning URL/Promise<URL> */
96
action?: Action;
97
/** HTTP method for upload request */
98
method?: UploadRequestMethod;
99
/** Additional form data to include with upload */
100
data?: Record<string, unknown> | ((file: RcFile | string | Blob) => Record<string, unknown>);
101
/** Custom HTTP headers */
102
headers?: UploadRequestHeader;
103
/** Include credentials in CORS requests */
104
withCredentials?: boolean;
105
/** Custom upload implementation */
106
customRequest?: (option: UploadRequestOption) => void | { abort: () => void };
107
108
/** File type restrictions (MIME types or extensions) */
109
accept?: string;
110
/** Allow multiple file selection */
111
multiple?: boolean;
112
/** Enable directory upload (deprecated, use folder instead) */
113
directory?: boolean;
114
/** Enable directory/folder upload */
115
folder?: boolean;
116
/** Enable paste-to-upload functionality */
117
pastable?: boolean;
118
119
/** Wrapper component type */
120
component?: React.ComponentType<any> | string;
121
/** CSS class name */
122
className?: string;
123
/** Inline styles */
124
style?: React.CSSProperties;
125
/** CSS class prefix */
126
prefixCls?: string;
127
/** Element ID */
128
id?: string;
129
/** Disable upload functionality */
130
disabled?: boolean;
131
/** Open file dialog on click */
132
openFileDialogOnClick?: boolean;
133
/** Whether control elements are inside component */
134
hasControlInside?: boolean;
135
136
/** Nested class names */
137
classNames?: {
138
input?: string;
139
};
140
/** Nested styles */
141
styles?: {
142
input?: React.CSSProperties;
143
};
144
145
/** Pre-upload validation/transformation hook */
146
beforeUpload?: (file: RcFile, FileList: RcFile[]) => BeforeUploadFileType | Promise<void | BeforeUploadFileType> | void;
147
148
/** Called when file upload starts */
149
onStart?: (file: RcFile) => void;
150
/** Called during upload progress */
151
onProgress?: (event: UploadProgressEvent, file: RcFile) => void;
152
/** Called on successful upload */
153
onSuccess?: (response: Record<string, unknown>, file: RcFile, xhr: XMLHttpRequest) => void;
154
/** Called on upload error */
155
onError?: (error: Error, ret: Record<string, unknown>, file: RcFile) => void;
156
/** Called when batch upload starts */
157
onBatchStart?: (fileList: Array<{ file: RcFile; parsedFile: Exclude<BeforeUploadFileType, boolean> }>) => void;
158
159
/** Custom click handler */
160
onClick?: (e: React.MouseEvent<HTMLDivElement> | React.KeyboardEvent<HTMLDivElement>) => void;
161
/** Mouse enter handler */
162
onMouseEnter?: (e: React.MouseEvent<HTMLDivElement>) => void;
163
/** Mouse leave handler */
164
onMouseLeave?: (e: React.MouseEvent<HTMLDivElement>) => void;
165
}
166
```
167
168
### File Types and Interfaces
169
170
Core type definitions for files, upload requests, and configuration options.
171
172
```typescript { .api }
173
/**
174
* Enhanced File interface with unique identifier
175
*/
176
interface RcFile extends File {
177
/** Unique identifier for the file */
178
uid: string;
179
}
180
181
/**
182
* Upload request configuration and callbacks
183
*/
184
interface UploadRequestOption<T = any> {
185
/** Upload progress callback */
186
onProgress?: (event: UploadProgressEvent, file?: UploadRequestFile) => void;
187
/** Upload error callback */
188
onError?: (event: UploadRequestError | ProgressEvent, body?: T) => void;
189
/** Upload success callback */
190
onSuccess?: (body: T, fileOrXhr?: UploadRequestFile | XMLHttpRequest) => void;
191
/** Additional form data */
192
data?: Record<string, unknown>;
193
/** Target filename */
194
filename?: string;
195
/** File to upload */
196
file: UploadRequestFile;
197
/** Include credentials */
198
withCredentials?: boolean;
199
/** Upload URL */
200
action: string;
201
/** HTTP headers */
202
headers?: UploadRequestHeader;
203
/** HTTP method */
204
method: UploadRequestMethod;
205
}
206
207
/**
208
* Upload progress event with percentage
209
*/
210
interface UploadProgressEvent extends Partial<ProgressEvent> {
211
/** Upload progress percentage (0-100) */
212
percent?: number;
213
}
214
215
/**
216
* Enhanced error interface for upload failures
217
*/
218
interface UploadRequestError extends Error {
219
/** HTTP response status */
220
status?: number;
221
/** HTTP method used */
222
method?: UploadRequestMethod;
223
/** Request URL */
224
url?: string;
225
}
226
```
227
228
### Type Aliases
229
230
Utility type definitions used throughout the upload component.
231
232
```typescript { .api }
233
/** Upload URL - string or function returning URL */
234
type Action = string | ((file: RcFile) => string | PromiseLike<string>);
235
236
/** HTTP methods supported for upload */
237
type UploadRequestMethod = 'POST' | 'PUT' | 'PATCH' | 'post' | 'put' | 'patch';
238
239
/** HTTP headers object */
240
type UploadRequestHeader = Record<string, string>;
241
242
/** Return type for beforeUpload hook */
243
type BeforeUploadFileType = File | Blob | boolean | string;
244
245
/** File type for upload requests */
246
type UploadRequestFile = Exclude<BeforeUploadFileType, File | boolean> | RcFile;
247
```
248
249
## Usage Examples
250
251
### Directory Upload
252
253
```typescript
254
import Upload from "rc-upload";
255
256
<Upload
257
directory
258
action="/api/upload"
259
onStart={(file) => {
260
console.log('Starting upload:', file.name);
261
console.log('File path:', file.webkitRelativePath); // Available for directory uploads
262
}}
263
onSuccess={(response, file) => {
264
console.log('Upload completed:', file.name);
265
}}
266
>
267
<div style={{ padding: '20px', border: '2px dashed #ccc' }}>
268
Click or drag folders here
269
</div>
270
</Upload>
271
```
272
273
### Custom Request Handler
274
275
```typescript
276
import Upload from "rc-upload";
277
278
const customUpload = ({ file, onSuccess, onError, onProgress }) => {
279
const formData = new FormData();
280
formData.append('file', file);
281
formData.append('userId', '123');
282
283
const xhr = new XMLHttpRequest();
284
285
xhr.upload.addEventListener('progress', (e) => {
286
if (e.lengthComputable) {
287
onProgress({ percent: (e.loaded / e.total) * 100 });
288
}
289
});
290
291
xhr.addEventListener('load', () => {
292
if (xhr.status === 200) {
293
onSuccess(JSON.parse(xhr.responseText), file);
294
} else {
295
onError(new Error(`Upload failed: ${xhr.status}`));
296
}
297
});
298
299
xhr.addEventListener('error', () => {
300
onError(new Error('Network error'));
301
});
302
303
xhr.open('POST', '/api/upload');
304
xhr.send(formData);
305
};
306
307
<Upload customRequest={customUpload}>
308
<button>Upload with Custom Handler</button>
309
</Upload>
310
```
311
312
### File Validation
313
314
```typescript
315
import Upload from "rc-upload";
316
317
const validateFile = (file, fileList) => {
318
// Check file size (max 5MB)
319
if (file.size > 5 * 1024 * 1024) {
320
console.error('File too large');
321
return false; // Reject file
322
}
323
324
// Check file type
325
const allowedTypes = ['image/jpeg', 'image/png', 'image/gif'];
326
if (!allowedTypes.includes(file.type)) {
327
console.error('Invalid file type');
328
return false;
329
}
330
331
// Transform file name
332
const newFile = new File([file], `prefix_${file.name}`, {
333
type: file.type,
334
lastModified: file.lastModified,
335
});
336
337
return newFile; // Return transformed file
338
};
339
340
<Upload
341
action="/api/upload"
342
accept=".jpg,.png,.gif"
343
beforeUpload={validateFile}
344
onError={(error, response, file) => {
345
console.error('Upload error:', error.message);
346
}}
347
>
348
<button>Upload Images Only</button>
349
</Upload>
350
```
351
352
### Drag and Drop with Visual Feedback
353
354
```typescript
355
import Upload from "rc-upload";
356
import { useState } from "react";
357
358
const DragUpload = () => {
359
const [dragOver, setDragOver] = useState(false);
360
361
return (
362
<Upload
363
action="/api/upload"
364
multiple
365
onStart={() => setDragOver(false)}
366
onMouseEnter={() => setDragOver(true)}
367
onMouseLeave={() => setDragOver(false)}
368
style={{
369
display: 'block',
370
width: '300px',
371
height: '200px',
372
border: `2px dashed ${dragOver ? '#007acc' : '#ccc'}`,
373
borderRadius: '8px',
374
padding: '20px',
375
textAlign: 'center',
376
cursor: 'pointer',
377
backgroundColor: dragOver ? '#f0f8ff' : '#fafafa'
378
}}
379
>
380
<div>
381
<p>๐ Drop files here or click to upload</p>
382
<p style={{ fontSize: '12px', color: '#666' }}>
383
Supports multiple files and drag & drop
384
</p>
385
</div>
386
</Upload>
387
);
388
};
389
```