# ADR 0004: Media behind an S3-like interface - Status: accepted - Date: 2026-09 ## Context Attachments (images, files, videos) need storage, thumbnails for images, and bounded upload size. Storage must survive container restarts and, ideally, be swappable without touching API code. ## Decision Define a `Storage` interface (`Save`/`Open`/`Delete` keyed by opaque keys) in `internal/media`. Phase 2 ships `Local` — files on disk with atomic temp-file+rename writes and path-traversal protection. API handlers depend only on the interface. ## Consequences - Metadata lives in Postgres (`media` table); bytes live in storage. - Replacing disk with MinIO/S3 means a new `Storage` implementation, no handler changes. - Image thumbnails are generated with stdlib decoding + `x/image/draw`, avoiding CGO and external binaries.