Project structure
The Valcraven monorepo layout at a glance — apps/web, apps/realtime, apps/mobile, and packages/core.
Valcraven is an npm-workspace monorepo (workspaces: ["apps/*", "packages/*"]). The root package.json is named valcraven-monorepo and delegates the common scripts to the web app, so npm install, npm run dev, npm run build, npm run db:migrate, and npm run build:cf all run from the repo root (each forwards to apps/web via -w apps/web). For a deeper tour of how the workspaces fit together, see Monorepo architecture.
Layout
valcraven/
├── apps/
│ ├── web/ # The Next.js app — the product itself
│ ├── realtime/ # Cloudflare Worker hosting the AI agent
│ └── mobile/ # Expo (React Native) app — opt-in
├── packages/
│ └── core/ # @valcraven/core — shared schemas, types, API client
├── docker-compose.yml # dev / prod profiles
├── tailscale/ # Caddy + Tailscale sidecar config
├── cli/ # Go scaffolding CLI
├── changelogs/ # Template changelog entries
├── AGENTS.md # What's already built (the "don't rebuild it" reference)
└── CLAUDE.md # AI-assistant conventions for this repoThe workspaces
apps/web — the Next.js app
This is the product: the App Router pages, API routes, admin panel, auth, billing, email, blog, and docs. Almost all feature work happens here. Notable subdirectories:
| Path | Contents |
|---|---|
app/ | App Router pages and API routes. Authenticated features live under /app. |
components/ | React components (ui/, admin/, landing/). |
lib/ | The building blocks — auth.ts, db.ts, email.ts, stripe, errors.ts, logger, chat config, and more. |
content/ | MDX content: the blog, changelog, and these docs. |
migrations/ | SQLite/D1 schema migrations, applied in lexical order. |
e2e/ | Playwright end-to-end tests. |
wrangler.toml | Cloudflare Workers bindings and config (D1, R2, queues, cron). |
next.config.ts, Dockerfile, Dockerfile.dev | Build and dev config. |
Runs on localhost:3013 in the Docker dev stack. Deploys to Cloudflare Workers via OpenNext — see Cloudflare Workers architecture.
apps/realtime — the realtime Worker
A separate Cloudflare Worker (name valcraven-realtime) built on the Cloudflare Agents SDK. It hosts a per-user AppAgent Durable Object that provides WebSocket chat, chat tools, and scheduled wakes. In dev it runs under wrangler dev (internal port 8788) behind the Caddy sidecar at /agents/*; in production it deploys and is wired to the web app through a service binding. AI chat is WebSocket-only and goes through this Worker. See The realtime Worker.
The realtime Worker deploys separately from the web app (
npm run deploy:realtime), and itsAGENTS_INTERNAL_SECRETmust match the web app's for server-to-server calls to succeed.
apps/mobile — the Expo app (opt-in)
A native iOS/Android app built with Expo (SDK 54) and expo-router, runnable in the Expo Go app on a physical device. It authenticates against the web app's Better Auth backend over the network and shares all request/response logic with the web app through @valcraven/core. It's excluded from the default scaffold — opt in when creating a project (or add it later). See Mobile.
packages/core — @valcraven/core
A shared workspace package with no next, Drizzle, or DOM dependencies: Zod schemas, Better Auth $Infer types, and a typed fetch API client. Both apps/web and apps/mobile import it so web and mobile don't duplicate schemas, types, or client logic.
@valcraven/coreis intra-app sharing, not a cross-app dependency. It'sprivateand unpublished — each app that's scaffolded from Valcraven carries its own copy that drifts independently. A change to the template'spackages/corereaches a downstream app only through thevalcraven-syncskill, like the rest of the template.
Related
- Monorepo architecture — how the pieces connect at build and run time.
- Quickstart — get the dev stack running.
- Create a project — scaffold your own copy of this layout.