mirror of
https://github.com/affaan-m/everything-claude-code.git
synced 2026-06-11 02:33:10 +08:00
Compare commits
6 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
7197ab9439 | ||
|
|
2432e560f4 | ||
|
|
ca0e6a8dc7 | ||
|
|
4423f10cfb | ||
|
|
3b12fb273f | ||
|
|
4fb80d8861 |
70
.caliber/learning/current-session.jsonl
Normal file
70
.caliber/learning/current-session.jsonl
Normal file
File diff suppressed because one or more lines are too long
6
.caliber/learning/state.json
Normal file
6
.caliber/learning/state.json
Normal file
@@ -0,0 +1,6 @@
|
|||||||
|
{
|
||||||
|
"sessionId": "d43d7ca3-7fe6-40a0-8bf6-92c3848903b8",
|
||||||
|
"eventCount": 13,
|
||||||
|
"lastAnalysisTimestamp": null,
|
||||||
|
"lastAnalysisEventCount": 0
|
||||||
|
}
|
||||||
15
.github/workflows/reusable-test.yml
vendored
15
.github/workflows/reusable-test.yml
vendored
@@ -149,6 +149,21 @@ jobs:
|
|||||||
env:
|
env:
|
||||||
CLAUDE_CODE_PACKAGE_MANAGER: ${{ inputs.package-manager }}
|
CLAUDE_CODE_PACKAGE_MANAGER: ${{ inputs.package-manager }}
|
||||||
|
|
||||||
|
- name: Run coverage
|
||||||
|
run: npm run coverage
|
||||||
|
continue-on-error: true
|
||||||
|
env:
|
||||||
|
CLAUDE_CODE_PACKAGE_MANAGER: ${{ inputs.package-manager }}
|
||||||
|
|
||||||
|
- name: Upload coverage reports
|
||||||
|
if: always()
|
||||||
|
uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7.0.1
|
||||||
|
with:
|
||||||
|
name: coverage-${{ inputs.os }}-node${{ inputs.node-version }}-${{ inputs.package-manager }}
|
||||||
|
path: |
|
||||||
|
coverage/
|
||||||
|
*.lcov
|
||||||
|
|
||||||
- name: Upload test artifacts
|
- name: Upload test artifacts
|
||||||
if: failure()
|
if: failure()
|
||||||
uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7.0.1
|
uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7.0.1
|
||||||
|
|||||||
@@ -89,7 +89,7 @@ This repo is the raw code only. The guides explain everything.
|
|||||||
### v2.0.0-rc.1 — Surface Refresh, Operator Workflows, and ECC 2.0 Alpha (Apr 2026)
|
### v2.0.0-rc.1 — Surface Refresh, Operator Workflows, and ECC 2.0 Alpha (Apr 2026)
|
||||||
|
|
||||||
- **Dashboard GUI** — New Tkinter-based desktop application (`ecc_dashboard.py` or `npm run dashboard`) with dark/light theme toggle, font customization, and project logo in header and taskbar.
|
- **Dashboard GUI** — New Tkinter-based desktop application (`ecc_dashboard.py` or `npm run dashboard`) with dark/light theme toggle, font customization, and project logo in header and taskbar.
|
||||||
- **Public surface synced to the live repo** — metadata, catalog counts, plugin manifests, and install-facing docs now match the actual OSS surface: 55 agents, 208 skills, and 72 legacy command shims.
|
- **Public surface synced to the live repo** — metadata, catalog counts, plugin manifests, and install-facing docs now match the actual OSS surface: 60 agents, 228 skills, and 75 legacy command shims.
|
||||||
- **Operator and outbound workflow expansion** — `brand-voice`, `social-graph-ranker`, `connections-optimizer`, `customer-billing-ops`, `ecc-tools-cost-audit`, `google-workspace-ops`, `project-flow-ops`, and `workspace-surface-audit` round out the operator lane.
|
- **Operator and outbound workflow expansion** — `brand-voice`, `social-graph-ranker`, `connections-optimizer`, `customer-billing-ops`, `ecc-tools-cost-audit`, `google-workspace-ops`, `project-flow-ops`, and `workspace-surface-audit` round out the operator lane.
|
||||||
- **Media and launch tooling** — `manim-video`, `remotion-video-creation`, and upgraded social publishing surfaces make technical explainers and launch content part of the same system.
|
- **Media and launch tooling** — `manim-video`, `remotion-video-creation`, and upgraded social publishing surfaces make technical explainers and launch content part of the same system.
|
||||||
- **Framework and product surface growth** — `nestjs-patterns`, richer Codex/OpenCode install surfaces, and expanded cross-harness packaging keep the repo usable beyond Claude Code alone.
|
- **Framework and product surface growth** — `nestjs-patterns`, richer Codex/OpenCode install surfaces, and expanded cross-harness packaging keep the repo usable beyond Claude Code alone.
|
||||||
|
|||||||
798
docs/COMMAND-REGISTRY.json
Normal file
798
docs/COMMAND-REGISTRY.json
Normal file
@@ -0,0 +1,798 @@
|
|||||||
|
{
|
||||||
|
"generated": "2026-05-14T18:36:38.210Z",
|
||||||
|
"totalCommands": 75,
|
||||||
|
"commands": [
|
||||||
|
{
|
||||||
|
"command": "aside",
|
||||||
|
"description": "Aside Command",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/aside.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "auto-update",
|
||||||
|
"description": "Auto Update",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/auto-update.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "build-fix",
|
||||||
|
"description": "Build and Fix",
|
||||||
|
"type": "refactoring",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/build-fix.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "checkpoint",
|
||||||
|
"description": "Checkpoint Command",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/checkpoint.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "code-review",
|
||||||
|
"description": "Code Review",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/code-review.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "cost-report",
|
||||||
|
"description": "Cost Report",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/cost-report.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "cpp-build",
|
||||||
|
"description": "C++ Build and Fix",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [
|
||||||
|
"cpp-coding-standards"
|
||||||
|
],
|
||||||
|
"path": "commands/cpp-build.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "cpp-review",
|
||||||
|
"description": "C++ Code Review",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [
|
||||||
|
"cpp-coding-standards",
|
||||||
|
"cpp-testing"
|
||||||
|
],
|
||||||
|
"path": "commands/cpp-review.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "cpp-test",
|
||||||
|
"description": "C++ TDD Command",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [
|
||||||
|
"cpp-testing",
|
||||||
|
"tdd-workflow"
|
||||||
|
],
|
||||||
|
"path": "commands/cpp-test.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "ecc-guide",
|
||||||
|
"description": "/ecc-guide",
|
||||||
|
"type": "review",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [
|
||||||
|
"ecc-guide",
|
||||||
|
"security-scan"
|
||||||
|
],
|
||||||
|
"path": "commands/ecc-guide.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "evolve",
|
||||||
|
"description": "Analyze instincts and suggest or generate evolved structures",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [
|
||||||
|
"continuous-learning-v2"
|
||||||
|
],
|
||||||
|
"path": "commands/evolve.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "fastapi-review",
|
||||||
|
"description": "FastAPI Review",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/fastapi-review.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "feature-dev",
|
||||||
|
"description": "",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/feature-dev.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "flutter-build",
|
||||||
|
"description": "Flutter Build and Fix",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [
|
||||||
|
"flutter-dart-code-review"
|
||||||
|
],
|
||||||
|
"path": "commands/flutter-build.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "flutter-review",
|
||||||
|
"description": "Flutter Code Review",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [
|
||||||
|
"flutter-dart-code-review"
|
||||||
|
],
|
||||||
|
"path": "commands/flutter-review.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "flutter-test",
|
||||||
|
"description": "Flutter Test",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [
|
||||||
|
"flutter-dart-code-review"
|
||||||
|
],
|
||||||
|
"path": "commands/flutter-test.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "gan-build",
|
||||||
|
"description": "",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/gan-build.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "gan-design",
|
||||||
|
"description": "",
|
||||||
|
"type": "review",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/gan-design.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "go-build",
|
||||||
|
"description": "Go Build and Fix",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [
|
||||||
|
"golang-patterns"
|
||||||
|
],
|
||||||
|
"path": "commands/go-build.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "go-review",
|
||||||
|
"description": "Go Code Review",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [
|
||||||
|
"golang-patterns",
|
||||||
|
"golang-testing"
|
||||||
|
],
|
||||||
|
"path": "commands/go-review.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "go-test",
|
||||||
|
"description": "Go TDD Command",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [
|
||||||
|
"golang-testing",
|
||||||
|
"tdd-workflow"
|
||||||
|
],
|
||||||
|
"path": "commands/go-test.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "gradle-build",
|
||||||
|
"description": "Gradle Build Fix",
|
||||||
|
"type": "build",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/gradle-build.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "harness-audit",
|
||||||
|
"description": "Harness Audit Command",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/harness-audit.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "hookify-configure",
|
||||||
|
"description": "",
|
||||||
|
"type": "general",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/hookify-configure.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "hookify-help",
|
||||||
|
"description": "",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/hookify-help.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "hookify-list",
|
||||||
|
"description": "",
|
||||||
|
"type": "general",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/hookify-list.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "hookify",
|
||||||
|
"description": "",
|
||||||
|
"type": "general",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/hookify.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "instinct-export",
|
||||||
|
"description": "Export instincts from project/global scope to a file",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/instinct-export.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "instinct-import",
|
||||||
|
"description": "Import instincts from file or URL into project/global scope",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [
|
||||||
|
"continuous-learning-v2"
|
||||||
|
],
|
||||||
|
"path": "commands/instinct-import.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "instinct-status",
|
||||||
|
"description": "Show learned instincts (project + global) with confidence",
|
||||||
|
"type": "general",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [
|
||||||
|
"continuous-learning-v2"
|
||||||
|
],
|
||||||
|
"path": "commands/instinct-status.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "jira",
|
||||||
|
"description": "Jira Command",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [
|
||||||
|
"jira-integration"
|
||||||
|
],
|
||||||
|
"path": "commands/jira.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "kotlin-build",
|
||||||
|
"description": "Kotlin Build and Fix",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [
|
||||||
|
"kotlin-patterns"
|
||||||
|
],
|
||||||
|
"path": "commands/kotlin-build.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "kotlin-review",
|
||||||
|
"description": "Kotlin Code Review",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [
|
||||||
|
"kotlin-patterns",
|
||||||
|
"kotlin-testing"
|
||||||
|
],
|
||||||
|
"path": "commands/kotlin-review.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "kotlin-test",
|
||||||
|
"description": "Kotlin TDD Command",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [
|
||||||
|
"kotlin-testing",
|
||||||
|
"tdd-workflow"
|
||||||
|
],
|
||||||
|
"path": "commands/kotlin-test.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "learn-eval",
|
||||||
|
"description": "\"Under 130 characters\"",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/learn-eval.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "learn",
|
||||||
|
"description": "/learn - Extract Reusable Patterns",
|
||||||
|
"type": "review",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/learn.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "loop-start",
|
||||||
|
"description": "Loop Start Command",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/loop-start.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "loop-status",
|
||||||
|
"description": "Loop Status Command",
|
||||||
|
"type": "general",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/loop-status.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "model-route",
|
||||||
|
"description": "Model Route Command",
|
||||||
|
"type": "review",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/model-route.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "multi-backend",
|
||||||
|
"description": "Backend - Backend-Focused Development",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/multi-backend.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "multi-execute",
|
||||||
|
"description": "Execute - Multi-Model Collaborative Execution",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/multi-execute.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "multi-frontend",
|
||||||
|
"description": "Frontend - Frontend-Focused Development",
|
||||||
|
"type": "review",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/multi-frontend.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "multi-plan",
|
||||||
|
"description": "Plan - Multi-Model Collaborative Planning",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [
|
||||||
|
"accessibility"
|
||||||
|
],
|
||||||
|
"path": "commands/multi-plan.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "multi-workflow",
|
||||||
|
"description": "Workflow - Multi-Model Collaborative Development",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/multi-workflow.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "plan-prd",
|
||||||
|
"description": "PRD Command",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/plan-prd.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "plan",
|
||||||
|
"description": "Plan Command",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/plan.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "pm2",
|
||||||
|
"description": "PM2 Init",
|
||||||
|
"type": "general",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/pm2.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "pr",
|
||||||
|
"description": "Create Pull Request",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/pr.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "project-init",
|
||||||
|
"description": "/project-init",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [
|
||||||
|
"ecc-guide"
|
||||||
|
],
|
||||||
|
"path": "commands/project-init.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "projects",
|
||||||
|
"description": "List known projects and their instinct statistics",
|
||||||
|
"type": "general",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [
|
||||||
|
"continuous-learning-v2"
|
||||||
|
],
|
||||||
|
"path": "commands/projects.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "promote",
|
||||||
|
"description": "Promote project-scoped instincts to global scope",
|
||||||
|
"type": "review",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [
|
||||||
|
"continuous-learning-v2"
|
||||||
|
],
|
||||||
|
"path": "commands/promote.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "prp-commit",
|
||||||
|
"description": "Smart Commit",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/prp-commit.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "prp-implement",
|
||||||
|
"description": "PRP Implement",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/prp-implement.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "prp-plan",
|
||||||
|
"description": "PRP Plan",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/prp-plan.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "prp-pr",
|
||||||
|
"description": "Create Pull Request",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/prp-pr.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "prp-prd",
|
||||||
|
"description": "Product Requirements Document Generator",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/prp-prd.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "prune",
|
||||||
|
"description": "Delete pending instincts older than 30 days that were never promoted",
|
||||||
|
"type": "review",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [
|
||||||
|
"continuous-learning-v2"
|
||||||
|
],
|
||||||
|
"path": "commands/prune.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "python-review",
|
||||||
|
"description": "Python Code Review",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [
|
||||||
|
"python-patterns",
|
||||||
|
"python-testing"
|
||||||
|
],
|
||||||
|
"path": "commands/python-review.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "quality-gate",
|
||||||
|
"description": "Quality Gate Command",
|
||||||
|
"type": "review",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/quality-gate.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "refactor-clean",
|
||||||
|
"description": "Refactor Clean",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/refactor-clean.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "resume-session",
|
||||||
|
"description": "Resume Session Command",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/resume-session.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "review-pr",
|
||||||
|
"description": "",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/review-pr.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "rust-build",
|
||||||
|
"description": "Rust Build and Fix",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [
|
||||||
|
"rust-patterns"
|
||||||
|
],
|
||||||
|
"path": "commands/rust-build.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "rust-review",
|
||||||
|
"description": "Rust Code Review",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [
|
||||||
|
"rust-patterns",
|
||||||
|
"rust-testing"
|
||||||
|
],
|
||||||
|
"path": "commands/rust-review.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "rust-test",
|
||||||
|
"description": "Rust TDD Command",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [
|
||||||
|
"rust-patterns",
|
||||||
|
"rust-testing"
|
||||||
|
],
|
||||||
|
"path": "commands/rust-test.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "santa-loop",
|
||||||
|
"description": "Santa Loop",
|
||||||
|
"type": "review",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/santa-loop.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "save-session",
|
||||||
|
"description": "Save Session Command",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/save-session.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "security-scan",
|
||||||
|
"description": "Security Scan Command",
|
||||||
|
"type": "review",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [
|
||||||
|
"security-scan"
|
||||||
|
],
|
||||||
|
"path": "commands/security-scan.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "sessions",
|
||||||
|
"description": "Sessions Command",
|
||||||
|
"type": "general",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/sessions.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "setup-pm",
|
||||||
|
"description": "Package Manager Setup",
|
||||||
|
"type": "build",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/setup-pm.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "skill-create",
|
||||||
|
"description": "Analyze local git history to extract coding patterns and generate SKILL.md files. Local version of the Skill Creator GitHub App.",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/skill-create.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "skill-health",
|
||||||
|
"description": "Show skill portfolio health dashboard with charts and analytics",
|
||||||
|
"type": "review",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/skill-health.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "test-coverage",
|
||||||
|
"description": "Test Coverage",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/test-coverage.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "update-codemaps",
|
||||||
|
"description": "Update Codemaps",
|
||||||
|
"type": "planning",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/update-codemaps.md"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"command": "update-docs",
|
||||||
|
"description": "Update Documentation",
|
||||||
|
"type": "testing",
|
||||||
|
"primaryAgents": [],
|
||||||
|
"allAgents": [],
|
||||||
|
"skills": [],
|
||||||
|
"path": "commands/update-docs.md"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"statistics": {
|
||||||
|
"byType": {
|
||||||
|
"testing": 52,
|
||||||
|
"refactoring": 1,
|
||||||
|
"review": 11,
|
||||||
|
"build": 2,
|
||||||
|
"general": 8,
|
||||||
|
"planning": 1
|
||||||
|
},
|
||||||
|
"topAgents": [],
|
||||||
|
"topSkills": [
|
||||||
|
{
|
||||||
|
"skill": "continuous-learning-v2",
|
||||||
|
"count": 6
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"skill": "tdd-workflow",
|
||||||
|
"count": 3
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"skill": "flutter-dart-code-review",
|
||||||
|
"count": 3
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"skill": "rust-patterns",
|
||||||
|
"count": 3
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"skill": "cpp-coding-standards",
|
||||||
|
"count": 2
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"skill": "cpp-testing",
|
||||||
|
"count": 2
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"skill": "ecc-guide",
|
||||||
|
"count": 2
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"skill": "security-scan",
|
||||||
|
"count": 2
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"skill": "golang-patterns",
|
||||||
|
"count": 2
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"skill": "golang-testing",
|
||||||
|
"count": 2
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -153,6 +153,24 @@ As of 2026-05-13:
|
|||||||
`/ecc-tools analyze --job status` now reads the #65 latest-result cache for
|
`/ecc-tools analyze --job status` now reads the #65 latest-result cache for
|
||||||
the current PR head and posts a compact completed/blocked/not-run table with
|
the current PR head and posts a compact completed/blocked/not-run table with
|
||||||
the next hosted job command, without queueing work or billing usage.
|
the next hosted job command, without queueing work or billing usage.
|
||||||
|
- ECC-Tools PR #67 merged as `f20e6bec2b0bf49e4cc36e08b7285c795973b73d`
|
||||||
|
and made the hosted depth-plan check-run status-aware:
|
||||||
|
queued PR analysis now reads the #65/#66 latest-result cache when publishing
|
||||||
|
`ECC Tools / Hosted Depth Plan`, includes the latest hosted run status in
|
||||||
|
the plan table, and recommends the next unrun ready job before reruns.
|
||||||
|
- ECC-Tools PR #68 merged as `2cde524b5ef8f34ab7bb1af973248fe4be4359f8`
|
||||||
|
and added deterministic hosted promotion readiness:
|
||||||
|
opened/synchronized PRs now publish a non-blocking
|
||||||
|
`ECC Tools / Hosted Promotion Readiness` check-run that compares changed
|
||||||
|
files against the checked-in evaluator/RAG corpus, warns on missing
|
||||||
|
hosted-job promotion evidence, and can be disabled with
|
||||||
|
`PR_HOSTED_PROMOTION_READINESS_CHECK_MODE=off`.
|
||||||
|
- ECC-Tools PR #69 merged as `d0112dac7cef807ae27def41f057682ef0772cce`
|
||||||
|
and extended hosted promotion readiness with deterministic output scoring:
|
||||||
|
the check now reads cached completed hosted job results for the current PR
|
||||||
|
head, scores their artifacts and findings against evaluator/RAG corpus
|
||||||
|
expectations, and treats matching hosted artifacts as promotion evidence
|
||||||
|
before reporting a gap.
|
||||||
- Handoff `ecc-supply-chain-audit-20260513-0645.md` under
|
- Handoff `ecc-supply-chain-audit-20260513-0645.md` under
|
||||||
`~/.cluster-swarm/handoffs/`
|
`~/.cluster-swarm/handoffs/`
|
||||||
records the May 13 supply-chain sweep: no active lockfile/manifest hit for
|
records the May 13 supply-chain sweep: no active lockfile/manifest hit for
|
||||||
@@ -386,6 +404,16 @@ As of 2026-05-13:
|
|||||||
`/ecc-tools analyze --job status`, summarizing completed, blocked, and
|
`/ecc-tools analyze --job status`, summarizing completed, blocked, and
|
||||||
not-yet-run hosted jobs for the PR head and recommending the next hosted job
|
not-yet-run hosted jobs for the PR head and recommending the next hosted job
|
||||||
command.
|
command.
|
||||||
|
- ECC-Tools PR #67 feeds those cached results back into the hosted depth-plan
|
||||||
|
check-run so queued analysis recommends the next unrun ready hosted job from
|
||||||
|
cache state instead of repeating the static readiness order.
|
||||||
|
- ECC-Tools PR #68 adds the first evaluator-backed hosted promotion gate:
|
||||||
|
opened/synchronized PRs get a non-blocking Hosted Promotion Readiness
|
||||||
|
check-run that turns the evaluator/RAG corpus into warnings when changed
|
||||||
|
files match fixture scenarios without their expected evidence artifacts.
|
||||||
|
- ECC-Tools PR #69 extends that gate to score cached completed hosted job
|
||||||
|
outputs for the current PR head, so hosted artifacts can satisfy corpus
|
||||||
|
evidence expectations before the check reports a promotion gap.
|
||||||
- ECC PR #1803 landed the contributor Quarkus handling branch after maintainer
|
- ECC PR #1803 landed the contributor Quarkus handling branch after maintainer
|
||||||
cleanup, current-`main` alignment, full local validation, and preservation of
|
cleanup, current-`main` alignment, full local validation, and preservation of
|
||||||
the author's removal of incomplete ja-JP and zh-CN Quarkus translations.
|
the author's removal of incomplete ja-JP and zh-CN Quarkus translations.
|
||||||
@@ -439,10 +467,10 @@ is not complete unless the evidence column exists and has been freshly verified.
|
|||||||
| Claude and Codex plugin publication | Contact/submission path with required artifacts and status | Publication readiness, naming matrix, and May 12 dry-run evidence document plugin validation, clean-checkout Claude tag/install smoke, and Codex marketplace CLI shape | Needs explicit approval for real tag/push and marketplace submission |
|
| Claude and Codex plugin publication | Contact/submission path with required artifacts and status | Publication readiness, naming matrix, and May 12 dry-run evidence document plugin validation, clean-checkout Claude tag/install smoke, and Codex marketplace CLI shape | Needs explicit approval for real tag/push and marketplace submission |
|
||||||
| Articles, tweets, and announcements | X thread, LinkedIn copy, GitHub release copy, push checklist | Draft launch collateral exists under rc.1 release docs | Needs URL-backed refresh |
|
| Articles, tweets, and announcements | X thread, LinkedIn copy, GitHub release copy, push checklist | Draft launch collateral exists under rc.1 release docs | Needs URL-backed refresh |
|
||||||
| AgentShield enterprise iteration | Policy gates, SARIF, packs, provenance, corpus, HTML reports, exception lifecycle audit, baseline drift Action/CLI surfaces, evidence-pack redaction, harness adapter registry, enterprise research roadmap, supply-chain hardened release path, CI-safe baseline fingerprints, corpus accuracy recommendations, remediation workflow phases, env proxy hijack corpus coverage | PRs #53, #55-#64, #67-#69, and #78-#82 landed with test evidence; native PDF export deferred in favor of self-contained HTML plus print-to-PDF until explicit enterprise demand appears; `docs/architecture/agentshield-enterprise-research-roadmap.md` now has baseline drift, evidence-pack bundle, redaction, adapter-registry, supply-chain hardening, hashed baseline fingerprints, corpus accuracy recommendation, remediation workflow, and env proxy hijack corpus slices landed | Next hosted evidence-pack workflow depth |
|
| AgentShield enterprise iteration | Policy gates, SARIF, packs, provenance, corpus, HTML reports, exception lifecycle audit, baseline drift Action/CLI surfaces, evidence-pack redaction, harness adapter registry, enterprise research roadmap, supply-chain hardened release path, CI-safe baseline fingerprints, corpus accuracy recommendations, remediation workflow phases, env proxy hijack corpus coverage | PRs #53, #55-#64, #67-#69, and #78-#82 landed with test evidence; native PDF export deferred in favor of self-contained HTML plus print-to-PDF until explicit enterprise demand appears; `docs/architecture/agentshield-enterprise-research-roadmap.md` now has baseline drift, evidence-pack bundle, redaction, adapter-registry, supply-chain hardening, hashed baseline fingerprints, corpus accuracy recommendation, remediation workflow, and env proxy hijack corpus slices landed | Next hosted evidence-pack workflow depth |
|
||||||
| ECC Tools next-level app | Billing audit, PR checks, deep analyzer, sync backlog, evaluator/RAG corpus, analysis-depth readiness, hosted execution planning, hosted CI diagnostics, hosted security evidence review, hosted harness compatibility audit, hosted reference-set evaluation, hosted AI routing/cost review, hosted team backlog routing, hosted depth-plan check-run, PR-comment hosted job dispatch, hosted job result history/check-runs, hosted result status command | PRs #26-#43 plus #53-#66 landed with test evidence, including AgentShield evidence-pack gap routing, canonical bundle recognition, supply-chain signature gates, PR draft follow-up Linear tracking, evidence-backed/deep-ready repository classification, the `/api/analysis/depth-plan` hosted job plan, `/api/analysis/jobs/ci-diagnostics`, `/api/analysis/jobs/security-evidence-review`, `/api/analysis/jobs/harness-compatibility-audit`, `/api/analysis/jobs/reference-set-evaluation`, `/api/analysis/jobs/ai-routing-cost-review`, `/api/analysis/jobs/team-backlog-routing`, the `ECC Tools / Hosted Depth Plan` check-run, `/ecc-tools analyze --job ...` PR-comment dispatch, non-blocking per-hosted-job result check-runs backed by 30-day result cache records, and `/ecc-tools analyze --job status` cache lookup | Next work is evaluator-backed hosted promotion and status-aware depth-plan recommendations |
|
| ECC Tools next-level app | Billing audit, PR checks, deep analyzer, sync backlog, evaluator/RAG corpus, analysis-depth readiness, hosted execution planning, hosted CI diagnostics, hosted security evidence review, hosted harness compatibility audit, hosted reference-set evaluation, hosted AI routing/cost review, hosted team backlog routing, hosted depth-plan check-run, PR-comment hosted job dispatch, hosted job result history/check-runs, hosted result status command, status-aware depth-plan recommendations, hosted promotion readiness, hosted promotion output scoring | PRs #26-#43 plus #53-#69 landed with test evidence, including AgentShield evidence-pack gap routing, canonical bundle recognition, supply-chain signature gates, PR draft follow-up Linear tracking, evidence-backed/deep-ready repository classification, the `/api/analysis/depth-plan` hosted job plan, `/api/analysis/jobs/ci-diagnostics`, `/api/analysis/jobs/security-evidence-review`, `/api/analysis/jobs/harness-compatibility-audit`, `/api/analysis/jobs/reference-set-evaluation`, `/api/analysis/jobs/ai-routing-cost-review`, `/api/analysis/jobs/team-backlog-routing`, the `ECC Tools / Hosted Depth Plan` check-run, `/ecc-tools analyze --job ...` PR-comment dispatch, non-blocking per-hosted-job result check-runs backed by 30-day result cache records, `/ecc-tools analyze --job status` cache lookup, cache-aware next-job recommendations in the depth-plan check-run, the `ECC Tools / Hosted Promotion Readiness` corpus-backed PR check-run, and deterministic hosted-output scoring against cached completed job artifacts/findings | Next work is retrieval/model-backed hosted promotion after deterministic output scoring |
|
||||||
| GitGuardian/Dependabot/CodeRabbit-style checks | Non-blocking taxonomy, deterministic follow-up checks, and local supply-chain gates | ECC-Tools risk taxonomy check plus follow-up signals landed, including Skill Quality, Deep Analyzer Evidence, Analyzer Corpus Evidence, RAG/Evaluator Evidence, PR Review/Salvage Evidence, and AgentShield evidence-pack evidence; #1846 added npm registry signature gates; #1848 added the supply-chain incident-response playbook and `pull_request_target` cache-poisoning validator guard; #1851 added the privileged checkout credential-persistence guard; AgentShield #78, JARVIS #13, and ECC-Tools #53 applied the same hardening outside trunk | Current supply-chain gate complete; deeper hosted review features remain future |
|
| GitGuardian/Dependabot/CodeRabbit-style checks | Non-blocking taxonomy, deterministic follow-up checks, and local supply-chain gates | ECC-Tools risk taxonomy check plus follow-up signals landed, including Skill Quality, Deep Analyzer Evidence, Analyzer Corpus Evidence, RAG/Evaluator Evidence, PR Review/Salvage Evidence, and AgentShield evidence-pack evidence; #1846 added npm registry signature gates; #1848 added the supply-chain incident-response playbook and `pull_request_target` cache-poisoning validator guard; #1851 added the privileged checkout credential-persistence guard; AgentShield #78, JARVIS #13, and ECC-Tools #53 applied the same hardening outside trunk | Current supply-chain gate complete; deeper hosted review features remain future |
|
||||||
| Harness-agnostic learning system | Audit, adapter matrix, observability, traces, promotion loop | Audit/adapters/observability gates plus `docs/architecture/evaluator-rag-prototype.md`, `examples/evaluator-rag-prototype/`, and ECC-Tools PR #40 define read-only stale-salvage, billing-readiness, CI-failure-diagnosis, harness-config-quality, AgentShield policy-exception, skill-quality evidence, deep-analyzer evidence, and RAG/evaluator comparison scenarios with trace, report, playbook, verifier, and predictive-check artifacts | Local corpus complete; hosted integration remains future |
|
| Harness-agnostic learning system | Audit, adapter matrix, observability, traces, promotion loop | Audit/adapters/observability gates plus `docs/architecture/evaluator-rag-prototype.md`, `examples/evaluator-rag-prototype/`, and ECC-Tools PR #40 define read-only stale-salvage, billing-readiness, CI-failure-diagnosis, harness-config-quality, AgentShield policy-exception, skill-quality evidence, deep-analyzer evidence, and RAG/evaluator comparison scenarios with trace, report, playbook, verifier, and predictive-check artifacts; ECC-Tools PRs #68/#69 now turn that corpus into a deterministic PR check-run gate with cached hosted-output scoring | Deterministic hosted PR check and cached output scoring integrated; hosted retrieval remains future |
|
||||||
| Linear roadmap is detailed | Linear project status plus repo mirror | Repo mirror exists; issue creation was retried on 2026-05-12 and remains blocked by the workspace free issue limit; this May 13 sync adds ECC #1860, AgentShield #78-#82, JARVIS #13, ECC-Tools #53-#66, resolved queue/discussion counts, and Linear project status updates through ECC-Tools #66 | Needs recurring status updates after each merge batch |
|
| Linear roadmap is detailed | Linear project status plus repo mirror | Repo mirror exists; issue creation was retried on 2026-05-12 and remains blocked by the workspace free issue limit; this May 13 sync adds ECC #1860, AgentShield #78-#82, JARVIS #13, ECC-Tools #53-#69, resolved queue/discussion counts, and Linear project status updates through ECC-Tools #69 | Needs recurring status updates after each merge batch |
|
||||||
| Flow separation and progress tracking | Flow lanes with owner artifacts and update cadence | This roadmap defines lanes below and `docs/architecture/progress-sync-contract.md` makes GitHub/Linear/handoff/roadmap sync part of the readiness gate | Active |
|
| Flow separation and progress tracking | Flow lanes with owner artifacts and update cadence | This roadmap defines lanes below and `docs/architecture/progress-sync-contract.md` makes GitHub/Linear/handoff/roadmap sync part of the readiness gate | Active |
|
||||||
| Realtime Linear sync | Project updates while issue limit is blocked; issues later | ECC-Tools #39 implements opt-in Linear API sync for deferred follow-up backlog items, and ECC-Tools #54 adds copy-ready PR drafts to that backlog when draft PR shells are not opened; `docs/architecture/progress-sync-contract.md` defines the local file-backed realtime boundary while issue capacity is blocked | Needs workspace capacity/config rollout |
|
| Realtime Linear sync | Project updates while issue limit is blocked; issues later | ECC-Tools #39 implements opt-in Linear API sync for deferred follow-up backlog items, and ECC-Tools #54 adds copy-ready PR drafts to that backlog when draft PR shells are not opened; `docs/architecture/progress-sync-contract.md` defines the local file-backed realtime boundary while issue capacity is blocked | Needs workspace capacity/config rollout |
|
||||||
| Observability for self-use | Local readiness gate, traces, status snapshots, HUD/status contract, risk ledger, progress-sync contract | `npm run observability:ready` reports 21/21 | Complete for local gate |
|
| Observability for self-use | Local readiness gate, traces, status snapshots, HUD/status contract, risk ledger, progress-sync contract | `npm run observability:ready` reports 21/21 | Complete for local gate |
|
||||||
@@ -461,9 +489,9 @@ repo evidence and merge commits.
|
|||||||
| Queue hygiene and salvage | GitHub PR/issue state, salvage ledger | Append ledger entries for any future stale closures | Every cleanup batch |
|
| Queue hygiene and salvage | GitHub PR/issue state, salvage ledger | Append ledger entries for any future stale closures | Every cleanup batch |
|
||||||
| Release and publication | rc.1 release docs, publication readiness doc | Naming matrix and plugin submission/contact checklist | Before any tag |
|
| Release and publication | rc.1 release docs, publication readiness doc | Naming matrix and plugin submission/contact checklist | Before any tag |
|
||||||
| Harness OS core | Audit, adapter matrix, observability docs, `ecc2/` | HUD/session-control acceptance spec | Weekly until GA |
|
| Harness OS core | Audit, adapter matrix, observability docs, `ecc2/` | HUD/session-control acceptance spec | Weekly until GA |
|
||||||
| Evaluation and RAG | Reference-set validation, harness audit, traces, ECC-Tools corpus | Read-only evaluator/RAG prototype plus stale-salvage, billing-readiness, CI-failure-diagnosis, harness-config-quality, AgentShield policy-exception, skill-quality evidence, deep-analyzer evidence, and RAG/evaluator comparison fixtures | Hosted retrieval/check-run automation plan |
|
| Evaluation and RAG | Reference-set validation, harness audit, traces, ECC-Tools corpus | Read-only evaluator/RAG prototype plus stale-salvage, billing-readiness, CI-failure-diagnosis, harness-config-quality, AgentShield policy-exception, skill-quality evidence, deep-analyzer evidence, and RAG/evaluator comparison fixtures; ECC-Tools #68 publishes the corpus as a hosted promotion readiness check-run, and #69 scores cached hosted job outputs against the same corpus | Hosted retrieval/model-backed promotion plan |
|
||||||
| AgentShield enterprise | AgentShield PR evidence and roadmap notes | Remediation workflow depth or corpus expansion follow-up | Next implementation batch |
|
| AgentShield enterprise | AgentShield PR evidence and roadmap notes | Remediation workflow depth or corpus expansion follow-up | Next implementation batch |
|
||||||
| ECC Tools app | ECC-Tools PR evidence, billing audit, risk taxonomy, evaluator/RAG corpus | ECC-Tools #53 published the supply-chain workflow hardening branch, #54 tracks copy-ready PR drafts in the Linear/project backlog, #55 classifies analysis-depth readiness, #56 exposes the hosted execution plan, #57 executes the first hosted CI diagnostics job, #58 executes the hosted security evidence review job, #59 executes the hosted harness compatibility audit, #60 executes the hosted reference-set evaluation, #61 executes the hosted AI routing/cost review, #62 executes hosted team backlog routing, #63 publishes the hosted depth-plan check-run, and #64 dispatches hosted jobs from PR comments; next work is hosted result history/check-run summaries | Next implementation batch |
|
| ECC Tools app | ECC-Tools PR evidence, billing audit, risk taxonomy, evaluator/RAG corpus | ECC-Tools #53 published the supply-chain workflow hardening branch, #54 tracks copy-ready PR drafts in the Linear/project backlog, #55 classifies analysis-depth readiness, #56 exposes the hosted execution plan, #57 executes the first hosted CI diagnostics job, #58 executes the hosted security evidence review job, #59 executes the hosted harness compatibility audit, #60 executes the hosted reference-set evaluation, #61 executes the hosted AI routing/cost review, #62 executes hosted team backlog routing, #63 publishes the hosted depth-plan check-run, #64 dispatches hosted jobs from PR comments, #65 persists hosted result history/check-runs, #66 exposes hosted job status from PR comments, #67 makes depth-plan recommendations cache-aware, #68 publishes hosted promotion readiness from the evaluator/RAG corpus, and #69 scores cached hosted job outputs against that corpus; next work is retrieval/model-backed hosted promotion | Next implementation batch |
|
||||||
| Linear progress | Linear project status updates, `docs/architecture/progress-sync-contract.md`, and this mirror | Status update with queue/evidence/missing gates | Every significant merge batch |
|
| Linear progress | Linear project status updates, `docs/architecture/progress-sync-contract.md`, and this mirror | Status update with queue/evidence/missing gates | Every significant merge batch |
|
||||||
|
|
||||||
The project status update should always include:
|
The project status update should always include:
|
||||||
@@ -680,9 +708,9 @@ Acceptance:
|
|||||||
PR #82 expanded corpus coverage for env proxy hijacks and out-of-band
|
PR #82 expanded corpus coverage for env proxy hijacks and out-of-band
|
||||||
exfiltration; and ECC-Tools PRs #42/#43 now route and recognize evidence
|
exfiltration; and ECC-Tools PRs #42/#43 now route and recognize evidence
|
||||||
packs. The next slice is hosted evidence-pack workflow depth.
|
packs. The next slice is hosted evidence-pack workflow depth.
|
||||||
2. Feed the #66 status surface back into hosted depth-plan recommendations so
|
2. Plan retrieval/model-backed hosted promotion on top of the #69 deterministic
|
||||||
queued analysis can suggest the next unrun or newly blocked hosted job from
|
hosted output scoring contract, keeping vector/model judgment behind fixture
|
||||||
cached outcomes, not only static readiness.
|
evaluation until the retrieval contract is stable.
|
||||||
3. Enable/configure the merged Linear backlog sync path after workspace issue
|
3. Enable/configure the merged Linear backlog sync path after workspace issue
|
||||||
capacity clears or the Linear workspace is upgraded, then verify PR-draft
|
capacity clears or the Linear workspace is upgraded, then verify PR-draft
|
||||||
salvage items land in the expected project.
|
salvage items land in the expected project.
|
||||||
|
|||||||
@@ -285,6 +285,8 @@
|
|||||||
"postinstall": "echo '\\n ecc-universal installed!\\n Run: npx ecc typescript\\n Compat: npx ecc-install typescript\\n Docs: https://github.com/affaan-m/everything-claude-code\\n'",
|
"postinstall": "echo '\\n ecc-universal installed!\\n Run: npx ecc typescript\\n Compat: npx ecc-install typescript\\n Docs: https://github.com/affaan-m/everything-claude-code\\n'",
|
||||||
"catalog:check": "node scripts/ci/catalog.js --text",
|
"catalog:check": "node scripts/ci/catalog.js --text",
|
||||||
"catalog:sync": "node scripts/ci/catalog.js --write --text",
|
"catalog:sync": "node scripts/ci/catalog.js --write --text",
|
||||||
|
"command-registry:generate": "node scripts/ci/generate-command-registry.js",
|
||||||
|
"command-registry:write": "node scripts/ci/generate-command-registry.js --write",
|
||||||
"lint": "eslint . && markdownlint '**/*.md' --ignore node_modules",
|
"lint": "eslint . && markdownlint '**/*.md' --ignore node_modules",
|
||||||
"harness:adapters": "node scripts/harness-adapter-compliance.js",
|
"harness:adapters": "node scripts/harness-adapter-compliance.js",
|
||||||
"harness:audit": "node scripts/harness-audit.js",
|
"harness:audit": "node scripts/harness-audit.js",
|
||||||
|
|||||||
249
scripts/ci/generate-command-registry.js
Normal file
249
scripts/ci/generate-command-registry.js
Normal file
@@ -0,0 +1,249 @@
|
|||||||
|
#!/usr/bin/env node
|
||||||
|
/**
|
||||||
|
* Generate Command → Agent/Skill Registry
|
||||||
|
*
|
||||||
|
* Scans all command markdown files and extracts:
|
||||||
|
* - Command name/description
|
||||||
|
* - Primary agent(s) referenced
|
||||||
|
* - Skills referenced
|
||||||
|
* - Command type (workflow, testing, review, etc.)
|
||||||
|
*
|
||||||
|
* Usage:
|
||||||
|
* node scripts/ci/generate-command-registry.js
|
||||||
|
* node scripts/ci/generate-command-registry.js --json
|
||||||
|
* node scripts/ci/generate-command-registry.js --write
|
||||||
|
*/
|
||||||
|
|
||||||
|
'use strict';
|
||||||
|
|
||||||
|
const fs = require('fs');
|
||||||
|
const path = require('path');
|
||||||
|
|
||||||
|
const ROOT = path.join(__dirname, '../..');
|
||||||
|
const COMMANDS_DIR = path.join(ROOT, 'commands');
|
||||||
|
const AGENTS_DIR = path.join(ROOT, 'agents');
|
||||||
|
const OUTPUT_PATH = path.join(ROOT, 'docs', 'COMMAND-REGISTRY.json');
|
||||||
|
const WRITE_MODE = process.argv.includes('--write');
|
||||||
|
const OUTPUT_JSON = process.argv.includes('--json');
|
||||||
|
|
||||||
|
const KNOWN_AGENTS = new Set();
|
||||||
|
const KNOWN_SKILLS = new Set();
|
||||||
|
|
||||||
|
// Scan agents directory for known agents
|
||||||
|
function scanKnownAgents() {
|
||||||
|
if (!fs.existsSync(AGENTS_DIR)) return;
|
||||||
|
|
||||||
|
const files = fs.readdirSync(AGENTS_DIR, { withFileTypes: true });
|
||||||
|
files.forEach(entry => {
|
||||||
|
if (entry.isFile() && entry.name.endsWith('.md')) {
|
||||||
|
const agentName = entry.name.replace('.md', '');
|
||||||
|
KNOWN_AGENTS.add(agentName);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
// Scan skills directory for known skills
|
||||||
|
function scanKnownSkills() {
|
||||||
|
const skillsDir = path.join(ROOT, 'skills');
|
||||||
|
if (!fs.existsSync(skillsDir)) return;
|
||||||
|
|
||||||
|
const entries = fs.readdirSync(skillsDir, { withFileTypes: true });
|
||||||
|
entries.forEach(entry => {
|
||||||
|
if (entry.isDirectory() && fs.existsSync(path.join(skillsDir, entry.name, 'SKILL.md'))) {
|
||||||
|
KNOWN_SKILLS.add(entry.name);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
// Extract agents and skills from markdown content
|
||||||
|
function extractReferences(content) {
|
||||||
|
const agents = new Set();
|
||||||
|
const skills = new Set();
|
||||||
|
|
||||||
|
// Pattern: @agent-name or agent-name in code blocks, lists, or descriptions
|
||||||
|
const agentPatterns = [
|
||||||
|
/@([a-z][a-z0-9-]*)/gi, // @agent-name
|
||||||
|
/agent:\s*([a-z][a-z0-9-]*)/gi, // agent: name
|
||||||
|
/subagent(?:_type)?:\s*["']?([a-z][a-z0-9-]*)/gi, // subagent_type: "name"
|
||||||
|
];
|
||||||
|
|
||||||
|
// Pattern: /skill-name or /command-name
|
||||||
|
const skillPatterns = [
|
||||||
|
/\/([a-z][a-z0-9-]*)/gi, // /skill-name
|
||||||
|
/skill:\s*\/?([a-z][a-z0-9-]*)/gi, // skill: /name or skill: name
|
||||||
|
];
|
||||||
|
|
||||||
|
// Extract agents
|
||||||
|
agentPatterns.forEach(pattern => {
|
||||||
|
const matches = content.matchAll(pattern);
|
||||||
|
for (const match of matches) {
|
||||||
|
const ref = match[1];
|
||||||
|
if (KNOWN_AGENTS.has(ref)) {
|
||||||
|
agents.add(ref);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
// Extract skills
|
||||||
|
skillPatterns.forEach(pattern => {
|
||||||
|
const matches = content.matchAll(pattern);
|
||||||
|
for (const match of matches) {
|
||||||
|
const ref = match[1];
|
||||||
|
if (KNOWN_SKILLS.has(ref)) {
|
||||||
|
skills.add(ref);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
return {
|
||||||
|
agents: Array.from(agents).sort(),
|
||||||
|
skills: Array.from(skills).sort()
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
// Infer command type from content
|
||||||
|
function inferCommandType(content, filename) {
|
||||||
|
const lower = content.toLowerCase();
|
||||||
|
|
||||||
|
if (lower.includes('test') || lower.includes('tdd') || lower.includes('coverage')) {
|
||||||
|
return 'testing';
|
||||||
|
}
|
||||||
|
if (lower.includes('review') || lower.includes('audit') || lower.includes('quality')) {
|
||||||
|
return 'review';
|
||||||
|
}
|
||||||
|
if (lower.includes('plan') || lower.includes('design') || lower.includes('architecture')) {
|
||||||
|
return 'planning';
|
||||||
|
}
|
||||||
|
if (lower.includes('refactor') || lower.includes('clean') || lower.includes('simplify')) {
|
||||||
|
return 'refactoring';
|
||||||
|
}
|
||||||
|
if (lower.includes('build') || lower.includes('compile') || lower.includes('setup')) {
|
||||||
|
return 'build';
|
||||||
|
}
|
||||||
|
if (filename.startsWith('multi-')) {
|
||||||
|
return 'orchestration';
|
||||||
|
}
|
||||||
|
|
||||||
|
return 'general';
|
||||||
|
}
|
||||||
|
|
||||||
|
// Process single command file
|
||||||
|
function processCommandFile(filename) {
|
||||||
|
const filePath = path.join(COMMANDS_DIR, filename);
|
||||||
|
const content = fs.readFileSync(filePath, 'utf8');
|
||||||
|
|
||||||
|
// Extract description from frontmatter or first heading
|
||||||
|
let description = '';
|
||||||
|
const frontmatterMatch = content.match(/^---\n[\s\S]*?\ndescription:\s*(.+?)\n[\s\S]*?^---/m);
|
||||||
|
if (frontmatterMatch) {
|
||||||
|
description = frontmatterMatch[1].trim();
|
||||||
|
} else {
|
||||||
|
const headingMatch = content.match(/^#\s+(.+)$/m);
|
||||||
|
if (headingMatch) {
|
||||||
|
description = headingMatch[1].trim();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
const commandName = filename.replace('.md', '');
|
||||||
|
const references = extractReferences(content);
|
||||||
|
const type = inferCommandType(content, filename);
|
||||||
|
|
||||||
|
return {
|
||||||
|
command: commandName,
|
||||||
|
description,
|
||||||
|
type,
|
||||||
|
primaryAgents: references.agents.slice(0, 3), // Top 3 agents
|
||||||
|
allAgents: references.agents,
|
||||||
|
skills: references.skills,
|
||||||
|
path: `commands/${filename}`
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
// Generate full registry
|
||||||
|
function generateRegistry() {
|
||||||
|
scanKnownAgents();
|
||||||
|
scanKnownSkills();
|
||||||
|
|
||||||
|
if (!fs.existsSync(COMMANDS_DIR)) {
|
||||||
|
console.error('commands/ directory not found');
|
||||||
|
process.exit(1);
|
||||||
|
}
|
||||||
|
|
||||||
|
const files = fs.readdirSync(COMMANDS_DIR, { withFileTypes: true })
|
||||||
|
.filter(entry => entry.isFile() && entry.name.endsWith('.md'))
|
||||||
|
.map(entry => entry.name)
|
||||||
|
.sort();
|
||||||
|
|
||||||
|
const registry = {
|
||||||
|
generated: new Date().toISOString(),
|
||||||
|
totalCommands: files.length,
|
||||||
|
commands: files.map(processCommandFile)
|
||||||
|
};
|
||||||
|
|
||||||
|
// Add statistics
|
||||||
|
const typeCounts = {};
|
||||||
|
const agentUsage = {};
|
||||||
|
const skillUsage = {};
|
||||||
|
|
||||||
|
registry.commands.forEach(cmd => {
|
||||||
|
typeCounts[cmd.type] = (typeCounts[cmd.type] || 0) + 1;
|
||||||
|
cmd.allAgents.forEach(agent => {
|
||||||
|
agentUsage[agent] = (agentUsage[agent] || 0) + 1;
|
||||||
|
});
|
||||||
|
cmd.skills.forEach(skill => {
|
||||||
|
skillUsage[skill] = (skillUsage[skill] || 0) + 1;
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
registry.statistics = {
|
||||||
|
byType: typeCounts,
|
||||||
|
topAgents: Object.entries(agentUsage)
|
||||||
|
.sort((a, b) => b[1] - a[1])
|
||||||
|
.slice(0, 10)
|
||||||
|
.map(([agent, count]) => ({ agent, count })),
|
||||||
|
topSkills: Object.entries(skillUsage)
|
||||||
|
.sort((a, b) => b[1] - a[1])
|
||||||
|
.slice(0, 10)
|
||||||
|
.map(([skill, count]) => ({ skill, count }))
|
||||||
|
};
|
||||||
|
|
||||||
|
return registry;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Main execution
|
||||||
|
function main() {
|
||||||
|
const registry = generateRegistry();
|
||||||
|
|
||||||
|
if (OUTPUT_JSON) {
|
||||||
|
console.log(JSON.stringify(registry, null, 2));
|
||||||
|
} else {
|
||||||
|
console.log('\n📊 Command Registry Statistics\n');
|
||||||
|
console.log(`Total commands: ${registry.totalCommands}`);
|
||||||
|
console.log('\nBy type:');
|
||||||
|
Object.entries(registry.statistics.byType)
|
||||||
|
.sort((a, b) => b[1] - a[1])
|
||||||
|
.forEach(([type, count]) => {
|
||||||
|
console.log(` ${type}: ${count}`);
|
||||||
|
});
|
||||||
|
|
||||||
|
console.log('\nTop 10 agents:');
|
||||||
|
registry.statistics.topAgents.forEach(({ agent, count }) => {
|
||||||
|
console.log(` ${agent}: ${count} commands`);
|
||||||
|
});
|
||||||
|
|
||||||
|
console.log('\nTop 10 skills:');
|
||||||
|
registry.statistics.topSkills.forEach(({ skill, count }) => {
|
||||||
|
console.log(` ${skill}: ${count} commands`);
|
||||||
|
});
|
||||||
|
|
||||||
|
console.log(`\n📄 Generated: ${registry.generated}`);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (WRITE_MODE) {
|
||||||
|
fs.mkdirSync(path.dirname(OUTPUT_PATH), { recursive: true });
|
||||||
|
fs.writeFileSync(OUTPUT_PATH, JSON.stringify(registry, null, 2) + '\n');
|
||||||
|
console.log(`\n✅ Registry written to: ${OUTPUT_PATH}`);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
main();
|
||||||
@@ -4,10 +4,6 @@
|
|||||||
const MAX_STDIN = 1024 * 1024;
|
const MAX_STDIN = 1024 * 1024;
|
||||||
const path = require('path');
|
const path = require('path');
|
||||||
const { splitShellSegments } = require('../lib/shell-split');
|
const { splitShellSegments } = require('../lib/shell-split');
|
||||||
const {
|
|
||||||
extractCommandSubstitutions,
|
|
||||||
extractSubshellGroups
|
|
||||||
} = require('../lib/shell-substitution');
|
|
||||||
|
|
||||||
const DEV_COMMAND_WORDS = new Set([
|
const DEV_COMMAND_WORDS = new Set([
|
||||||
'npm',
|
'npm',
|
||||||
@@ -127,8 +123,6 @@ function getLeadingCommandWord(segment) {
|
|||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (token === '{' || token === '}') continue;
|
|
||||||
|
|
||||||
if (/^[A-Za-z_][A-Za-z0-9_]*=.*/.test(token)) continue;
|
if (/^[A-Za-z_][A-Za-z0-9_]*=.*/.test(token)) continue;
|
||||||
|
|
||||||
const normalizedToken = normalizeCommandWord(token);
|
const normalizedToken = normalizeCommandWord(token);
|
||||||
@@ -160,55 +154,23 @@ process.stdin.on('data', chunk => {
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
const TMUX_LAUNCHER = /^\s*tmux\s+(new|new-session|new-window|split-window)\b/;
|
|
||||||
const DEV_PATTERN = /\b(npm\s+run\s+dev|pnpm(?:\s+run)?\s+dev|yarn(?:\s+run)?\s+dev|bun(?:\s+run)?\s+dev)\b/;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Collect every command-line segment we should evaluate. Returns the top-level
|
|
||||||
* segments first, then segments harvested from `$(...)` / backtick command
|
|
||||||
* substitutions and plain `(...)` subshell groups, recursively.
|
|
||||||
*
|
|
||||||
* Without this expansion the leading-command and dev-pattern check below only
|
|
||||||
* sees the outermost command, so wrappers like `$(npm run dev)` and
|
|
||||||
* `(npm run dev)` (which still spawn a dev server) sneak past.
|
|
||||||
*/
|
|
||||||
function collectCheckSegments(cmd) {
|
|
||||||
const segments = [...splitShellSegments(cmd)];
|
|
||||||
const queue = [cmd];
|
|
||||||
const seen = new Set();
|
|
||||||
|
|
||||||
while (queue.length) {
|
|
||||||
const current = queue.shift();
|
|
||||||
if (seen.has(current)) continue;
|
|
||||||
seen.add(current);
|
|
||||||
|
|
||||||
for (const body of extractCommandSubstitutions(current)) {
|
|
||||||
for (const seg of splitShellSegments(body)) segments.push(seg);
|
|
||||||
queue.push(body);
|
|
||||||
}
|
|
||||||
for (const body of extractSubshellGroups(current)) {
|
|
||||||
for (const seg of splitShellSegments(body)) segments.push(seg);
|
|
||||||
queue.push(body);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return segments;
|
|
||||||
}
|
|
||||||
|
|
||||||
function isBlockedDevSegment(segment) {
|
|
||||||
const commandWord = getLeadingCommandWord(segment);
|
|
||||||
if (!commandWord || !DEV_COMMAND_WORDS.has(commandWord)) return false;
|
|
||||||
return DEV_PATTERN.test(segment) && !TMUX_LAUNCHER.test(segment);
|
|
||||||
}
|
|
||||||
|
|
||||||
process.stdin.on('end', () => {
|
process.stdin.on('end', () => {
|
||||||
try {
|
try {
|
||||||
const input = JSON.parse(raw);
|
const input = JSON.parse(raw);
|
||||||
const cmd = String(input.tool_input?.command || '');
|
const cmd = String(input.tool_input?.command || '');
|
||||||
|
|
||||||
if (process.platform !== 'win32') {
|
if (process.platform !== 'win32') {
|
||||||
const segments = collectCheckSegments(cmd);
|
const segments = splitShellSegments(cmd);
|
||||||
const hasBlockedDev = segments.some(isBlockedDevSegment);
|
const tmuxLauncher = /^\s*tmux\s+(new|new-session|new-window|split-window)\b/;
|
||||||
|
const devPattern = /\b(npm\s+run\s+dev|pnpm(?:\s+run)?\s+dev|yarn\s+dev|bun\s+run\s+dev)\b/;
|
||||||
|
|
||||||
|
const hasBlockedDev = segments.some(segment => {
|
||||||
|
const commandWord = getLeadingCommandWord(segment);
|
||||||
|
if (!commandWord || !DEV_COMMAND_WORDS.has(commandWord)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
return devPattern.test(segment) && !tmuxLauncher.test(segment);
|
||||||
|
});
|
||||||
|
|
||||||
if (hasBlockedDev) {
|
if (hasBlockedDev) {
|
||||||
console.error('[Hook] BLOCKED: Dev server must run in tmux for log access');
|
console.error('[Hook] BLOCKED: Dev server must run in tmux for log access');
|
||||||
|
|||||||
@@ -1,246 +0,0 @@
|
|||||||
'use strict';
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Extract executable command-substitution bodies from a shell line.
|
|
||||||
*
|
|
||||||
* Single quotes are literal, so substitutions inside them are ignored;
|
|
||||||
* double quotes still permit substitutions, so those bodies are scanned
|
|
||||||
* before quoted text is stripped. Returns each substitution body plus
|
|
||||||
* any nested substitutions discovered recursively.
|
|
||||||
*
|
|
||||||
* Originally introduced in scripts/hooks/gateguard-fact-force.js
|
|
||||||
* (PR #1853 round 2). Extracted to a shared lib so other PreToolUse
|
|
||||||
* hooks that need the same "scan inside `$(...)` and backticks"
|
|
||||||
* behavior can reuse it without duplicating the parser.
|
|
||||||
*
|
|
||||||
* @param {string} input
|
|
||||||
* @returns {string[]}
|
|
||||||
*/
|
|
||||||
function extractCommandSubstitutions(input) {
|
|
||||||
const source = String(input || '');
|
|
||||||
const substitutions = [];
|
|
||||||
let inSingle = false;
|
|
||||||
let inDouble = false;
|
|
||||||
|
|
||||||
for (let i = 0; i < source.length; i++) {
|
|
||||||
const ch = source[i];
|
|
||||||
const prev = source[i - 1];
|
|
||||||
|
|
||||||
if (ch === '\\' && !inSingle) {
|
|
||||||
i += 1;
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (ch === "'" && !inDouble && prev !== '\\') {
|
|
||||||
inSingle = !inSingle;
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (ch === '"' && !inSingle && prev !== '\\') {
|
|
||||||
inDouble = !inDouble;
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (inSingle) {
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (ch === '`') {
|
|
||||||
let body = '';
|
|
||||||
i += 1;
|
|
||||||
while (i < source.length) {
|
|
||||||
const inner = source[i];
|
|
||||||
if (inner === '\\') {
|
|
||||||
body += inner;
|
|
||||||
if (i + 1 < source.length) {
|
|
||||||
body += source[i + 1];
|
|
||||||
i += 2;
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (inner === '`') {
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
body += inner;
|
|
||||||
i += 1;
|
|
||||||
}
|
|
||||||
if (body.trim()) {
|
|
||||||
substitutions.push(body);
|
|
||||||
substitutions.push(...extractCommandSubstitutions(body));
|
|
||||||
}
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (ch === '$' && source[i + 1] === '(') {
|
|
||||||
let depth = 1;
|
|
||||||
let body = '';
|
|
||||||
let bodyInSingle = false;
|
|
||||||
let bodyInDouble = false;
|
|
||||||
i += 2;
|
|
||||||
while (i < source.length && depth > 0) {
|
|
||||||
const inner = source[i];
|
|
||||||
const innerPrev = source[i - 1];
|
|
||||||
if (inner === '\\' && !bodyInSingle) {
|
|
||||||
body += inner;
|
|
||||||
if (i + 1 < source.length) {
|
|
||||||
body += source[i + 1];
|
|
||||||
i += 2;
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (inner === "'" && !bodyInDouble && innerPrev !== '\\') {
|
|
||||||
bodyInSingle = !bodyInSingle;
|
|
||||||
} else if (inner === '"' && !bodyInSingle && innerPrev !== '\\') {
|
|
||||||
bodyInDouble = !bodyInDouble;
|
|
||||||
} else if (!bodyInSingle && !bodyInDouble) {
|
|
||||||
if (inner === '(') {
|
|
||||||
depth += 1;
|
|
||||||
} else if (inner === ')') {
|
|
||||||
depth -= 1;
|
|
||||||
if (depth === 0) {
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
body += inner;
|
|
||||||
i += 1;
|
|
||||||
}
|
|
||||||
if (body.trim()) {
|
|
||||||
substitutions.push(body);
|
|
||||||
substitutions.push(...extractCommandSubstitutions(body));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return substitutions;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Extract bodies of plain `(...)` subshell groups.
|
|
||||||
*
|
|
||||||
* Bash treats `(npm run dev)` as a subshell that executes its contents, but
|
|
||||||
* the regex-light segment splitters used by our PreToolUse hooks don't peer
|
|
||||||
* inside those parens. This helper finds top-level `(...)` groups (skipping
|
|
||||||
* `$(...)` command substitutions and backticks, which `extractCommandSubstitutions`
|
|
||||||
* already covers) and returns each body, recursing for nested groups.
|
|
||||||
*
|
|
||||||
* Quote semantics:
|
|
||||||
* - Single quotes are literal: `'( ... )'` is a string, not a subshell.
|
|
||||||
* - Double quotes are literal *for parens*: `"( ... )"` is a string too —
|
|
||||||
* bash only honors `$( )` inside double quotes, not bare `( )`.
|
|
||||||
*
|
|
||||||
* @param {string} input
|
|
||||||
* @returns {string[]}
|
|
||||||
*/
|
|
||||||
function extractSubshellGroups(input) {
|
|
||||||
const source = String(input || '');
|
|
||||||
const groups = [];
|
|
||||||
let inSingle = false;
|
|
||||||
let inDouble = false;
|
|
||||||
|
|
||||||
for (let i = 0; i < source.length; i++) {
|
|
||||||
const ch = source[i];
|
|
||||||
const prev = source[i - 1];
|
|
||||||
|
|
||||||
if (ch === '\\' && !inSingle) {
|
|
||||||
i += 1;
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (ch === "'" && !inDouble && prev !== '\\') {
|
|
||||||
inSingle = !inSingle;
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (ch === '"' && !inSingle && prev !== '\\') {
|
|
||||||
inDouble = !inDouble;
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (inSingle || inDouble) {
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (ch === '$' && source[i + 1] === '(') {
|
|
||||||
let depth = 1;
|
|
||||||
let skipInSingle = false;
|
|
||||||
let skipInDouble = false;
|
|
||||||
i += 2;
|
|
||||||
while (i < source.length && depth > 0) {
|
|
||||||
const inner = source[i];
|
|
||||||
const innerPrev = source[i - 1];
|
|
||||||
if (inner === '\\' && !skipInSingle) {
|
|
||||||
i += 2;
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
if (inner === "'" && !skipInDouble && innerPrev !== '\\') {
|
|
||||||
skipInSingle = !skipInSingle;
|
|
||||||
} else if (inner === '"' && !skipInSingle && innerPrev !== '\\') {
|
|
||||||
skipInDouble = !skipInDouble;
|
|
||||||
} else if (!skipInSingle && !skipInDouble) {
|
|
||||||
if (inner === '(') depth += 1;
|
|
||||||
else if (inner === ')') depth -= 1;
|
|
||||||
}
|
|
||||||
i += 1;
|
|
||||||
}
|
|
||||||
i -= 1;
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (ch === '`') {
|
|
||||||
i += 1;
|
|
||||||
while (i < source.length && source[i] !== '`') {
|
|
||||||
if (source[i] === '\\' && i + 1 < source.length) {
|
|
||||||
i += 2;
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
i += 1;
|
|
||||||
}
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (ch === '(') {
|
|
||||||
let depth = 1;
|
|
||||||
let body = '';
|
|
||||||
let bodyInSingle = false;
|
|
||||||
let bodyInDouble = false;
|
|
||||||
i += 1;
|
|
||||||
while (i < source.length && depth > 0) {
|
|
||||||
const inner = source[i];
|
|
||||||
const innerPrev = source[i - 1];
|
|
||||||
if (inner === '\\' && !bodyInSingle) {
|
|
||||||
body += inner;
|
|
||||||
if (i + 1 < source.length) {
|
|
||||||
body += source[i + 1];
|
|
||||||
i += 2;
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (inner === "'" && !bodyInDouble && innerPrev !== '\\') {
|
|
||||||
bodyInSingle = !bodyInSingle;
|
|
||||||
} else if (inner === '"' && !bodyInSingle && innerPrev !== '\\') {
|
|
||||||
bodyInDouble = !bodyInDouble;
|
|
||||||
} else if (!bodyInSingle && !bodyInDouble) {
|
|
||||||
if (inner === '(') {
|
|
||||||
depth += 1;
|
|
||||||
} else if (inner === ')') {
|
|
||||||
depth -= 1;
|
|
||||||
if (depth === 0) {
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
body += inner;
|
|
||||||
i += 1;
|
|
||||||
}
|
|
||||||
if (body.trim()) {
|
|
||||||
groups.push(body);
|
|
||||||
groups.push(...extractSubshellGroups(body));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return groups;
|
|
||||||
}
|
|
||||||
|
|
||||||
module.exports = { extractCommandSubstitutions, extractSubshellGroups };
|
|
||||||
@@ -130,12 +130,12 @@ test('candidate playbook preserves stale-salvage operating rules', () => {
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
test('roadmap points to the evaluator RAG prototype and keeps hosted integration open', () => {
|
test('roadmap points to the evaluator RAG prototype and hosted PR check', () => {
|
||||||
const roadmap = read('docs/ECC-2.0-GA-ROADMAP.md');
|
const roadmap = read('docs/ECC-2.0-GA-ROADMAP.md');
|
||||||
|
|
||||||
assert.ok(roadmap.includes('docs/architecture/evaluator-rag-prototype.md'));
|
assert.ok(roadmap.includes('docs/architecture/evaluator-rag-prototype.md'));
|
||||||
assert.ok(roadmap.includes('examples/evaluator-rag-prototype/'));
|
assert.ok(roadmap.includes('examples/evaluator-rag-prototype/'));
|
||||||
assert.ok(roadmap.includes('Local corpus complete; hosted integration remains future'));
|
assert.ok(roadmap.includes('Deterministic hosted PR check and cached output scoring integrated; hosted retrieval remains future'));
|
||||||
});
|
});
|
||||||
|
|
||||||
test('billing readiness scenario rejects launch copy overclaims', () => {
|
test('billing readiness scenario rejects launch copy overclaims', () => {
|
||||||
|
|||||||
@@ -89,110 +89,6 @@ function runTests() {
|
|||||||
assert.strictEqual(result.code, 0, `Expected exit code 0, got ${result.code}`);
|
assert.strictEqual(result.code, 0, `Expected exit code 0, got ${result.code}`);
|
||||||
}) ? passed++ : failed++);
|
}) ? passed++ : failed++);
|
||||||
|
|
||||||
// --- Subshell bypass regression (issue: dev server slipped past via $(), ``, ()) ---
|
|
||||||
|
|
||||||
if (!isWindows) {
|
|
||||||
(test('blocks $(npm run dev) — command substitution', () => {
|
|
||||||
const result = runScript('$(npm run dev)');
|
|
||||||
assert.strictEqual(result.code, 2, `Expected exit code 2, got ${result.code}`);
|
|
||||||
assert.ok(result.stderr.includes('BLOCKED'), 'expected BLOCKED in stderr');
|
|
||||||
}) ? passed++ : failed++);
|
|
||||||
|
|
||||||
(test('blocks `npm run dev` — backtick substitution', () => {
|
|
||||||
const result = runScript('`npm run dev`');
|
|
||||||
assert.strictEqual(result.code, 2, `Expected exit code 2, got ${result.code}`);
|
|
||||||
}) ? passed++ : failed++);
|
|
||||||
|
|
||||||
(test('blocks echo $(npm run dev) — substitution nested in argument', () => {
|
|
||||||
const result = runScript('echo $(npm run dev)');
|
|
||||||
assert.strictEqual(result.code, 2, `Expected exit code 2, got ${result.code}`);
|
|
||||||
}) ? passed++ : failed++);
|
|
||||||
|
|
||||||
(test('blocks (npm run dev) — plain subshell group', () => {
|
|
||||||
const result = runScript('(npm run dev)');
|
|
||||||
assert.strictEqual(result.code, 2, `Expected exit code 2, got ${result.code}`);
|
|
||||||
}) ? passed++ : failed++);
|
|
||||||
|
|
||||||
(test('blocks $(echo a; npm run dev) — substitution with sequenced segments', () => {
|
|
||||||
const result = runScript('$(echo a; npm run dev)');
|
|
||||||
assert.strictEqual(result.code, 2, `Expected exit code 2, got ${result.code}`);
|
|
||||||
}) ? passed++ : failed++);
|
|
||||||
|
|
||||||
(test('blocks (pnpm dev) — plain subshell group with pnpm', () => {
|
|
||||||
const result = runScript('(pnpm dev)');
|
|
||||||
assert.strictEqual(result.code, 2, `Expected exit code 2, got ${result.code}`);
|
|
||||||
}) ? passed++ : failed++);
|
|
||||||
|
|
||||||
(test('allows tmux launcher inside subshell wrapping (exit code 0)', () => {
|
|
||||||
const result = runScript('(tmux new-session -d -s dev "npm run dev")');
|
|
||||||
assert.strictEqual(result.code, 0, `Expected exit code 0, got ${result.code}`);
|
|
||||||
}) ? passed++ : failed++);
|
|
||||||
|
|
||||||
(test('allows single-quoted "(npm run dev)" — literal string, not a subshell', () => {
|
|
||||||
const result = runScript("git commit -m '(npm run dev)'");
|
|
||||||
assert.strictEqual(result.code, 0, `Expected exit code 0, got ${result.code}`);
|
|
||||||
}) ? passed++ : failed++);
|
|
||||||
|
|
||||||
(test('allows double-quoted "(npm run dev)" — literal in double quotes (bash does not subshell)', () => {
|
|
||||||
const result = runScript('echo "(npm run dev)"');
|
|
||||||
assert.strictEqual(result.code, 0, `Expected exit code 0, got ${result.code}`);
|
|
||||||
}) ? passed++ : failed++);
|
|
||||||
|
|
||||||
(test("allows single-quoted '$(npm run dev)' — literal string, no substitution", () => {
|
|
||||||
const result = runScript("git commit -m '$(npm run dev) fix'");
|
|
||||||
assert.strictEqual(result.code, 0, `Expected exit code 0, got ${result.code}`);
|
|
||||||
}) ? passed++ : failed++);
|
|
||||||
}
|
|
||||||
|
|
||||||
// --- Round 1 review fixes (Greptile + CodeRabbit on PR #1889) ---
|
|
||||||
|
|
||||||
if (!isWindows) {
|
|
||||||
(test('blocks $(echo ")"; (npm run dev)) — quoted ) does not terminate $() early', () => {
|
|
||||||
const result = runScript('$(echo ")"; (npm run dev))');
|
|
||||||
assert.strictEqual(result.code, 2, `Expected exit code 2, got ${result.code}`);
|
|
||||||
}) ? passed++ : failed++);
|
|
||||||
|
|
||||||
(test('blocks (echo ")"; npm run dev) — quoted ) does not terminate (...) early', () => {
|
|
||||||
const result = runScript('(echo ")"; npm run dev)');
|
|
||||||
assert.strictEqual(result.code, 2, `Expected exit code 2, got ${result.code}`);
|
|
||||||
}) ? passed++ : failed++);
|
|
||||||
|
|
||||||
(test('allows $(echo "(npm run dev)") — () inside double-quoted substitution body is literal', () => {
|
|
||||||
const result = runScript('$(echo "(npm run dev)")');
|
|
||||||
assert.strictEqual(result.code, 0, `Expected exit code 0, got ${result.code}`);
|
|
||||||
}) ? passed++ : failed++);
|
|
||||||
|
|
||||||
(test('blocks { npm run dev; } — brace group runs in current shell', () => {
|
|
||||||
const result = runScript('{ npm run dev; }');
|
|
||||||
assert.strictEqual(result.code, 2, `Expected exit code 2, got ${result.code}`);
|
|
||||||
}) ? passed++ : failed++);
|
|
||||||
|
|
||||||
(test('blocks echo hi && { npm run dev; } — brace group after &&', () => {
|
|
||||||
const result = runScript('echo hi && { npm run dev; }');
|
|
||||||
assert.strictEqual(result.code, 2, `Expected exit code 2, got ${result.code}`);
|
|
||||||
}) ? passed++ : failed++);
|
|
||||||
|
|
||||||
(test('allows {npm run dev} — bash requires space after { to form a group', () => {
|
|
||||||
const result = runScript('{npm run dev}');
|
|
||||||
assert.strictEqual(result.code, 0, `Expected exit code 0, got ${result.code}`);
|
|
||||||
}) ? passed++ : failed++);
|
|
||||||
|
|
||||||
(test('blocks yarn run dev — yarn 1.x convention', () => {
|
|
||||||
const result = runScript('yarn run dev');
|
|
||||||
assert.strictEqual(result.code, 2, `Expected exit code 2, got ${result.code}`);
|
|
||||||
}) ? passed++ : failed++);
|
|
||||||
|
|
||||||
(test('blocks bun dev — bun bare form', () => {
|
|
||||||
const result = runScript('bun dev');
|
|
||||||
assert.strictEqual(result.code, 2, `Expected exit code 2, got ${result.code}`);
|
|
||||||
}) ? passed++ : failed++);
|
|
||||||
|
|
||||||
(test('blocks "$(npm run dev)" — double-quoted substitution still substitutes', () => {
|
|
||||||
const result = runScript('echo "$(npm run dev)"');
|
|
||||||
assert.strictEqual(result.code, 2, `Expected exit code 2, got ${result.code}`);
|
|
||||||
}) ? passed++ : failed++);
|
|
||||||
}
|
|
||||||
|
|
||||||
// --- Edge cases ---
|
// --- Edge cases ---
|
||||||
|
|
||||||
(test('empty/invalid input passes through (exit code 0)', () => {
|
(test('empty/invalid input passes through (exit code 0)', () => {
|
||||||
|
|||||||
Reference in New Issue
Block a user