This commit captures the current state before implementing the composable monorepo template system. Key changes included: Infrastructure: - Add CockroachDB provisioner adapter for database provisioning - Add Redis provisioner adapter for cache provisioning - Add build events system with PostgreSQL storage - Add WebSocket endpoint for real-time build progress Code agent improvements: - Fix Claude Code adapter to use default allowed tools instead of dangerously-skip-permissions - Add context-aware stream closing for cancellation support - Improve parser tests for edge cases Build system: - Add build event constants and metrics - Remove deprecated git_operations.go (replaced by pod_git_operations.go) - Add rollback logic for multi-step provisioning operations Documentation: - Add composable-monorepo feature documentation - Add DNS/Cloudflare service documentation - Update deployment and troubleshooting guides Cookbooks: - Add fullstack-app cookbook - Refactor landing-test with shared library Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
13 KiB
Full-Stack App Cookbook
Deploy a full-stack application (Next.js + Go backend) built entirely by Claude through the threesix.ai infrastructure.
Overview
This cookbook creates and deploys a complete full-stack application using agent-driven development:
POST /project/create-and-build
↓
Creates: Gitea repo + DNS + Woodpecker CI + K8s deployment
↓
Enqueues build task with comprehensive prompt
↓
Worker picks up task → Claude builds the entire stack
↓
Agent commits + pushes
↓
CI builds and deploys
↓
Live full-stack app
Claude builds everything from scratch: Next.js frontend with shadcn/ui, Go backend API, Docker configs, and CI pipeline.
Prerequisites
API Access
export RDEV_API_URL="https://rdev.masq-ops.orchard9.ai"
export RDEV_API_KEY="<your-api-key>"
Infrastructure Required
- rdev-api running with embedded worker
- Gitea at https://git.threesix.ai
- Woodpecker CI at https://ci.threesix.ai
- claudebox-0 pod running in rdev namespace
Step 1: Create Project and Build Full-Stack App
Single API call that creates infrastructure AND enqueues the full-stack build:
curl -X POST "$RDEV_API_URL/project/create-and-build" \
-H "X-API-Key: $RDEV_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"name": "my-fullstack-app",
"description": "Full-stack app with Next.js frontend and Go backend",
"build": {
"prompt": "Build a full-stack task management application with the following structure:\n\nFRONTEND (Next.js 14 + shadcn/ui):\n- Create a Next.js 14 app with App Router in /frontend\n- Use shadcn/ui for all components (install with npx shadcn-ui@latest init)\n- Dark theme with modern aesthetic\n- Pages: Dashboard showing tasks, Add Task form, Task detail view\n- Use Tailwind CSS for styling\n- Connect to backend API at /api proxy\n\nBACKEND (Go):\n- Create a Go HTTP server in /backend using chi router\n- Endpoints: GET /api/tasks, POST /api/tasks, GET /api/tasks/{id}, DELETE /api/tasks/{id}\n- In-memory task storage (no database needed)\n- Structured JSON responses\n- CORS middleware for frontend\n\nDOCKER:\n- /frontend/Dockerfile: Multi-stage build for Next.js (node:20-alpine)\n- /backend/Dockerfile: Multi-stage build for Go (golang:1.22-alpine)\n- /docker-compose.yml: Run both services, frontend proxies to backend\n\nCI/CD:\n- /.woodpecker.yml: Build both images, push to registry, deploy to k8s\n\nCreate all necessary files including package.json, go.mod, and configuration files.",
"auto_commit": true,
"auto_push": true
}
}'
Response:
{
"project": {
"project_id": "my-fullstack-app",
"domain": "xyz789ab.threesix.ai",
"git": {
"html_url": "https://git.threesix.ai/jordan/my-fullstack-app"
}
},
"build": {
"task_id": "task-uuid",
"status": "pending",
"status_url": "/builds/task-uuid"
}
}
Step 2: Monitor Build Progress
Poll the build status:
curl -s "$RDEV_API_URL/builds/{task_id}" \
-H "X-API-Key: $RDEV_API_KEY" | jq .
Status progression: pending → running → completed (or failed)
Full-stack builds take longer than simple landing pages. Expect 2-5 minutes.
When completed:
{
"task_id": "task-uuid",
"status": "completed",
"result": {
"success": true,
"commit_sha": "def456",
"files_changed": [
"frontend/package.json",
"frontend/app/page.tsx",
"frontend/app/layout.tsx",
"frontend/components/task-list.tsx",
"frontend/components/add-task-form.tsx",
"frontend/Dockerfile",
"backend/main.go",
"backend/go.mod",
"backend/Dockerfile",
"docker-compose.yml",
".woodpecker.yml"
],
"duration_ms": 180000
}
}
Step 3: Monitor CI Pipeline
The agent's push triggers Woodpecker CI to build both services:
curl -s "$RDEV_API_URL/projects/my-fullstack-app/pipelines" \
-H "X-API-Key: $RDEV_API_KEY" | jq '.data[0]'
Pipeline stages:
- Build frontend Docker image
- Build backend Docker image
- Push both to registry
- Deploy to Kubernetes
Wait for status: "success".
Step 4: Verify Deployment
# Check site is live
curl -I https://xyz789ab.threesix.ai
# Test frontend loads
curl -s https://xyz789ab.threesix.ai | head -20
# Test backend API
curl -s https://xyz789ab.threesix.ai/api/tasks | jq .
# Open in browser
open https://xyz789ab.threesix.ai
Iterating on the App
Add a Feature
curl -X POST "$RDEV_API_URL/projects/my-fullstack-app/builds" \
-H "X-API-Key: $RDEV_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"prompt": "Add task priority levels (low, medium, high) with color-coded badges in the UI. Update the backend Task struct and frontend components to support priorities. Add a priority filter dropdown on the dashboard.",
"auto_commit": true,
"auto_push": true
}'
Fix a Bug
curl -X POST "$RDEV_API_URL/projects/my-fullstack-app/builds" \
-H "X-API-Key: $RDEV_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"prompt": "Fix the task deletion - ensure the DELETE endpoint returns 204 No Content and the frontend removes the task from the list immediately without requiring a page refresh.",
"auto_commit": true,
"auto_push": true
}'
Add Authentication
curl -X POST "$RDEV_API_URL/projects/my-fullstack-app/builds" \
-H "X-API-Key: $RDEV_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"prompt": "Add simple JWT authentication:\n- Backend: Add /api/auth/login endpoint that accepts username/password and returns JWT\n- Backend: Add auth middleware to protect /api/tasks endpoints\n- Frontend: Add login page with shadcn form components\n- Frontend: Store JWT in localStorage, include in API requests\n- Create a demo user (admin/admin123) for testing",
"auto_commit": true,
"auto_push": true
}'
Each build:
- Claude clones the existing repo
- Makes the requested changes
- Commits and pushes
- CI deploys automatically
Alternative Prompts
E-commerce Storefront
curl -X POST "$RDEV_API_URL/project/create-and-build" \
-H "X-API-Key: $RDEV_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"name": "my-store",
"description": "E-commerce storefront",
"build": {
"prompt": "Build an e-commerce storefront:\n\nFRONTEND: Next.js 14 with shadcn/ui, dark theme\n- Product grid with images, prices, descriptions\n- Product detail page\n- Shopping cart (localStorage)\n- Checkout form (no payment processing)\n\nBACKEND: Go with chi router\n- GET /api/products - list products\n- GET /api/products/{id} - product detail\n- POST /api/orders - create order (log to console)\n- Seed with 6 sample products\n\nInclude Dockerfiles and .woodpecker.yml for CI/CD.",
"auto_commit": true,
"auto_push": true
}
}'
Dashboard App
curl -X POST "$RDEV_API_URL/project/create-and-build" \
-H "X-API-Key: $RDEV_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"name": "my-dashboard",
"description": "Analytics dashboard",
"build": {
"prompt": "Build an analytics dashboard:\n\nFRONTEND: Next.js 14 with shadcn/ui + recharts\n- Dashboard with 4 stat cards (users, revenue, orders, growth)\n- Line chart showing weekly trends\n- Bar chart showing top products\n- Recent activity table\n- Dark theme, responsive grid layout\n\nBACKEND: Go with chi router\n- GET /api/stats - return dashboard statistics\n- GET /api/trends - return weekly trend data\n- GET /api/activity - return recent activity\n- Generate realistic sample data\n\nInclude Dockerfiles and .woodpecker.yml for CI/CD.",
"auto_commit": true,
"auto_push": true
}
}'
Adding Custom Domains
# Add custom domain
curl -X POST "$RDEV_API_URL/projects/my-fullstack-app/domains" \
-H "X-API-Key: $RDEV_API_KEY" \
-H "Content-Type: application/json" \
-d '{"domain": "app.mycompany.com"}'
# List all domains
curl -s "$RDEV_API_URL/projects/my-fullstack-app/domains" \
-H "X-API-Key: $RDEV_API_KEY" | jq '.data.domains'
Teardown
curl -X DELETE "$RDEV_API_URL/project/my-fullstack-app" \
-H "X-API-Key: $RDEV_API_KEY"
Removes: DNS records, K8s deployment, project metadata. Gitea repo preserved for safety.
E2E Test Script
Run the full flow:
./cookbooks/scripts/fullstack-test.sh run my-test-fullstack
Check status:
./cookbooks/scripts/fullstack-test.sh status my-test-fullstack
Cleanup:
./cookbooks/scripts/fullstack-test.sh teardown my-test-fullstack
Architecture
┌─────────────────────────────────────────────────────────────────────┐
│ Agent-Driven Full-Stack App │
│ │
│ POST /project/create-and-build │
│ │ │
│ ├──► Gitea: creates repo │
│ ├──► Cloudflare: creates DNS │
│ ├──► Woodpecker: activates CI │
│ ├──► K8s: creates Deployment/Service/Ingress │
│ └──► Work Queue: enqueues build task │
│ │ │
│ ▼ │
│ Worker polls queue, claims task │
│ │ │
│ ▼ │
│ Claude Code executes in claudebox-0: │
│ - Clones repo │
│ - Creates Next.js frontend with shadcn/ui │
│ - Creates Go backend with chi router │
│ - Writes Dockerfiles and CI config │
│ - Commits and pushes │
│ │ │
│ ▼ │
│ Woodpecker CI triggered by push: │
│ - Builds frontend Docker image │
│ - Builds backend Docker image │
│ - Pushes to registry │
│ - Deploys to K8s │
│ │ │
│ ▼ │
│ Full-stack app live at https://{slug}.threesix.ai │
│ - Frontend: Next.js + shadcn/ui │
│ - Backend: Go API │
│ │
└─────────────────────────────────────────────────────────────────────┘
Troubleshooting
Build stuck in pending
# Check worker status
curl -s "$RDEV_API_URL/workers" -H "X-API-Key: $RDEV_API_KEY" | jq '.data.summary'
# Should show at least 1 idle worker
Build failed
# Get build details with full output
curl -s "$RDEV_API_URL/builds/{task_id}" -H "X-API-Key: $RDEV_API_KEY" | jq '.result'
# Check rdev-api logs for worker errors
./scripts/logs.sh -e
Pipeline not triggering
# Check if commit was pushed
curl -s "https://git.threesix.ai/api/v1/repos/jordan/my-fullstack-app/commits" | jq '.[0]'
# Check Woodpecker
open https://ci.threesix.ai/jordan/my-fullstack-app
Frontend/Backend connection issues
# Check both containers are running
kubectl get pods -n projects -l app=my-fullstack-app
# Check frontend logs
kubectl logs -n projects -l app=my-fullstack-app -c frontend
# Check backend logs
kubectl logs -n projects -l app=my-fullstack-app -c backend
Related
- Landing Page Cookbook - Simpler single-page deployment
- Worker Pool Guide
- Build Orchestration