@humaan/payload-storage-imagekit
v2.3.3
Published
ImageKit storage adapter plugin for Payload CMS uploads
Readme
payload-storage-imagekit
ImageKit storage adapter plugin for Payload CMS uploads.
This plugin integrates @payloadcms/plugin-cloud-storage with ImageKit and provides:
- Uploads to ImageKit per collection
- Optional client-side uploads for Payload admin to bypass request size limits on platforms like Vercel
- Required root folder with per-collection subfolders
- Stored ImageKit references (
imagekit.fileId,imagekit.url,imagekit.thumbnailUrl) crop: falsefor configured upload collections- Admin thumbnails using ImageKit transforms (
tr=w-300,h-300) - Built-in thumbnail path for videos and PDFs in admin previews
- Migration utility for copying collection files between ImageKit folders
Installation
pnpm add @humaan/payload-storage-imagekitUsage
import { buildConfig } from 'payload'
import { imagekitStorage } from '@humaan/payload-storage-imagekit'
export default buildConfig({
collections: [
{
slug: 'media',
upload: true,
fields: [],
},
],
plugins: [
imagekitStorage({
clientUploads: true,
folder: '/payload-uploads',
collections: {
media: true,
},
privateKey: process.env.IMAGEKIT_PRIVATE_KEY || '',
publicKey: process.env.IMAGEKIT_PUBLIC_KEY || '',
urlEndpoint: process.env.IMAGEKIT_URL_ENDPOINT || '',
}),
],
})Configuration
imagekitStorage(options) options:
collections(required):Partial<Record<UploadCollectionSlug, true>>folder(required): root upload folder in ImageKit, e.g./payload-uploadsprivateKey(required): ImageKit private API keypublicKey(required): ImageKit public keyurlEndpoint(required): ImageKit URL endpoint, e.g.https://ik.imagekit.io/your_idclientUploads(optional): whentrue, Payload admin uploads go directly from the browser to ImageKit before Payload fetches the file back for persistence and image-size generation. This helps avoid server request body limits such as Vercel's. Duplicate filenames still follow Payload's normal safe-name behavior, so a secondpug.jpgbecomespug-1.jpginstead of overwriting the first asset in ImageKit.enabled(optional): enable / disable pluginalwaysInsertFields(optional): pass-through to cloud storage plugindisablePayloadAccessControl(optional): pass-through to cloud storage plugin
Exports
imagekitStorage(primary)migrateFolderpayloadStorageImagekit(alias ofimagekitStorage)
Folder Migration
Use migrateFolder to copy uploads from one ImageKit root folder to another (e.g. staging to production).
Behavior:
- Copies files one-by-one per collection
- Creates destination folders automatically if they do not exist
- Optional database update via Payload local API
- Dry-run is enabled by default (
dryRun: true) - Copies from the configured source folder path first, with stored
imagekit.urlas a fallback only when the source file cannot be found
Example:
import { migrateFolder } from '@humaan/payload-storage-imagekit'
import config from '@payload-config'
import { getPayload } from 'payload'
const payload = await getPayload({ config })
const results = await migrateFolder({
collections: { media: true },
dryRun: true,
from: process.env.IMAGEKIT_FOLDER!,
payload,
privateKey: process.env.IMAGEKIT_PRIVATE_KEY!,
to: process.env.IMAGEKIT_FOLDER_MIGRATION_DESTINATION!,
urlEndpoint: process.env.IMAGEKIT_URL_ENDPOINT!,
})
console.log(results)
await payload.destroy()migrateFolder(options) options:
collections(required):Partial<Record<UploadCollectionSlug, true>>from(required): source root folder, e.g./payload-uploads-stagingto(required): destination root folder, e.g./payload-uploads-productionprivateKey(required): ImageKit private API keyurlEndpoint(required): ImageKit URL endpointdryRun(optional, defaulttrue): whentrue, logs what would happen without writespayload(optional): when provided anddryRunisfalse, updatesurl+imagekit.*fields
Run a migration script:
# dry-run (default)
pnpx tsx --env-file=../.env imagekit-migration.ts
# live run
DRY_RUN=false pnpx tsx --env-file=../.env imagekit-migration.tsNotes
- Files are uploaded under:
<folder>/<collectionSlug>/<filename>. - With
clientUploads: true, the browser uploads the original file directly to ImageKit, then Payload continues its normal document save flow using the uploaded asset. - Deletion prefers stored
imagekit.fileId, with path lookup fallback. - Admin thumbnail behavior:
- Images:
<imagekit.url>?tr=w-300,h-300 - Videos / PDFs:
<imagekit.url>/ik-thumbnail.jpg?tr=w-300,h-300
- Images:
Development
pnpm dev
pnpm test:int
pnpm build