cd78f72f33
Complete rename of all technical identifiers across the codebase: Package names (11 packages): - @planarchy/* → @capakraken/* in all package.json, tsconfig, imports Import statements: 277 files, 548 occurrences replaced Database & Docker: - PostgreSQL user/db: planarchy → capakraken - Docker volumes: planarchy_pgdata → capakraken_pgdata - Connection strings updated in docker-compose, .env, CI CI/CD: - GitHub Actions workflow: all filter commands updated - Test database credentials updated Infrastructure: - Redis channel: planarchy:sse → capakraken:sse - Logger service name: planarchy-api → capakraken-api - Anonymization seed updated - Start/stop/restart scripts updated Test data: - Seed emails: @planarchy.dev → @capakraken.dev - E2E test credentials: all 11 spec files updated - Email defaults: @planarchy.app → @capakraken.app - localStorage keys: planarchy_* → capakraken_* Documentation: 30+ .md files updated Verification: - pnpm install: workspace resolution works - TypeScript: only pre-existing TS2589 (no new errors) - Engine: 310/310 tests pass - Staffing: 37/37 tests pass Co-Authored-By: claude-flow <ruv@ruv.net>
317 lines
7.5 KiB
Markdown
317 lines
7.5 KiB
Markdown
# Planarchy CI/CD Manual
|
|
|
|
## Overview
|
|
|
|
Planarchy uses GitHub Actions for continuous integration and Docker for deployment. This document covers the full pipeline from code push to production.
|
|
|
|
---
|
|
|
|
## 1. CI Pipeline (Automatic on every PR)
|
|
|
|
### What triggers it
|
|
|
|
| Event | Trigger |
|
|
|-------|---------|
|
|
| Pull request to `main` | All CI jobs run |
|
|
| Push to `main` | All CI jobs run |
|
|
|
|
### Jobs and their purpose
|
|
|
|
```
|
|
PR opened / pushed
|
|
│
|
|
├──→ typecheck (tsc --noEmit, ~40s)
|
|
├──→ lint (ESLint via Turborepo, ~20s)
|
|
├──→ test (Vitest unit tests, ~60s, needs PostgreSQL + Redis)
|
|
│
|
|
└──→ build (next build, ~90s, runs after typecheck)
|
|
│
|
|
└──→ e2e (Playwright, ~3-5min, runs after build)
|
|
```
|
|
|
|
**typecheck, lint, and test run in parallel** for speed. Build waits for typecheck. E2E waits for build.
|
|
|
|
### What each job checks
|
|
|
|
| Job | Command | What it catches |
|
|
|-----|---------|----------------|
|
|
| **typecheck** | `pnpm --filter @capakraken/web exec tsc --noEmit` | Type errors across the full web app |
|
|
| **lint** | `pnpm lint` | Code style violations, unused imports, etc. |
|
|
| **test** | `pnpm test:unit` | Unit test failures in engine, staffing, API, shared |
|
|
| **build** | `pnpm --filter @capakraken/web exec next build` | SSR errors, dynamic import issues, bundle problems |
|
|
| **e2e** | `pnpm test:e2e` | End-to-end user flow regressions |
|
|
|
|
### Required status checks
|
|
|
|
Before merging a PR, **all 5 jobs must pass**. Configure this in GitHub Settings > Branches > Branch protection rules > Require status checks.
|
|
|
|
### Caching
|
|
|
|
The pipeline caches these artifacts to speed up subsequent runs:
|
|
|
|
| Cache | Key | Saves |
|
|
|-------|-----|-------|
|
|
| pnpm store | `pnpm-lock.yaml` hash | ~30s install time |
|
|
| Turborepo | `.turbo` directory | ~60s on unchanged packages |
|
|
| Playwright browsers | Playwright version | ~45s browser download |
|
|
|
|
---
|
|
|
|
## 2. Local Development Quality Gates
|
|
|
|
Run these before pushing to catch issues early:
|
|
|
|
```bash
|
|
# Quick check (< 2 min)
|
|
pnpm --filter @capakraken/web exec tsc --noEmit && pnpm lint
|
|
|
|
# Full check (< 3 min)
|
|
pnpm test:unit
|
|
|
|
# Full check including build (< 5 min)
|
|
pnpm --filter @capakraken/web exec next build
|
|
```
|
|
|
|
### Pre-commit hook (optional)
|
|
|
|
You can add a Git pre-commit hook to run the quick check automatically:
|
|
|
|
```bash
|
|
# .husky/pre-commit
|
|
pnpm --filter @capakraken/web exec tsc --noEmit
|
|
pnpm lint
|
|
```
|
|
|
|
---
|
|
|
|
## 3. Health Check Endpoints
|
|
|
|
Two endpoints are available for monitoring:
|
|
|
|
### GET `/api/health` — Liveness Probe
|
|
|
|
Returns 200 if the Node.js process is running. No external dependencies checked.
|
|
|
|
```json
|
|
{ "status": "ok", "timestamp": "2026-03-19T10:00:00.000Z" }
|
|
```
|
|
|
|
**Use for:** Kubernetes/Docker liveness probe, uptime monitoring.
|
|
|
|
### GET `/api/ready` — Readiness Probe
|
|
|
|
Checks PostgreSQL and Redis connectivity. Returns 200 if all services are reachable, 503 if not.
|
|
|
|
```json
|
|
// Healthy
|
|
{ "status": "ready", "postgres": "ok", "redis": "ok" }
|
|
|
|
// Unhealthy
|
|
{ "status": "not_ready", "postgres": "ok", "redis": "error" }
|
|
```
|
|
|
|
**Use for:** Kubernetes/Docker readiness probe, load balancer health checks, nginx upstream checks.
|
|
|
|
---
|
|
|
|
## 4. Production Docker Build
|
|
|
|
### Building the production image
|
|
|
|
```bash
|
|
# Build the image
|
|
docker build -f Dockerfile.prod -t planarchy:latest .
|
|
|
|
# Test it locally
|
|
docker compose -f docker-compose.prod.yml up -d
|
|
```
|
|
|
|
### Image details
|
|
|
|
| Property | Value |
|
|
|----------|-------|
|
|
| Base | `node:20-bookworm-slim` |
|
|
| Size | ~150-200 MB (vs ~1.5 GB dev image) |
|
|
| Output | Next.js standalone mode |
|
|
| Healthcheck | `curl -f http://localhost:3000/api/health` |
|
|
| Port | 3000 (internal), mapped to 3100 externally |
|
|
|
|
### Environment variables
|
|
|
|
The production image requires these environment variables:
|
|
|
|
```env
|
|
# Required
|
|
DATABASE_URL=postgresql://user:pass@host:5432/planarchy
|
|
REDIS_URL=redis://host:6379
|
|
NEXTAUTH_URL=https://planarchy.your-domain.com
|
|
NEXTAUTH_SECRET=<random-32-char-string>
|
|
|
|
# Optional
|
|
SENTRY_DSN=https://xxx@sentry.io/xxx
|
|
SMTP_HOST=smtp.example.com
|
|
SMTP_PORT=587
|
|
SMTP_USER=notifications@example.com
|
|
SMTP_PASSWORD=<password>
|
|
SMTP_FROM=Planarchy <notifications@example.com>
|
|
```
|
|
|
|
Generate a secure `NEXTAUTH_SECRET`:
|
|
|
|
```bash
|
|
openssl rand -base64 32
|
|
```
|
|
|
|
---
|
|
|
|
## 5. Deployment
|
|
|
|
### docker-compose (simplest)
|
|
|
|
```bash
|
|
# On your server
|
|
git pull
|
|
docker compose -f docker-compose.prod.yml up -d --build
|
|
|
|
# Run database migrations
|
|
docker compose -f docker-compose.prod.yml exec app \
|
|
npx prisma db push --skip-generate
|
|
|
|
# Seed initial data (first deployment only)
|
|
docker compose -f docker-compose.prod.yml exec app \
|
|
npx prisma db seed
|
|
```
|
|
|
|
### Manual deployment (current setup)
|
|
|
|
Since `capakraken.hartmut-noerenberg.com` runs behind nginx:
|
|
|
|
```bash
|
|
# On the server
|
|
cd /home/hartmut/Documents/Copilot/planarchy
|
|
git pull origin main
|
|
pnpm install
|
|
pnpm --filter @capakraken/db exec prisma generate
|
|
pnpm --filter @capakraken/web exec next build
|
|
rm -rf apps/web/.next/cache # clear stale cache
|
|
|
|
# Restart the app (systemd, pm2, or manual)
|
|
fuser -k 3100/tcp 2>/dev/null
|
|
PORT=3100 pnpm --filter @capakraken/web start &
|
|
```
|
|
|
|
### nginx configuration
|
|
|
|
The existing nginx reverse proxy should forward to port 3100:
|
|
|
|
```nginx
|
|
server {
|
|
server_name capakraken.hartmut-noerenberg.com;
|
|
|
|
location / {
|
|
proxy_pass http://127.0.0.1:3100;
|
|
proxy_http_version 1.1;
|
|
proxy_set_header Upgrade $http_upgrade;
|
|
proxy_set_header Connection "upgrade";
|
|
proxy_set_header Host $host;
|
|
proxy_set_header X-Real-IP $remote_addr;
|
|
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
|
|
proxy_set_header X-Forwarded-Proto $scheme;
|
|
|
|
# SSE support (keep connection open)
|
|
proxy_read_timeout 86400s;
|
|
proxy_buffering off;
|
|
}
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
## 6. Monitoring Setup
|
|
|
|
### Sentry (error tracking)
|
|
|
|
After creating a Sentry project, add the DSN to `.env.production`:
|
|
|
|
```env
|
|
SENTRY_DSN=https://xxx@sentry.io/xxx
|
|
```
|
|
|
|
Errors are automatically captured by the Sentry integration in Next.js.
|
|
|
|
### Uptime monitoring
|
|
|
|
Point an external monitor (UptimeRobot, Better Stack, etc.) at:
|
|
|
|
```
|
|
https://capakraken.hartmut-noerenberg.com/api/health
|
|
```
|
|
|
|
Alert if status code != 200 for more than 2 consecutive checks.
|
|
|
|
---
|
|
|
|
## 7. Troubleshooting
|
|
|
|
### CI job fails: "tsc --noEmit"
|
|
|
|
TypeScript error in the web app. Run locally:
|
|
```bash
|
|
pnpm --filter @capakraken/web exec tsc --noEmit
|
|
```
|
|
|
|
### CI job fails: "test:unit"
|
|
|
|
Unit test failure. Run locally:
|
|
```bash
|
|
pnpm test:unit
|
|
```
|
|
|
|
### CI job fails: "next build"
|
|
|
|
Build error (often `ssr: false` in Server Components, missing exports). Run locally:
|
|
```bash
|
|
pnpm --filter @capakraken/web exec next build
|
|
```
|
|
|
|
### CI job fails: "e2e"
|
|
|
|
Playwright test failure. Check the HTML report artifact in the GitHub Actions run.
|
|
|
|
### Production: 502 Bad Gateway
|
|
|
|
The Next.js process isn't running. Check:
|
|
```bash
|
|
ss -tlnp | grep 3100 # Is anything listening?
|
|
tail -50 /tmp/planarchy-dev.log # Check app logs
|
|
```
|
|
|
|
Restart:
|
|
```bash
|
|
fuser -k 3100/tcp 2>/dev/null
|
|
pnpm dev & # or pnpm start for production mode
|
|
```
|
|
|
|
### Production: 500 Internal Server Error
|
|
|
|
Usually a stale Prisma client after schema changes:
|
|
```bash
|
|
pnpm --filter @capakraken/db exec prisma generate
|
|
rm -rf apps/web/.next
|
|
pnpm --filter @capakraken/web exec next build
|
|
# Restart the server
|
|
```
|
|
|
|
### Database connection issues
|
|
|
|
Check the `/api/ready` endpoint:
|
|
```bash
|
|
curl -s https://capakraken.hartmut-noerenberg.com/api/ready | jq .
|
|
```
|
|
|
|
If `postgres: "error"`, verify:
|
|
```bash
|
|
docker ps | grep postgres # Is container running?
|
|
psql -h localhost -p 5433 -U planarchy -d planarchy # Can you connect?
|
|
```
|