Files
stack/.woodpecker
Jason Woltje a534f70abd fix(#364): add prisma-generate dependency to lint step in CI
The lint step in .woodpecker/api.yml depended only on install, but
ESLint needs Prisma-generated client types to resolve imports. Without
prisma-generate running first, all Prisma type references produce
false-positive errors (3,919 total). Changing the dependency from
install to prisma-generate fixes the issue since prisma-generate
already depends on install.

Fixes #364

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-12 12:40:20 -06:00
..

Woodpecker CI Configuration for Mosaic Stack

Pipeline Architecture

Split per-package pipelines with path filtering. Only affected packages rebuild on push.

.woodpecker/
├── api.yml           # @mosaic/api (NestJS)
├── web.yml           # @mosaic/web (Next.js)
├── orchestrator.yml  # @mosaic/orchestrator (NestJS)
├── coordinator.yml   # mosaic-coordinator (Python/FastAPI)
├── infra.yml         # postgres + openbao Docker images
├── codex-review.yml  # AI code/security review (PRs only)
├── README.md
└── schemas/
    ├── code-review-schema.json
    └── security-review-schema.json

Path Filtering

Pipeline Triggers On
api.yml apps/api/**, packages/**, root configs
web.yml apps/web/**, packages/**, root configs
orchestrator.yml apps/orchestrator/**, packages/**, root configs
coordinator.yml apps/coordinator/**
infra.yml docker/**
codex-review.yml All PRs (no path filter)

Root configs = pnpm-lock.yaml, pnpm-workspace.yaml, turbo.json, package.json

Security Chain

Every pipeline follows the full security chain required by the CI/CD guide:

source scanning (lint + pnpm audit / bandit + pip-audit)
  -> docker build (Kaniko)
  -> container scanning (Trivy: HIGH,CRITICAL)
  -> package linking (Gitea registry)

Docker builds gate on ALL quality + security steps passing.

Pipeline Dependency Graphs

Node.js Apps (api, web, orchestrator)

install -> [security-audit, lint, prisma-generate*]
prisma-generate* -> [typecheck, prisma-migrate*]
prisma-migrate* -> test
[all quality gates] -> build -> docker-build -> trivy -> link

*prisma steps: api.yml only

Coordinator (Python)

install -> [ruff-check, mypy, security-bandit, security-pip-audit, test]
[all quality gates] -> docker-build -> trivy -> link

Infrastructure

[docker-build-postgres, docker-build-openbao]
-> [trivy-postgres, trivy-openbao]
-> link

Docker Images

Image Registry Path Context
stack-api git.mosaicstack.dev/mosaic/stack-api . (monorepo root)
stack-web git.mosaicstack.dev/mosaic/stack-web . (monorepo root)
stack-orchestrator git.mosaicstack.dev/mosaic/stack-orchestrator . (monorepo root)
stack-coordinator git.mosaicstack.dev/mosaic/stack-coordinator apps/coordinator
stack-postgres git.mosaicstack.dev/mosaic/stack-postgres docker/postgres
stack-openbao git.mosaicstack.dev/mosaic/stack-openbao docker/openbao

Image Tagging

Condition Tag Purpose
Always ${CI_COMMIT_SHA:0:8} Immutable commit reference
main branch latest Current production release
develop branch dev Current development build
Git tag tag value (e.g., v1.0.0) Semantic version release

Required Secrets

Configure in Woodpecker UI (Settings > Secrets):

Secret Scope Purpose
gitea_username push, manual, tag Gitea registry auth
gitea_token push, manual, tag Gitea registry auth (package:write scope)
codex_api_key pull_request Codex AI reviews

Codex AI Review Pipeline

The codex-review.yml pipeline runs independently on all PRs:

  • Code review: Correctness, code quality, testing, performance
  • Security review: OWASP Top 10, hardcoded secrets, injection flaws

Fails on blockers or critical/high severity security findings.

Local Testing

~/.claude/scripts/codex/codex-code-review.sh --uncommitted
~/.claude/scripts/codex/codex-security-review.sh --uncommitted

Troubleshooting

"unauthorized: authentication required"

  • Verify gitea_username and gitea_token secrets in Woodpecker
  • Verify token has package:write scope

Trivy scan fails with HIGH/CRITICAL

  • Check if the vulnerability is in the base image (not our code)
  • Add to .trivyignore if it's a known, accepted risk
  • Use --ignore-unfixed (already set) to skip unfixable CVEs

Package linking returns 404

  • Normal for recently pushed packages — retry logic handles this
  • If persistent: verify package name matches exactly (case-sensitive)

Pipeline runs Docker builds on pull requests

  • Docker build steps have when: branch: [main, develop] guards
  • PRs only run quality gates, not Docker builds