Review: Add Woodpecker CI pipeline and k8s manifests (linkedin-scheduler-remote)

review-65-2026-03-27-v2 Review

review needs-refinement

Verdict: NEEDS_REFINEMENT

Template Completeness

  • [x] Repo
  • [x] User Story
  • [x] Acceptance Criteria
  • [x] Checklist
  • [x] Related
  • [ ] Type -- MISSING (board labels say type:feature but issue body has no ### Type header)
  • [ ] Lineage -- MISSING (has deprecated ### Plan header instead)
  • [ ] Context -- MISSING (has ad-hoc ### [SCOPE] and ### Additional Information, not formal Context)
  • [ ] File Targets -- MISSING (files listed in scope narrative but not in template format with modify/do-not-touch)
  • [ ] Test Expectations -- MISSING
  • [ ] Constraints -- MISSING
6 of 11 required feature template sections missing.

Traceability

  • [x] story:superuser-onboard -- superuser onboarding pipeline
  • [x] arch:ci-pipeline -- CI pipeline architecture component
  • [x] Forgejo issue -- forgejo_admin/linkedin-scheduler-remote#3, open
All three legs present. Traceability is complete.

File Targets

  • [x] k8s/deployment.yaml -- verified: contains inline Service (lines ~76-90) and PVC (lines ~91-103) after --- separators. Split to separate files is valid.
  • [x] k8s/kustomization.yaml -- verified: currently lists only deployment.yaml and servicemonitor.yaml. Needs service.yaml and pvc.yaml added after split.
  • [x] server.py -- verified: NO /metrics endpoint exists. grep returned empty. ServiceMonitor references /metrics but it will 404.
  • [x] pyproject.toml -- verified: ruff config present ([tool.ruff] with target-version py312, line-length 120, lint select E/F/I/W). Dev deps include ruff>=0.15.2. No action needed.
  • [x] .woodpecker.yml -- verified: CI pipeline exists with test (ruff check/format) and build-and-push (kaniko to Harbor) steps. No action needed.
  • [x] k8s/servicemonitor.yaml -- verified: exists, references /metrics on port http at 30s interval. No action needed.
All claimed files verified. The delta is accurate: split Service/PVC, update kustomization.yaml, add /metrics endpoint.

Repo Placement

OK. Issue filed on linkedin-scheduler-remote, all changes are in that repo. Single-repo scope.

Dependencies

No blocking dependencies. Board item #63 (gcal-mcp-remote CI pipeline) is a sibling ticket with same labels, also in todo column -- not a dependency. No items in in_progress block this work.
Note: PR #4 exists on the repo (open, stale) from a prior attempt. Agent should be told to close it or build on it.

Acceptance Criteria

Two AC provided. Both are testable in principle:
  • AC1: Push to main triggers Woodpecker ruff + build -- testable via Woodpecker MCP
  • AC2: ArgoCD syncs k8s/ directory deploys correctly -- testable via kubectl
MISSING: No AC for /metrics endpoint. The ServiceMonitor exists and expects /metrics, but there is no criterion like "When Prometheus scrapes /metrics, then valid metrics are returned." This is the only substantive code change and it has no AC.

Blast Radius

Low. The k8s file split is a convention alignment (no behavioral change). The /metrics endpoint is additive. ServiceMonitor already exists and is currently getting 404s from the missing endpoint -- adding /metrics fixes an existing silent failure. No downstream consumers affected.

Decomposition

4-5 file targets in 1 repo, 2 AC (should be 3). Estimated agent time: ~3-4 minutes. The split is mechanical, /metrics is a small feature. No decomposition needed.

Recommendation

  • [BODY] Add missing template sections: ### Type (Feature), ### Lineage (standalone or link to prior plan context), ### Context, ### File Targets (formal modify/do-not-touch format), ### Test Expectations, ### Constraints
  • [BODY] Replace deprecated ### Plan header with ### Lineage
  • [BODY] Add formal File Targets section listing: modify k8s/deployment.yaml (remove inline Service+PVC), create k8s/service.yaml, create k8s/pvc.yaml, modify k8s/kustomization.yaml (add new files), modify server.py (add /metrics). Do-not-touch: .woodpecker.yml, Dockerfile, k8s/servicemonitor.yaml, pyproject.toml
  • [BODY] Add AC for /metrics: "When Prometheus scrapes /metrics on port 8000, then it receives valid metrics response"
  • [BODY] Add Test Expectations: ruff check passes, /metrics returns 200, kustomize build k8s/ succeeds
  • [BODY] Add note about stale PR #4 -- close or reference it so agent knows the state
  • [SCOPE] Consider renaming issue title to reflect actual remaining delta (e.g., "Align linkedin-scheduler-remote k8s manifests + add /metrics endpoint") -- the current title implies greenfield CI/k8s work that is 80% done