Ad operations for video podcasts. Nullpod combines episode ingest, sponsor creative, dynamic marker placement, waveform navigation, composed playback, and timeline snapshots in one dark control surface.
- Next.js 16 and React 19
- TypeScript and Tailwind CSS
- Drizzle ORM with Cloudflare D1
- Cloudflare Stream for video ingest and playback
- Cloudflare R2 for media storage
- Cloudflare Media Transformations for audio extraction
- OpenNext adapter for Workers deployment
- TanStack Query and Zustand for editor state
- HLS.js for browser playback
npm install
npm run devOpen http://localhost:3000. The root route redirects to the episode launcher at /ads.
The dev server uses initOpenNextCloudflareForDev() to provide local D1, R2, and Media bindings via getPlatformProxy.
Runtime uploads and Stream synchronization use:
CLOUDFLARE_ACCOUNT_ID=<your-account-id>
CLOUDFLARE_STREAM_API_TOKEN=<your-stream-token>Useful commands:
npm run cf:whoami
npm run cf:stream:list -- --limit 20
npm run cf:stream:get -- --uid <stream-uid>
npm run cf:stream:seed -- --map scripts/cloudflare/stream-seed-map.json# Apply D1 migrations
npx wrangler d1 migrations apply nullpod --remote
# Build and deploy
npm run deployPreview locally in the Workers runtime:
npm run previewGenerate Cloudflare env types:
npm run cf-typegen| Binding | Type | Purpose |
|---|---|---|
DB |
D1 | Relational data (episodes, markers, sessions, snapshots) |
MEDIA |
R2 | Media artifacts and seed images |
MEDIA_TRANSFORM |
Media | Audio extraction for waveform analysis |
ASSETS |
Assets | Static assets from Next.js build |
npm run lint
npm run build- D1 data store replaces
better-sqlite3. All queries usedrizzle-orm/d1viagetCloudflareContext(). - Synthetic waveforms are generated from duration data. Real PCM analysis requires a Cloudflare Container with FFmpeg.
- Export jobs queue but do not execute on Workers. Stitched export execution requires a Cloudflare Container.
- Seed data is inserted on first D1 query via
ensureD1Seeded(). - Seed images are served from
public/seed/as static assets.