A minimal and flexible uploader component tailored for Cloudflare R2 bucket. It supports multipart upload and was tested with files up to ~10 GB size. Fully compatible with PortalJS.
- R2 blob storage support (or any S3 API compatible storage)
- Tested with ~10 GB files
File content hashingRemoved to improve performance.- Drag and drop
- URL pre-signing
- Multipart upload support
- Customizable
The intent of this repo is to provide simple to use and simple to copy and paste file uploader component for Next.js.
The file uploader components use Uppy under the hood and are accompanied by the necessary API routes.
The components were written mainly to be used with R2 but any blob storage with a S3-compatible API should work with just a few tweaks.
Good for simple projects or for bootstrapping more complex file-uploading workflows when customized.
This repo provides two different sets of component and API routes, one for simple uploads and the other for multipart uploads. If your application is meant to handle large files, multipart upload is the recommended approach. Choose one and follow the instructions below.
On your project, run:
npm i @uppy/core @uppy/react @uppy/aws-s3 @uppy/dashboard @uppy/drag-drop @uppy/progress-bar @uppy/file-input crypto-hash @aws-sdk/client-s3 @aws-sdk/s3-request-presigner
If you want to use the multipart upload component, one more dependency is required:
npm i @uppy/aws-s3-multipart
Copy the following file to the components folder of your project:
https://github.com/datopian/r2-bucket-uploader/blob/main/components/FileUploader.tsx
Next, copy the following file into your project's pages/api/
folder:
https://github.com/datopian/r2-bucket-uploader/blob/main/pages/api/upload.ts
Copy the following file to the components folder of your project:
https://github.com/datopian/r2-bucket-uploader/blob/main/components/MultipartFileUploader.tsx
Next, copy the following folder into your project's pages/api/
folder:
https://github.com/datopian/r2-bucket-uploader/blob/main/pages/api/multipart-upload
In your .env
file, set the following environment variables:
R2_ACCOUNT_ID=
R2_ACCESS_KEY_ID=
R2_SECRET_KEY_ID=
R2_BUCKET_NAME=
The values should be available from the R2 management dashboard on Cloudflare.
Create the following CORS settings in order to make the upload components work with your bucket:
[
{
"AllowedOrigins": ["*"],
"AllowedMethods": ["GET", "PUT"],
"AllowedHeaders": ["Authorization", "content-type"],
"ExposeHeaders": ["ETag", "Location"],
"MaxAgeSeconds": 3000
},
{
"AllowedOrigins": ["*"],
"AllowedMethods": ["GET"],
"AllowedHeaders": ["*"]
}
]
Optionally, to increase security you can also customize the AllowedOrigins
properties.
Now you can import <FileUploader />
or <MultipartFileUploader />
anywhere in your project. E.g.:
// pages/index.js
import FileUploader from "@components/FileUploader";
import MultipartFileUploader from "@components/MultipartFileUploader";
export default function Home() {
return (
<div>
<h1>Upload an image:</h1>
<FileUploader
onUploadSuccess={(result) => alert(JSON.stringify(result))}
/>
{/* OR */}
<MultipartFileUploader
onUploadSuccess={(result) => alert(JSON.stringify(result))}
/>
</div>
);
}