ab2f4ab942
ci / test-pglite (PGlite, default) (push) Failing after 1m52s
ci / test-postgres (Postgres 16, G-022 RLS) (push) Failing after 1m11s
ci / test-pglite (PGlite, default) (pull_request) Failing after 1m51s
ci / test-postgres (Postgres 16, G-022 RLS) (pull_request) Failing after 1m11s
243 lines
9.2 KiB
YAML
243 lines
9.2 KiB
YAML
# .gitea/workflows/ci.yml — CoreCI Chat CI pipeline (G-011, G-022, R-009, Wave J Task 7).
|
|
#
|
|
# Gitea Actions (GitHub Actions-compatible YAML + secrets + service containers).
|
|
# The repo's forge is Gitea at git.cloudinit.dev; Gitea Actions runs the same
|
|
# workflow syntax as GitHub Actions. Two jobs:
|
|
#
|
|
# 1. test-pglite (default): pnpm install, typecheck, lint, test, conformance,
|
|
# coverage upload. Go tests. Runs on every push/PR. Track B LLM smoke
|
|
# runs when secrets.GITHUB_SMOKE_PAT is available (allow-failure — does
|
|
# NOT block the P0 gate).
|
|
#
|
|
# 2. test-postgres (G-022): Postgres 16 service container, setup-ci-roles.sql
|
|
# (coreci_app NOBYPASSRLS, migrator BYPASSRLS), DB_MODE=pg, pnpm migrate,
|
|
# full M1 + M2 suite against real Postgres (the first real-RLS test).
|
|
# Runs on every push/PR (parallel to test-pglite).
|
|
#
|
|
# Both jobs cache pnpm store + go modules. Coverage uploaded as artifacts.
|
|
# The M2 acceptance gate (spec §6) requires both jobs GREEN.
|
|
|
|
# NOTE (2026-10-26, coreci-chat-po, revised): the trigger shape below now
|
|
# matches the shape this instance actually runs - a bare `push:` and a
|
|
# `pull_request` filtered to `main` (coreci/nova-platform ci.yml fires on
|
|
# both). The earlier note here ("only a default-branch push touching THIS file
|
|
# registers the trigger", sre readback c12346, "F-1") is FALSIFIED: PR #7
|
|
# merged to main at 2026-10-26T22:59:04Z touching this file and the pipeline
|
|
# still produced no run record (coreci-chat#1, M3 kickoff gate).
|
|
#
|
|
# NOTE (2026-10-26, coreci-chat-po): the jobs run on the fleet shared-pool label
|
|
# `ubuntu-latest`. The `node` label is a bare node:24-bookworm image with no fleet
|
|
# toolchain - nova-platform run 51350 went green on ubuntu-latest, run 51345 red on
|
|
# node. Go and the postgres client are installed by the jobs themselves, and the
|
|
# postgres service is reached by its service name (coreci-chat#1, M3 kickoff gate).
|
|
name: ci
|
|
|
|
on:
|
|
push:
|
|
pull_request:
|
|
branches: [main]
|
|
workflow_dispatch: {}
|
|
|
|
env:
|
|
# Pin Node + pnpm versions for reproducibility.
|
|
# Node 22 is the floor: pnpm 11.23.0 (the packageManager pin) needs >= v22.13
|
|
# and dies on Node 20 with ERR_UNKNOWN_BUILTIN_MODULE (node:sqlite).
|
|
NODE_VERSION: "22"
|
|
# Display label for the pnpm step only. The INSTALLED pnpm version is the
|
|
# packageManager pin in package.json - pnpm/action-setup rejects a second
|
|
# pin (workflow version: + package.json packageManager:) and exits 1.
|
|
PNPM_VERSION: "11"
|
|
|
|
jobs:
|
|
# ─── Job 1: test-pglite (default — PGlite in-process) ──────────────────
|
|
test-pglite:
|
|
name: test-pglite (PGlite, default)
|
|
runs-on: ubuntu-latest
|
|
timeout-minutes: 20
|
|
steps:
|
|
- name: Checkout
|
|
uses: actions/checkout@v4
|
|
|
|
- name: Setup Node ${{ env.NODE_VERSION }}
|
|
uses: actions/setup-node@v4
|
|
with:
|
|
node-version: ${{ env.NODE_VERSION }}
|
|
|
|
- name: Setup pnpm ${{ env.PNPM_VERSION }}
|
|
uses: pnpm/action-setup@v4
|
|
with:
|
|
run_install: false
|
|
|
|
- name: Get pnpm store dir
|
|
id: pnpm-cache
|
|
run: echo "STORE=$(pnpm store path --silent)" >> "$GITHUB_OUTPUT"
|
|
|
|
- name: Cache pnpm store
|
|
uses: actions/cache@v4
|
|
with:
|
|
path: ${{ steps.pnpm-cache.outputs.STORE }}
|
|
key: pnpm-${{ runner.os }}-${{ hashFiles('**/pnpm-lock.yaml') }}
|
|
restore-keys: pnpm-${{ runner.os }}-
|
|
|
|
- name: Install dependencies
|
|
run: pnpm install --frozen-lockfile
|
|
|
|
# Consumers resolve @coreci/db and @coreci/secrets through their
|
|
# published dist/*.d.ts, so the packages must be built (pnpm runs
|
|
# them in dependency order) before typecheck and before the tests.
|
|
- name: Build (packages - dist for the type declarations)
|
|
run: pnpm --filter "./packages/*" -r build
|
|
|
|
- name: Typecheck
|
|
run: pnpm typecheck
|
|
|
|
- name: Lint
|
|
run: pnpm lint
|
|
|
|
- name: Build (mcp package — dist for the smoke imports)
|
|
run: pnpm --filter @coreci/mcp build
|
|
|
|
- name: "[G-018,R-008] Import guard (no @coreci/llm-mock in prod source)"
|
|
run: pnpm check:llm-mock-guard
|
|
|
|
- name: Unit + integration tests (PGlite)
|
|
run: pnpm test
|
|
|
|
- name: MCP conformance + LLM smoke (Track A mock-path P0 + Track B allow-failure)
|
|
env:
|
|
# Track B runs only when the PAT secret is present; it is allow-failure.
|
|
GITHUB_SMOKE_PAT: ${{ secrets.GITHUB_SMOKE_PAT }}
|
|
run: pnpm test:conformance
|
|
|
|
- name: Coverage (llm-mock + mcp)
|
|
run: |
|
|
pnpm --filter @coreci/llm-mock test:coverage
|
|
pnpm --filter @coreci/mcp test:coverage || true
|
|
continue-on-error: true
|
|
|
|
- name: Setup Go 1.23
|
|
uses: actions/setup-go@v5
|
|
with:
|
|
go-version: "1.23"
|
|
cache: false
|
|
|
|
- name: Go tests (Relay Agent)
|
|
run: |
|
|
if [ -f apps/relay-agent/go.mod ]; then
|
|
cd apps/relay-agent && go test ./...
|
|
fi
|
|
|
|
- name: Upload coverage artifacts
|
|
uses: actions/upload-artifact@v4
|
|
if: always()
|
|
with:
|
|
name: coverage-pglite
|
|
path: |
|
|
packages/llm-mock/coverage/
|
|
packages/mcp/coverage/
|
|
if-no-files-found: ignore
|
|
retention-days: 7
|
|
|
|
# ─── Job 2: test-postgres (G-022 — real Postgres 16, RLS enforced) ──────
|
|
test-postgres:
|
|
name: test-postgres (Postgres 16, G-022 RLS)
|
|
runs-on: ubuntu-latest
|
|
timeout-minutes: 25
|
|
services:
|
|
# Postgres 16 service container (R-009). The image is the official
|
|
# postgres:16; the CI runner connects to it via `postgres` hostname.
|
|
postgres:
|
|
image: postgres:16
|
|
env:
|
|
POSTGRES_USER: postgres
|
|
POSTGRES_PASSWORD: postgres
|
|
POSTGRES_DB: postgres
|
|
ports:
|
|
- 5432:5432
|
|
options: >-
|
|
--health-cmd "pg_isready -U postgres"
|
|
--health-interval 10s
|
|
--health-timeout 5s
|
|
--health-retries 5
|
|
env:
|
|
# The test harness reads DB_MODE + DATABASE_URL. Connect as the
|
|
# superuser to run setup-ci-roles.sql, then the tests connect as
|
|
# coreci_app (NOBYPASSRLS) so RLS is enforced.
|
|
# DATABASE_URL is exported by the "Resolve the CI database host" step
|
|
# below, so the service host is decided once for every later step.
|
|
DB_MODE: "pg"
|
|
PGPASSWORD: postgres
|
|
steps:
|
|
- name: Checkout
|
|
uses: actions/checkout@v4
|
|
|
|
- name: Setup Node ${{ env.NODE_VERSION }}
|
|
uses: actions/setup-node@v4
|
|
with:
|
|
node-version: ${{ env.NODE_VERSION }}
|
|
|
|
- name: Setup pnpm ${{ env.PNPM_VERSION }}
|
|
uses: pnpm/action-setup@v4
|
|
with:
|
|
run_install: false
|
|
|
|
- name: Cache pnpm store
|
|
uses: actions/cache@v4
|
|
with:
|
|
path: ~/.local/share/pnpm/store
|
|
key: pnpm-${{ runner.os }}-${{ hashFiles('**/pnpm-lock.yaml') }}
|
|
restore-keys: pnpm-${{ runner.os }}-
|
|
|
|
- name: Install dependencies
|
|
run: pnpm install --frozen-lockfile
|
|
|
|
# Consumers resolve @coreci/db and @coreci/secrets through their
|
|
# published dist/*.d.ts, so the packages must be built (pnpm runs
|
|
# them in dependency order) before typecheck and before the tests.
|
|
- name: Build (packages - dist for the type declarations)
|
|
run: pnpm --filter "./packages/*" -r build
|
|
|
|
- name: Install the postgres client (the runner image carries no psql)
|
|
run: |
|
|
apt-get update -qq && apt-get install -y -qq postgresql-client
|
|
|
|
- name: Resolve the CI database host
|
|
run: |
|
|
HOST=$(getent hosts postgres >/dev/null 2>&1 && echo postgres || echo localhost)
|
|
echo "CI_DB_HOST=$HOST" >> "$GITHUB_ENV"
|
|
echo "DATABASE_URL=postgres://coreci_app:coreci_app_ci@$HOST:5432/coreci_ci" >> "$GITHUB_ENV"
|
|
echo "CI_MIGRATOR_DATABASE_URL=postgres://migrator:migrator_ci@$HOST:5432/coreci_ci" >> "$GITHUB_ENV"
|
|
|
|
- name: "[R-009] Setup CI roles (coreci_app NOBYPASSRLS, migrator BYPASSRLS)"
|
|
run: |
|
|
psql -h "$CI_DB_HOST" -U postgres -d postgres -f packages/db/scripts/setup-ci-roles.sql
|
|
|
|
- name: "[G-022] Run migrations as migrator (BYPASSRLS)"
|
|
run: |
|
|
DATABASE_URL="$CI_MIGRATOR_DATABASE_URL" pnpm --filter @coreci/db migrate
|
|
|
|
- name: "[G-022] Build mcp (dist for smoke imports)"
|
|
run: pnpm --filter @coreci/mcp build
|
|
|
|
- name: "[G-022] Full M1 + M2 test suite against real Postgres 16"
|
|
# The tests read DB_MODE=pg + DATABASE_URL (coreci_app role, RLS
|
|
# enforced). The pen test's WITH CHECK assertion (R-009) is REAL here
|
|
# — a cross-tenant INSERT is rejected by the RLS policy.
|
|
run: pnpm test
|
|
|
|
- name: "[G-022] MCP conformance + LLM smoke (Track A only — no PAT in pg job)"
|
|
run: pnpm test:conformance
|
|
|
|
- name: "[G-022] DB pen test (real RLS WITH CHECK enforcement, R-009)"
|
|
run: pnpm --filter @coreci/db test:pen
|
|
|
|
- name: Upload coverage artifacts
|
|
uses: actions/upload-artifact@v4
|
|
if: always()
|
|
with:
|
|
name: coverage-postgres
|
|
path: |
|
|
packages/*/coverage/
|
|
apps/*/coverage/
|
|
if-no-files-found: ignore
|
|
retention-days: 7 |