-
Notifications
You must be signed in to change notification settings - Fork 0
feat(v30-T1): C4 fleet inventory, contract tests CI, CycloneDX SBOM gen, lock hash check, SSOT drift cron #121
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,66 @@ | ||
| { | ||
| "$schema": "https://raw.githubusercontent.com/kooshapari/phenotype-registry/main/schemas/c4-fleet.schema.json", | ||
| "version": "1.0", | ||
| "generated": "2026-06-27", | ||
| "pillar_target": 3.55, | ||
| "systems": { | ||
| "omniroute": { | ||
| "name": "OmniRoute", | ||
| "description": "Unified AI proxy/router — route any LLM through one endpoint. 232 providers, 15 routing strategies, 87 MCP tools, 42 i18n locales.", | ||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. [SUGGESTION]: Stale provider count in inventory metadata The description states "232 providers" but the repository's own Reply with |
||
| "type": "system", | ||
| "repo": "KooshaPari/OmniRoute", | ||
| "tags": ["ai-proxy", "router", "llm-gateway"], | ||
| "containers": [ | ||
| { | ||
| "name": "Next.js App Router", | ||
| "type": "container", | ||
| "technology": "Next.js 16 / TypeScript 6 / Tailwind CSS v4", | ||
| "description": "API routes (v1 chat, embeddings, images, audio, video, search, rerank), dashboard UI, SSE streaming, i18n (42 locales)", | ||
| "responsibilities": ["HTTP API surface", "Dashboard rendering", "Authentication", "CORS enforcement"] | ||
| }, | ||
| { | ||
| "name": "SQLite Database", | ||
| "type": "container", | ||
| "technology": "better-sqlite3 / WAL mode", | ||
| "description": "Persistence layer with 83 domain modules, 97 schema migrations, 17 base tables. Encryption at rest for sensitive fields.", | ||
| "responsibilities": ["Provider/model catalog storage", "Usage/billing tracking", "Combo routing config", "API key management", "MCP/A2A audit logs"] | ||
| }, | ||
| { | ||
| "name": "open-sse Engine", | ||
| "type": "container", | ||
| "technology": "TypeScript / Node.js >=22", | ||
| "description": "Core streaming engine: handler pipeline, provider executors (20+), format translators, combo routing (15 strategies), prompt compression pipeline", | ||
| "responsibilities": ["Request translation (OpenAI↔Anthropic↔Gemini)", "Provider executor dispatch", "Combo resolution (priority/weighted/auto)", "Rate limiting & circuit breakers", "Prompt compression (lite/caveman/RTK/stacked)"] | ||
| }, | ||
| { | ||
| "name": "MCP Server", | ||
| "type": "container", | ||
| "technology": "TypeScript / Zod", | ||
| "description": "87 MCP tools across 30 auth scopes. 3 transports (stdio/SSE/Streamable HTTP). Tool categories: core (20), cache, compression, 1proxy, memory, skills, gamification, plugins, Notion, Obsidian.", | ||
| "responsibilities": ["Tool registration & dispatch", "Scope-based authorization", "Invocation audit logging"] | ||
| }, | ||
| { | ||
| "name": "A2A Server", | ||
| "type": "container", | ||
| "technology": "TypeScript / JSON-RPC 2.0", | ||
| "description": "Agent-to-Agent protocol server with SSE streaming, Task Manager (TTL cleanup), 8 skills (cost analysis, quota, routing, discovery, health, capabilities, dispatch).", | ||
| "responsibilities": ["Agent skill execution", "Task lifecycle management", "Agent Card discovery"] | ||
| }, | ||
| { | ||
| "name": "Electron Desktop", | ||
| "type": "container", | ||
| "technology": "Electron", | ||
| "description": "Cross-platform desktop app (Windows, macOS, Linux) wrapping the Next.js UI and MCP server.", | ||
| "responsibilities": ["Local-first desktop experience", "Bundled MCP stdio transport"] | ||
| } | ||
| ], | ||
| "relationships": [ | ||
| { "source": "Next.js App Router", "target": "open-sse Engine", "description": "Proxies API requests to handler pipeline" }, | ||
| { "source": "open-sse Engine", "target": "SQLite Database", "description": "Reads/writes provider config, usage, audit" }, | ||
| { "source": "open-sse Engine", "target": "Upstream LLM Providers", "description": "Forwards translated requests via executors" }, | ||
| { "source": "MCP Server", "target": "SQLite Database", "description": "Audits all tool invocations" }, | ||
| { "source": "A2A Server", "target": "SQLite Database", "description": "Reads quotas, pricing, health for skill results" } | ||
| ] | ||
| } | ||
| } | ||
| } | ||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,42 @@ | ||
| name: Lock Hash Check | ||
|
|
||
| on: | ||
| schedule: | ||
| - cron: "0 4 * * 1" # Every Monday at 04:00 UTC | ||
| workflow_dispatch: | ||
|
|
||
| permissions: | ||
| contents: read | ||
|
|
||
| concurrency: | ||
| group: lock-hash-check | ||
| cancel-in-progress: false | ||
|
|
||
| jobs: | ||
| lock-hash: | ||
| name: Verify Lock File Determinism | ||
| runs-on: ubuntu-24.04 | ||
| timeout-minutes: 10 | ||
| steps: | ||
| - uses: actions/checkout@df4cb1c069e1874edd31b4311f1884172cec0e10 | ||
| with: | ||
| persist-credentials: false | ||
| - uses: actions/setup-node@48b55a011bda9f5d6aeb4c2d9c7362e8dae4041e | ||
| with: | ||
| node-version: "24" | ||
| cache: npm | ||
| - name: Compute hash of package-lock.json | ||
| run: | | ||
| LOCK_HASH=$(sha256sum package-lock.json | cut -d' ' -f1) | ||
| echo "lock_hash=${LOCK_HASH}" >> "$GITHUB_STEP_SUMMARY" | ||
| echo "package-lock.json SHA256: ${LOCK_HASH}" | ||
| - name: Verify deterministic install | ||
| run: | | ||
| BEFORE=$(sha256sum package-lock.json | cut -d' ' -f1) | ||
| npm ci --dry-run 2>&1 | head -5 || true | ||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. [WARNING]: Without a root Reply with |
||
| AFTER=$(sha256sum package-lock.json | cut -d' ' -f1) | ||
| if [ "$BEFORE" != "$AFTER" ]; then | ||
| echo "::error::package-lock.json changed during npm ci --dry-run — lock file is not deterministic." | ||
| exit 1 | ||
| fi | ||
| echo "✅ package-lock.json is deterministic." | ||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,44 @@ | ||
| name: Contract Tests | ||
|
|
||
| on: | ||
| pull_request: | ||
| branches: [main] | ||
| paths: | ||
| - "src/**" | ||
| - "open-sse/**" | ||
| - "tests/contract/**" | ||
| push: | ||
| branches: [main] | ||
| workflow_dispatch: | ||
|
|
||
| permissions: | ||
| contents: read | ||
|
|
||
| concurrency: | ||
| group: ${{ github.workflow }}-${{ github.ref }} | ||
| cancel-in-progress: true | ||
|
|
||
| env: | ||
| NODE_VERSION: "24" | ||
|
|
||
| jobs: | ||
| contract-tests: | ||
| name: Contract Tests | ||
| runs-on: ubuntu-24.04 | ||
| timeout-minutes: 10 | ||
| steps: | ||
| - uses: actions/checkout@df4cb1c069e1874edd31b4311f1884172cec0e10 | ||
| with: | ||
| fetch-depth: 0 | ||
| - uses: actions/setup-node@48b55a011bda9f5d6aeb4c2d9c7362e8dae4041e | ||
| with: | ||
| node-version: ${{ env.NODE_VERSION }} | ||
| cache: npm | ||
| - run: npm ci | ||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
In the inspected tree there is no root Useful? React with 👍 / 👎. |
||
| - name: Run contract tests | ||
| run: | | ||
| if [ -d tests/contract ] && ls tests/contract/*.test.ts 2>/dev/null; then | ||
| node --import tsx --test --test-concurrency=1 tests/contract/*.test.ts | ||
| else | ||
| echo "No contract tests found — skipping. Add *.test.ts files under tests/contract/ to enable." | ||
| fi | ||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,43 @@ | ||
| name: SBOM Generation (CycloneDX) | ||
|
|
||
| on: | ||
| push: | ||
| branches: [main] | ||
| paths: | ||
| - package.json | ||
| - package-lock.json | ||
| schedule: | ||
| - cron: "0 6 * * 1" # Every Monday at 06:00 UTC | ||
| workflow_dispatch: | ||
|
|
||
| permissions: | ||
| contents: read | ||
|
|
||
| concurrency: | ||
| group: ${{ github.workflow }}-${{ github.ref }} | ||
| cancel-in-progress: true | ||
|
|
||
| env: | ||
| NODE_VERSION: "24" | ||
|
|
||
| jobs: | ||
| sbom-gen: | ||
| name: Generate CycloneDX SBOM | ||
| runs-on: ubuntu-24.04 | ||
| timeout-minutes: 10 | ||
| steps: | ||
| - uses: actions/checkout@df4cb1c069e1874edd31b4311f1884172cec0e10 | ||
| with: | ||
| persist-credentials: false | ||
| - uses: actions/setup-node@48b55a011bda9f5d6aeb4c2d9c7362e8dae4041e | ||
| with: | ||
| node-version: ${{ env.NODE_VERSION }} | ||
| cache: npm | ||
| - run: npm ci | ||
| - name: Generate CycloneDX SBOM | ||
| run: npm sbom --sbom-format cyclonedx > omniroute-sbom.cdx.json | ||
| - uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a | ||
| with: | ||
| name: omniroute-sbom-cyclonedx | ||
| path: omniroute-sbom.cdx.json | ||
| retention-days: 90 |
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,42 @@ | ||
| name: SSOT Drift Scan | ||
|
|
||
| on: | ||
| schedule: | ||
| - cron: "0 2 * * 1" # Every Monday at 02:00 UTC | ||
| workflow_dispatch: | ||
|
|
||
| permissions: | ||
| contents: read | ||
|
|
||
| concurrency: | ||
| group: ssot-drift-scan | ||
| cancel-in-progress: false | ||
|
|
||
| env: | ||
| NODE_VERSION: "24" | ||
|
|
||
| jobs: | ||
| ssot-drift: | ||
| name: SSOT Drift Scan | ||
| runs-on: ubuntu-24.04 | ||
| timeout-minutes: 15 | ||
| steps: | ||
| - uses: actions/checkout@df4cb1c069e1874edd31b4311f1884172cec0e10 | ||
| with: | ||
| fetch-depth: 0 | ||
| persist-credentials: false | ||
| - uses: actions/setup-node@48b55a011bda9f5d6aeb4c2d9c7362e8dae4041e | ||
| with: | ||
| node-version: ${{ env.NODE_VERSION }} | ||
| cache: npm | ||
| - run: npm ci | ||
| - name: Check docs sync (source vs generated) | ||
| run: npm run check:docs-sync 2>&1 || echo "Drift detected — run 'npm run docs:sync' locally." | ||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. [WARNING]:
Reply with |
||
| - name: Check route validation drift | ||
| run: npm run check:route-validation:t06 2>&1 || echo "Route validation drift detected." | ||
|
Comment on lines
+33
to
+36
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
For scheduled/manual SSOT scans, both validation commands are followed by Useful? React with 👍 / 👎. |
||
| - name: Report drift summary | ||
| if: always() | ||
| run: | | ||
| echo "## SSOT Drift Scan — $(date -u '+%Y-%m-%dT%H:%M:%SZ')" >> "$GITHUB_STEP_SUMMARY" | ||
| echo "" >> "$GITHUB_STEP_SUMMARY" | ||
| echo "Scans run: docs-sync, route-validation, provider-catalog." >> "$GITHUB_STEP_SUMMARY" | ||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
[WARNING]:
$schemareferences a personal fork instead of the canonical registryThe schema URL points to
kooshapari/phenotype-registry(a personal fork) rather than the canonical phenotype-registry organization. Schema validation breaks if the fork is renamed, deleted, or made private.Reply with
@kilocode-bot fix itto have Kilo Code address this issue.