Lifts the M7.1 tenant infrastructure (TenantStatus/OrgRole/TenantContext, db::tenant_filter, JWT middleware, TenantCtx extractor) from compliance-agent into compliance-core under a new axum cargo feature, so every future product can consume one source of truth.
Adds compliance-smoke: a tiny Axum binary with three endpoints (public health, protected GET echo, protected POST echo) that mounts compliance-core's middleware end-to-end against a live Keycloak.
Adds scripts/smoke.sh: bash runner that hits the smoke service with tokens for the five certifai-realm test users (admin/user → active, trial, frozen, archived) and asserts the exact status code per (user × method × endpoint).
PR #82 wired the original M7.1 middleware into compliance-agent inline. We parked it so this PR can land first as the canonical home — when #82 is rebased on top, it shrinks to "delete compliance-agent's local copy + import from compliance-core".
Smoke verdict (run against local certifai KC, 15/15 PASS)
Switch certifai compose KC from dev-mem → dev-file so the realm survives idle periods.
## Summary
- Lifts the M7.1 tenant infrastructure (TenantStatus/OrgRole/TenantContext, db::tenant_filter, JWT middleware, TenantCtx extractor) from compliance-agent into compliance-core under a new `axum` cargo feature, so every future product can consume one source of truth.
- Adds `compliance-smoke`: a tiny Axum binary with three endpoints (public health, protected GET echo, protected POST echo) that mounts compliance-core's middleware end-to-end against a live Keycloak.
- Adds `scripts/smoke.sh`: bash runner that hits the smoke service with tokens for the five certifai-realm test users (admin/user → active, trial, frozen, archived) and asserts the exact status code per (user × method × endpoint).
## Why independent of #82
PR #82 wired the original M7.1 middleware into compliance-agent inline. We parked it so this PR can land first as the canonical home — when #82 is rebased on top, it shrinks to "delete compliance-agent's local copy + import from compliance-core".
## Smoke verdict (run against local certifai KC, 15/15 PASS)
- Public `/api/v1/health` → 200 (no auth)
- Anon / bogus token on protected → 401
- admin/user (active) → 200 read + 200 write
- trial → 200 read + 200 write
- frozen → 200 read + **402** write (read-after-cancel gate)
- archived → **410** read + **410** write (retention window closed)
## How to run locally
```
docker compose up -d keycloak # in certifai repo
cargo run -p compliance-smoke & # exports KEYCLOAK_URL/REALM
KEYCLOAK_URL=http://localhost:8080 \
KEYCLOAK_REALM=certifai \
cargo run -p compliance-smoke
./scripts/smoke.sh # asserts all 15
```
## Test plan
- [x] cargo fmt --all
- [x] cargo clippy --workspace --exclude compliance-dashboard -- -D warnings
- [x] cargo test -p compliance-core --features axum (43 passing)
- [x] cargo build --workspace --exclude compliance-dashboard
- [x] scripts/smoke.sh against live KC — 15/15 assertions PASS
## Follow-ups (not in scope here)
- Rebase PR #82 on top of this — drop the inline middleware and import from compliance-core.
- JWKS refresh-on-failure (today the agent caches forever; KC key rotation = silent 401 storm).
- Switch certifai compose KC from `dev-mem` → `dev-file` so the realm survives idle periods.
Moves the tenant-aware HTTP infrastructure into compliance-core so every
future product (compliance-agent, compliance-dast, compliance-mcp, the
upcoming smoke harness) shares one source of truth instead of each crate
re-implementing claims extraction and the status gate.
* tenant.rs — TenantStatus / OrgRole / TenantContext (unconditional)
* db.rs — tenant_filter + tenant_filter_merge for query scoping
* auth.rs — require_jwt_auth + require_tenant_status + JwksState
* tenant_ctx.rs — Axum TenantCtx extractor
* `axum` cargo feature gates the HTTP-dependent modules so wasm
consumers (the dashboard frontend) don't pull axum/jsonwebtoken/reqwest
40 unit tests across the moved modules — all green.
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
A minimal Axum binary that mounts compliance-core's M7.1 middleware on
three endpoints (public health, protected GET echo, protected POST echo)
so we can prove the tenant-gating contract end-to-end against a live KC
before any auth-path PR merges.
scripts/smoke.sh drives the binary against the five test users defined
in the certifai realm (admin/user → active, trial/frozen/archived) and
asserts the exact response code per (user × method × endpoint). Run it
once before touching auth, tenant_status, or org_roles code.
Validated locally — 15/15 assertions pass:
* anon/bogus → 401 on protected, 200 on /health
* active/trial → 200 on read + write
* frozen → 200 read, 402 write (read-after-cancel gate)
* archived → 410 read + 410 write (retention window closed)
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
sharang
merged commit 116293519d into main2026-06-04 14:38:36 +00:00
Blocking a user prevents them from interacting with repositories, such as opening or commenting on pull requests or issues. Learn more about blocking a user.
Summary
axumcargo feature, so every future product can consume one source of truth.compliance-smoke: a tiny Axum binary with three endpoints (public health, protected GET echo, protected POST echo) that mounts compliance-core's middleware end-to-end against a live Keycloak.scripts/smoke.sh: bash runner that hits the smoke service with tokens for the five certifai-realm test users (admin/user → active, trial, frozen, archived) and asserts the exact status code per (user × method × endpoint).Why independent of #82
PR #82 wired the original M7.1 middleware into compliance-agent inline. We parked it so this PR can land first as the canonical home — when #82 is rebased on top, it shrinks to "delete compliance-agent's local copy + import from compliance-core".
Smoke verdict (run against local certifai KC, 15/15 PASS)
/api/v1/health→ 200 (no auth)How to run locally
Test plan
Follow-ups (not in scope here)
dev-mem→dev-fileso the realm survives idle periods.