# dimah-s3

> Presign-first S3 toolkit: the server signs, the browser talks to your bucket. Not a hosted uploader, and not an S3 SDK wrapper.

TypeScript packages: `@dimah-s3/server` (handlers and hooks), `@dimah-s3/react` (headless client), optional `@dimah-s3/ui` (shadcn) and `@dimah-s3/db` (object tracking). Protocol types live in `@dimah-s3/core`. You pass an AWS SDK `S3Client`.

HTTP adapters: Next.js, Express, Hono, Fastify, Elysia, SvelteKit, Node, and Fetch. CLI starters include Next.js, Vite + Hono, and Hono.

Use it for direct uploads to a bucket you own, typed authorization, multipart/resume, and the same route rules for download and delete. Skip it when you need image or video transforms. List, copy, tagging, and other S3 operations stay in your own AWS SDK code.

Neighbors: UploadThing (hosted), Better Upload (BYO-bucket, upload-only), Uppy (client dashboard; can sit in front).

Install: `npx @dimah-s3/cli@latest create` or `npm i @dimah-s3/server @dimah-s3/react @aws-sdk/client-s3`.

Constraints:

- Never expose S3 credentials. The client sends a route name; the server owns keys under that route's `keyPrefix` (default: the route name). Default key is `{keyPrefix}/{uuid}/{name}`. `keyPrefix: false` generates `{uuid}/{name}`. Nested or identical prefixes across routes are rejected at init.
- Prefer one feature per named route. Combine upload, download, and delete only when those callers share the key namespace.
- Scope per-user folders with `upload.object` / `guard`. Enforce ownership with `db()` or a download/delete `guard`.
- Trust `onConfirmed` (HeadObject, including multipart complete) for size and type, not the presign body. `fileTypes` is the S3 Content-Type header and filename, not a byte sniff.
- Without `db()`, download can presign unconfirmed keys under `keyPrefix`. Auth and quota stay in consumer hooks.

## Docs

- Framework: All-in-one, quickstart and features
  - [Introduction](https://s3.dimah.dev/docs.md): Full-stack S3 toolkit for the React ecosystem — server handlers, client hooks, shadcn UI, and database tracking.
  - [Quickstart](https://s3.dimah.dev/docs/quickstart.md): A working S3 upload in minutes — new app or existing project.
  - [Comparison](https://s3.dimah.dev/docs/comparison.md): Compare dimah-s3 with Better Upload, UploadThing, and Uppy.

  - **UI**
  - [UI Setup](https://s3.dimah.dev/docs/react/ui.md): Install shadcn-compatible upload, download, and delete UI components.
  - Components: Upload, download, delete, and status rows
    - [Attachment](https://s3.dimah.dev/docs/react/ui/components/attachment.md): Reusable status rows for file previews, progress indicators, and error feedback.
    - [Upload Button](https://s3.dimah.dev/docs/react/ui/components/upload-button.md): File picker button for single- or multi-file uploads with inline status and toast support.
    - [Upload Dropzone](https://s3.dimah.dev/docs/react/ui/components/upload-dropzone.md): Drag-and-drop surface for single- or multi-file uploads with file queue list.
    - [Download Button](https://s3.dimah.dev/docs/react/ui/components/download-button.md): Button component to trigger native browser downloads from S3.
    - [Progress Download Button](https://s3.dimah.dev/docs/react/ui/components/progress-download-button.md): Download button with animated progress indicator and in-flight cancellation.
    - [Delete Button](https://s3.dimah.dev/docs/react/ui/components/delete-button.md): Button component to remove S3 objects with built-in confirmation dialog.
  - Customization: Theme tokens and building your own controls
    - [Theming](https://s3.dimah.dev/docs/react/ui/customization/theming.md): Customize color tokens and styling for @dimah-s3/ui components.
    - [Custom UI](https://s3.dimah.dev/docs/react/ui/customization/custom-ui.md): Build bespoke upload interfaces using headless hooks and custom components.

  - **Features**
  - Providers: Amazon S3, Cloudflare R2, and MinIO — CORS, PUT vs POST, and addressing
    - [Providers](https://s3.dimah.dev/docs/providers.md): Configure Amazon S3, Cloudflare R2, MinIO, and other S3-compatible storage.
    - [Amazon S3](https://s3.dimah.dev/docs/providers/aws-s3.md): Configuration, CORS, and bucket policies for AWS S3.
    - [Cloudflare R2](https://s3.dimah.dev/docs/providers/cloudflare-r2.md): PUT uploads, endpoint configuration, and CORS for Cloudflare R2.
    - [MinIO](https://s3.dimah.dev/docs/providers/minio.md): Self-hosted S3 storage with path-style addressing and server CORS.
  - Database: Optional plugin for ownership, listings, and object lifecycle
    - [Introduction](https://s3.dimah.dev/docs/db.md): Optional plugin to track object ownership, lifecycle, and listings in your database.
    - [Setup](https://s3.dimah.dev/docs/db/setup.md): Install @dimah-s3/db, add the schema, and register the db() plugin.
    - [Database Hooks](https://s3.dimah.dev/docs/db/hooks.md): Automatic lifecycle synchronization and ownership validation by @dimah-s3/db.
    - [API](https://s3.dimah.dev/docs/db/api.md): List objects and measure usage on the server and in the browser.
    - [Purge Stale Uploads](https://s3.dimah.dev/docs/db/purge.md): Clean up unconfirmed pending database rows and incomplete S3 uploads.
  - [Internationalization](https://s3.dimah.dev/docs/i18n.md): English by default. Pass a partial map to localize.
- Core
  - [Core](https://s3.dimah.dev/docs/core.md): Protocol SSOT — routes, createS3Client, shared helpers and APIError
- Server: Backend for dimah-s3
  - [Introduction](https://s3.dimah.dev/docs/server.md): Backend handlers, route policies, and lifecycle hooks for S3 file flows.
  - [Setup](https://s3.dimah.dev/docs/server/setup.md): Install `@dimah-s3/server`, configure S3, and mount your route handler.
  - [Routes](https://s3.dimah.dev/docs/server/routes.md): Named file routes — server-owned keys, constraints, and object policies.
  - [Security](https://s3.dimah.dev/docs/server/security.md): Server-owned keys, ACL, and verified file metadata.
  - [Errors](https://s3.dimah.dev/docs/server/errors.md): Stable error codes, error helpers, and APIError handling.

  - **Hooks**
  - [Global Guard](https://s3.dimah.dev/docs/server/hooks/global-guard.md): Request-level policy hook executing before all operations and plugin endpoints.
  - [Upload Hooks](https://s3.dimah.dev/docs/server/hooks/upload.md): Presign, authorize, confirm, and persist verified upload metadata.
  - [Download Hooks](https://s3.dimah.dev/docs/server/hooks/download.md): Authorize and sign GET download URLs or proxy streams.
  - [Delete Hooks](https://s3.dimah.dev/docs/server/hooks/delete.md): Authorize deletion and execute cleanup after S3 removes the object.
  - [Multipart Hooks](https://s3.dimah.dev/docs/server/hooks/multipart.md): Large-file multipart upload lifecycle, part authorization, and assembly.

  - **Extend**
  - [Plugins](https://s3.dimah.dev/docs/server/plugins.md): Extend dimahS3 with definePlugin — custom endpoints, lifecycle hooks, and typed context.
- Client: Headless S3 client for React
  - [Introduction](https://s3.dimah.dev/docs/react.md): Headless React client for S3 upload, download, and delete flows.
  - [Setup](https://s3.dimah.dev/docs/react/setup.md): Initialize `@dimah-s3/react`, configure S3Provider, and call your first hook.

  - **Hooks**
  - [useUpload](https://s3.dimah.dev/docs/react/hooks/upload.md): Headless React hook for single and multi-file S3 uploads with progress and retries.
  - [useDownload](https://s3.dimah.dev/docs/react/hooks/download.md): Headless React hook for presigned S3 downloads with browser navigation, fetch streams, and inline preview.
  - [useDelete](https://s3.dimah.dev/docs/react/hooks/delete.md): Headless React hook for single, batch, and confirmation-driven object deletion.

  - **Extra**
  - [Helpers](https://s3.dimah.dev/docs/react/helpers.md): Formatting utilities, validation functions, and error helpers.
  - [Upload Store](https://s3.dimah.dev/docs/react/upload-store.md): Persist multipart upload state to seamlessly resume large uploads after page reload.
  - [Forms](https://s3.dimah.dev/docs/react/forms.md): Integrate confirmed S3 uploads with React Hook Form or TanStack Form.
  - [TanStack Query](https://s3.dimah.dev/docs/react/tanstack-query.md): Invalidate queries after a confirmed upload. Do not wrap useUpload in useMutation.
  - Bring your own backend: Connect the React client to your API
    - [Bring your own backend](https://s3.dimah.dev/docs/react/custom-backend.md): Connect the React client to your existing API.
    - [Upload](https://s3.dimah.dev/docs/react/custom-backend/upload.md): upload and confirm — presign a single PUT/POST, then verify the object.
    - [Download](https://s3.dimah.dev/docs/react/custom-backend/download.md): download — return a presigned GET URL for an object key.
    - [Delete](https://s3.dimah.dev/docs/react/custom-backend/delete.md): delete — remove an object by key.
    - [Multipart](https://s3.dimah.dev/docs/react/custom-backend/multipart.md): init, signPart, listParts, complete, and abort — large-file uploads.

## Packages

- [@dimah-s3/server](https://www.npmjs.com/package/@dimah-s3/server): presign handlers, hooks, and adapters
- [@dimah-s3/react](https://www.npmjs.com/package/@dimah-s3/react): headless upload, download, and delete hooks
- [@dimah-s3/ui](https://www.npmjs.com/package/@dimah-s3/ui): optional shadcn components
- [@dimah-s3/core](https://www.npmjs.com/package/@dimah-s3/core): protocol SSOT (`S3_API_ROUTES`, `createS3Client`)
- [@dimah-s3/db](https://www.npmjs.com/package/@dimah-s3/db): optional object tracking plugin
- [@dimah-s3/cli](https://www.npmjs.com/package/@dimah-s3/cli): `create` scaffold

## Optional

- [Full docs dump](https://s3.dimah.dev/llms-full.txt): every page as markdown
- [GitHub](https://github.com/dimah-kz/dimah-s3): source and examples
- [X](https://x.com/dimahkzx): updates
