@hongmaple0820/scale-engine 0.21.2 → 0.23.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (82) hide show
  1. package/README.en.md +35 -11
  2. package/README.md +54 -23
  3. package/dist/api/cli.js +284 -4
  4. package/dist/api/cli.js.map +1 -1
  5. package/dist/api/doctor.d.ts +1 -0
  6. package/dist/api/doctor.js +83 -0
  7. package/dist/api/doctor.js.map +1 -1
  8. package/dist/artifact/types.d.ts +1 -1
  9. package/dist/artifact/types.js.map +1 -1
  10. package/dist/cli/phaseCommands.js +22 -6
  11. package/dist/cli/phaseCommands.js.map +1 -1
  12. package/dist/cli/runCommand.d.ts +39 -0
  13. package/dist/cli/runCommand.js +113 -0
  14. package/dist/cli/runCommand.js.map +1 -0
  15. package/dist/config/profiles.d.ts +52 -0
  16. package/dist/config/profiles.js +162 -0
  17. package/dist/config/profiles.js.map +1 -0
  18. package/dist/context/ContextBudget.d.ts +25 -1
  19. package/dist/context/ContextBudget.js +72 -7
  20. package/dist/context/ContextBudget.js.map +1 -1
  21. package/dist/context/ProjectAnatomy.d.ts +18 -0
  22. package/dist/context/ProjectAnatomy.js +287 -0
  23. package/dist/context/ProjectAnatomy.js.map +1 -0
  24. package/dist/dashboard/DashboardServer.d.ts +3 -0
  25. package/dist/dashboard/DashboardServer.js +114 -0
  26. package/dist/dashboard/DashboardServer.js.map +1 -1
  27. package/dist/hooks/BugPatternDetector.d.ts +36 -0
  28. package/dist/hooks/BugPatternDetector.js +207 -0
  29. package/dist/hooks/BugPatternDetector.js.map +1 -0
  30. package/dist/hooks/HookGeneratorEnhanced.js +301 -5
  31. package/dist/hooks/HookGeneratorEnhanced.js.map +1 -1
  32. package/dist/hooks/WorkflowHooksManager.js +24 -0
  33. package/dist/hooks/WorkflowHooksManager.js.map +1 -1
  34. package/dist/index.d.ts +4 -0
  35. package/dist/index.js +2 -0
  36. package/dist/index.js.map +1 -1
  37. package/dist/knowledge/CerebrumManager.d.ts +25 -0
  38. package/dist/knowledge/CerebrumManager.js +127 -0
  39. package/dist/knowledge/CerebrumManager.js.map +1 -0
  40. package/dist/knowledge/SQLiteKnowledgeBase.d.ts +1 -0
  41. package/dist/knowledge/SQLiteKnowledgeBase.js +31 -3
  42. package/dist/knowledge/SQLiteKnowledgeBase.js.map +1 -1
  43. package/dist/knowledge/TfidfIndex.d.ts +50 -0
  44. package/dist/knowledge/TfidfIndex.js +177 -0
  45. package/dist/knowledge/TfidfIndex.js.map +1 -0
  46. package/dist/skills/SkillDiscovery.js +1 -1
  47. package/dist/skills/SkillDiscovery.js.map +1 -1
  48. package/dist/tools/CommandOutputCompressor.d.ts +28 -0
  49. package/dist/tools/CommandOutputCompressor.js +242 -0
  50. package/dist/tools/CommandOutputCompressor.js.map +1 -0
  51. package/dist/tools/CommandRunLedger.d.ts +77 -0
  52. package/dist/tools/CommandRunLedger.js +111 -0
  53. package/dist/tools/CommandRunLedger.js.map +1 -0
  54. package/dist/tools/index.d.ts +2 -0
  55. package/dist/tools/index.js +2 -0
  56. package/dist/tools/index.js.map +1 -1
  57. package/dist/workflow/EngineeringStandards.js +91 -2
  58. package/dist/workflow/EngineeringStandards.js.map +1 -1
  59. package/dist/workflow/GovernanceTemplatePacks.js +2 -2
  60. package/dist/workflow/GovernanceTemplates.js +93 -92
  61. package/dist/workflow/GovernanceTemplates.js.map +1 -1
  62. package/dist/workflow/TaskLevelDetector.d.ts +41 -0
  63. package/dist/workflow/TaskLevelDetector.js +219 -0
  64. package/dist/workflow/TaskLevelDetector.js.map +1 -0
  65. package/dist/workflow/WorkflowOrchestrator.d.ts +59 -0
  66. package/dist/workflow/WorkflowOrchestrator.js +326 -0
  67. package/dist/workflow/WorkflowOrchestrator.js.map +1 -0
  68. package/dist/workflow/gates/GateSystem.d.ts +23 -6
  69. package/dist/workflow/gates/GateSystem.js +114 -25
  70. package/dist/workflow/gates/GateSystem.js.map +1 -1
  71. package/dist/workflow/gates/MetaGovernanceGates.d.ts +70 -0
  72. package/dist/workflow/gates/MetaGovernanceGates.js +617 -0
  73. package/dist/workflow/gates/MetaGovernanceGates.js.map +1 -0
  74. package/dist/workflow/types.d.ts +6 -1
  75. package/docs/README.md +2 -0
  76. package/docs/start/README.md +29 -3
  77. package/docs/start/artifact-lifecycle.md +326 -0
  78. package/docs/start/workflow-upgrade.md +150 -0
  79. package/image/wechat-public.jpg +0 -0
  80. package/image/wxPay.jpg +0 -0
  81. package/image/zfb.jpg +0 -0
  82. package/package.json +10 -9
package/README.en.md CHANGED
@@ -1,23 +1,47 @@
1
1
  <p align="center">
2
- <img src="https://img.shields.io/badge/version-0.21.2-orange?style=flat-square" alt="version" />
2
+ <img src="https://img.shields.io/badge/version-0.23.0-orange?style=flat-square" alt="version" />
3
3
  <img src="https://img.shields.io/badge/platforms-16-blue?style=flat-square" alt="platforms" />
4
4
  <img src="https://img.shields.io/badge/agents-12-blue?style=flat-square" alt="agents" />
5
5
  <img src="https://img.shields.io/badge/workflows-10-green?style=flat-square" alt="workflows" />
6
6
  <img src="https://img.shields.io/badge/detectors-19-red?style=flat-square" alt="detectors" />
7
7
  <img src="https://img.shields.io/badge/tests-verified-brightgreen?style=flat-square" alt="tests" />
8
- <img src="https://img.shields.io/badge/npm-0.21.2-cb3837?style=flat-square&logo=npm" alt="npm" />
9
- </p>
10
-
11
- # SCALE Engine v0.21.2
8
+ <img src="https://img.shields.io/badge/npm-0.23.0-cb3837?style=flat-square&logo=npm" alt="npm" />
9
+ </p>
10
+
11
+ # SCALE Engine v0.23.0
12
12
 
13
13
  SCALE Engine makes AI coding agents follow engineering rules through executable workflow gates, evidence files, and review constraints instead of relying on prompt discipline alone. It helps humans see what the agent explored, planned, verified, skipped, and why a task is or is not ready to ship.
14
14
 
15
- Repository: https://github.com/hongmaple0820/scale-engine
16
- Mirror: https://gitee.com/hongmaple/scale-engine
17
- npm: https://www.npmjs.com/package/@hongmaple0820/scale-engine
18
- Language: [English](README.en.md) | [Chinese](README.md)
19
-
20
- ## What It Solves
15
+ Repository: https://github.com/hongmaple0820/scale-engine
16
+ Mirror: https://gitee.com/hongmaple/scale-engine
17
+ npm: https://www.npmjs.com/package/@hongmaple0820/scale-engine
18
+ Language: [English](README.en.md) | [Chinese](README.md)
19
+
20
+ ## Community
21
+
22
+ SCALE Engine is an engineering workflow governance project for real AI-agent delivery. Contributions, issues, PRs, governance-pack ideas, and field reports are welcome through the source repositories. Chinese users can also follow the WeChat public account for updates, examples, and community entry points.
23
+
24
+ | Platform | Link | Purpose |
25
+ | --- | --- | --- |
26
+ | GitHub | [https://github.com/hongmaple0820/scale-engine](https://github.com/hongmaple0820/scale-engine) | Source, issues, and PRs |
27
+ | Gitee | [https://gitee.com/hongmaple/scale-engine](https://gitee.com/hongmaple/scale-engine) | China mirror and feedback |
28
+ | npm | [https://www.npmjs.com/package/@hongmaple0820/scale-engine](https://www.npmjs.com/package/@hongmaple0820/scale-engine) | CLI package |
29
+
30
+ <p align="center">
31
+ <img src="image/wechat-public.jpg" alt="SCALE Engine WeChat public account" width="220" />
32
+ </p>
33
+
34
+ ## Sponsorship
35
+
36
+ If SCALE Engine saves engineering governance time for your team, or helps move AI-agent work into a verifiable, reviewable, and releasable loop, voluntary sponsorship is welcome. Sponsorship supports maintenance, examples, documentation, test coverage, and community support. It is not a commercial support contract and does not change issue or PR priority.
37
+
38
+ <p align="center">
39
+ <img src="image/wxPay.jpg" alt="Sponsor with WeChat Pay" width="220" />
40
+ &nbsp;&nbsp;
41
+ <img src="image/zfb.jpg" alt="Sponsor with Alipay" width="220" />
42
+ </p>
43
+
44
+ ## What It Solves
21
45
 
22
46
  AI coding becomes hard when agents must behave consistently across real teams and real repositories:
23
47
 
package/README.md CHANGED
@@ -1,32 +1,61 @@
1
1
  <p align="center">
2
- <img src="https://img.shields.io/badge/version-0.21.2-orange?style=flat-square" alt="version" />
2
+ <img src="https://img.shields.io/badge/version-0.23.0-orange?style=flat-square" alt="version" />
3
3
  <img src="https://img.shields.io/badge/platforms-16-blue?style=flat-square" alt="platforms" />
4
4
  <img src="https://img.shields.io/badge/agents-12-blue?style=flat-square" alt="agents" />
5
5
  <img src="https://img.shields.io/badge/workflows-10-green?style=flat-square" alt="workflows" />
6
6
  <img src="https://img.shields.io/badge/detectors-19-red?style=flat-square" alt="detectors" />
7
7
  <img src="https://img.shields.io/badge/tests-verified-brightgreen?style=flat-square" alt="tests" />
8
- <img src="https://img.shields.io/badge/npm-0.21.2-cb3837?style=flat-square&logo=npm" alt="npm" />
9
- </p>
10
-
11
- # SCALE Engine v0.21.2
8
+ <img src="https://img.shields.io/badge/npm-0.23.0-cb3837?style=flat-square&logo=npm" alt="npm" />
9
+ </p>
10
+
11
+ # SCALE Engine v0.23.0
12
12
 
13
13
  SCALE Engine 让 AI Agent äøå†åŖé ā€œč‡Ŗč§‰ā€éµå®ˆå·„ēØ‹č§„čŒƒć€‚å®ƒęŠŠęŽ¢ē“¢ć€č§„åˆ’ć€å®žēŽ°ć€éŖŒčÆć€čÆ„å®”ć€å‘ē‰ˆčæ™äŗ›č¦ę±‚å˜ęˆåÆę‰§č”Œēš„å‘½ä»¤ć€é—Øē¦å’ŒčÆę®ę–‡ä»¶ļ¼Œč®©äŗŗē±»åÆä»„ēœ‹č§ Agent åšäŗ†ä»€ä¹ˆć€č·³čæ‡äŗ†ä»€ä¹ˆć€äøŗä»€ä¹ˆčƒ½äŗ¤ä»˜ęˆ–äøčƒ½äŗ¤ä»˜ć€‚
14
14
 
15
- ęŗē ä»“åŗ“ļ¼šhttps://github.com/hongmaple0820/scale-engine
16
- å›½å†…é•œåƒļ¼šhttps://gitee.com/hongmaple/scale-engine
17
- npm:https://www.npmjs.com/package/@hongmaple0820/scale-engine
18
- čÆ­čØ€ļ¼š[äø­ę–‡](README.md) | [English](README.en.md)
19
-
20
- ## ē¤¾åŒŗäøŽęŽØå¹æ
21
-
22
- ### é“¾ęŽ„
23
-
24
- | 平台 | é“¾ęŽ„ | čÆ“ę˜Ž |
25
- |------|------|------|
26
- | šŸ“¦ **GitHub** | [https://github.com/hongmaple0820/scale-engine](https://github.com/hongmaple0820/scale-engine) | 源码 + Issues + PR |
27
- | šŸ”§ **Gitee** | [https://gitee.com/hongmaple/scale-engine](https://gitee.com/hongmaple/scale-engine) | 国内镜像 |
28
- | šŸ“¦ **npm** | [https://www.npmjs.com/package/@hongmaple0820/scale-engine](https://www.npmjs.com/package/@hongmaple0820/scale-engine) | åŒ…äø‹č½½ |
29
- ## å®ƒč§£å†³ä»€ä¹ˆé—®é¢˜
15
+ ęŗē ä»“åŗ“ļ¼šhttps://github.com/hongmaple0820/scale-engine
16
+ å›½å†…é•œåƒļ¼šhttps://gitee.com/hongmaple/scale-engine
17
+ npm:https://www.npmjs.com/package/@hongmaple0820/scale-engine
18
+ čÆ­čØ€ļ¼š[äø­ę–‡](README.md) | [English](README.en.md)
19
+
20
+ ## å…ˆę€Žä¹ˆå­¦
21
+
22
+ å¦‚ęžœä½ ē¬¬äø€ę¬”ęŽ„č§¦ SCALEļ¼Œäøč¦ä»Žå®Œę•“å‘½ä»¤åˆ—č”Øå¼€å§‹čÆ»ć€‚ęŒ‰čæ™äøŖé”ŗåŗę›“å®¹ę˜“ęŽŒę”ļ¼š
23
+
24
+ | 目标 | 兄口 | ä½ åŗ”čÆ„å­¦ä¼šä»€ä¹ˆ |
25
+ | --- | --- | --- |
26
+ | å…ˆč·‘čµ·ę„ | [3 åˆ†é’Ÿåæ«é€Ÿå¼€å§‹](docs/start/quickstart.md) | 安装 CLIć€åˆå§‹åŒ–ę²»ē†ę–‡ä»¶ć€čæč”Œ preflight |
27
+ | ēœ‹å®Œę•“é—­ēŽÆ | [å®˜ę–¹ Demo Walkthrough](docs/start/agent-governance-demo.md) | ä»»åŠ”äøŠäø‹ę–‡ć€čÆŠę–­ć€TDD态artifact å’ŒéŖŒčÆčÆę®å¦‚ä½•äø²čµ·ę„ |
28
+ | ęŽ„å…„å·²ęœ‰é”¹ē›® | [SCALE å·„ä½œęµå‡ēŗ§ęŒ‡å—](docs/start/workflow-upgrade.md) | `init`态`upgrade check/plan/apply`ć€ęœ¬åœ° `make` åŒ…č£…å…„å£ę€Žä¹ˆē”Ø |
29
+ | é€‰ę‹©ę²»ē†åŒ… | ęœ¬ę–‡ēš„ Governance Pack ē« čŠ‚ | äøåŒé”¹ē›®å½¢ę€åŗ”čÆ„é€‰å“ŖäøŖ pack |
30
+ | ē»“ęŠ¤ęˆ–ę‰©å±• SCALE | [docs/README.md](docs/README.md) | ę–‡ę”£åœ°å›¾ć€å†…éƒØęØ”å—å’Œé•æęœŸē»“ęŠ¤čµ„ę–™ |
31
+
32
+ äø€å„čÆē†č§£ļ¼šSCALE äøę˜Æč®© Agent å¤šå†™ę–‡ę”£ļ¼Œč€Œę˜Æč®©ā€œåšäŗ†ä»€ä¹ˆć€éŖŒčÆäŗ†ä»€ä¹ˆć€ę²”éŖŒčÆä»€ä¹ˆā€åÆčæ½čøŖć€‚
33
+
34
+ ## ē¤¾åŒŗäøŽęŽØå¹æ
35
+
36
+ SCALE Engine ę˜Æäø€äøŖé¢å‘ēœŸå®žå·„ēØ‹äŗ¤ä»˜ēš„ Agent å·„ä½œęµę²»ē†é”¹ē›®ć€‚ę¬¢čæŽé€ščæ‡ęŗē ä»“åŗ“ęäŗ¤ Issue态PRć€åœŗę™Æåé¦ˆå’Œę²»ē†åŒ…ę”¹čæ›å»ŗč®®ļ¼›äø­ę–‡ē”Øęˆ·ä¹ŸåÆä»„å…³ę³Øå…¬ä¼—å·čŽ·å–ę›“ę–°ć€ē¤ŗä¾‹å’Œē¤¾åŒŗå…„å£ć€‚
37
+
38
+ | 平台 | é“¾ęŽ„ | čÆ“ę˜Ž |
39
+ |------|------|------|
40
+ | GitHub | [https://github.com/hongmaple0820/scale-engine](https://github.com/hongmaple0820/scale-engine) | 源码、Issues态PR |
41
+ | Gitee | [https://gitee.com/hongmaple/scale-engine](https://gitee.com/hongmaple/scale-engine) | å›½å†…é•œåƒäøŽåé¦ˆ |
42
+ | npm | [https://www.npmjs.com/package/@hongmaple0820/scale-engine](https://www.npmjs.com/package/@hongmaple0820/scale-engine) | CLI åŒ…äø‹č½½ |
43
+
44
+ <p align="center">
45
+ <img src="image/wechat-public.jpg" alt="SCALE Engine å¾®äæ”å…¬ä¼—å·" width="220" />
46
+ </p>
47
+
48
+ ## čµžåŠ©äøŽę”ÆęŒ
49
+
50
+ å¦‚ęžœ SCALE Engine čŠ‚ēœäŗ†ä½ ēš„å·„ēØ‹ę²»ē†ę—¶é—“ļ¼Œęˆ–åø®åŠ©ä½ ēš„å›¢é˜ŸęŠŠ AI Agent å·„ä½œęµč½åˆ°åÆéŖŒčÆć€åÆå¤ē›˜ć€åÆå‘ē‰ˆēš„é—­ēŽÆé‡Œļ¼Œę¬¢čæŽč‡Ŗę„æčµžåŠ©ć€‚čµžåŠ©ē”ØäŗŽęŒē»­ē»“ęŠ¤ć€ē¤ŗä¾‹é”¹ē›®ć€ę–‡ę”£ć€ęµ‹čÆ•ēŸ©é˜µå’Œē¤¾åŒŗę”ÆęŒļ¼Œäøęž„ęˆå•†äøšę”ÆęŒę‰æčÆŗļ¼Œä¹Ÿäøä¼šę”¹å˜ Issue ꈖ PR ēš„å¤„ē†ä¼˜å…ˆēŗ§ć€‚
51
+
52
+ <p align="center">
53
+ <img src="image/wxPay.jpg" alt="å¾®äæ”čµžåŠ©" width="220" />
54
+ &nbsp;&nbsp;
55
+ <img src="image/zfb.jpg" alt="ę”Æä»˜å®čµžåŠ©" width="220" />
56
+ </p>
57
+
58
+ ## å®ƒč§£å†³ä»€ä¹ˆé—®é¢˜
30
59
 
31
60
  AI ē¼–ē ēœŸę­£éš¾ēš„äøę˜Æā€œå†™ä»£ē ā€ļ¼Œč€Œę˜ÆęŒē»­ēØ³å®šåœ°éµå®ˆå·„ēØ‹ēŗŖå¾‹ļ¼š
32
61
 
@@ -121,9 +150,11 @@ scale skill outdated --dir .
121
150
  - `scale tools outdated` 和 `scale skill outdated` åŖåˆ—å‡ŗę›“ę–°é¢ć€ę„ęŗć€äæ”ä»»ē­‰ēŗ§å’Œå®‰å…Øē­–ē•„ļ¼Œäøåšč‡ŖåŠØå®‰č£…ć€‚
122
151
  - ē¬¬äø‰ę–¹ē¤¾åŒŗę„ęŗé»˜č®¤äŗŗå·„čÆ„å®”ļ¼Œé«˜ęƒé™ę”Œé¢č‡ŖåŠØåŒ–é»˜č®¤é˜»ę–­č‡ŖåŠØå‡ēŗ§ć€‚
123
152
 
124
- čÆ¦ē»†čÆ“ę˜Žč§ [å‡ēŗ§ē®”ē†](docs/UPGRADE_MANAGEMENT.md)怂
125
-
126
- ## Governance Pack
153
+ čÆ¦ē»†čÆ“ę˜Žč§ [å‡ēŗ§ē®”ē†](docs/UPGRADE_MANAGEMENT.md)怂
154
+
155
+ ę–°ē”Øęˆ·å’Œé”¹ē›®ē»“ęŠ¤č€…åÆå…ˆēœ‹ [SCALE workflow upgrade guide](docs/start/workflow-upgrade.md),它把 `scale init --interactive`态`scale upgrade check/plan/apply/rollback` å’Œä»“åŗ“ęœ¬åœ° `make workflow-upgrade-*` å…„å£ę”¾åœØäø€ę”åÆę‰§č”Œč·Æå¾„é‡Œć€‚
156
+
157
+ ## Governance Pack
127
158
 
128
159
  åœØå·²ęœ‰é”¹ē›®äø­å®‰č£…ę²»ē†å·„ä½œęµļ¼š
129
160
 
package/dist/api/cli.js CHANGED
@@ -11,7 +11,9 @@ import { BruteRetryDetector, PrematureDoneDetector, BlameShiftDetector } from '.
11
11
  import { DangerousCommandDetector, SecretLeakDetector, RoleGateDetector, ScopeCreepDetector, BUILT_IN_ROLES } from '../guardrails/advancedDetectors.js';
12
12
  import { SQLiteKnowledgeBase } from '../knowledge/SQLiteKnowledgeBase.js';
13
13
  import { ContextBuilder } from '../context/ContextBuilder.js';
14
+ import { ProjectAnatomy } from '../context/ProjectAnatomy.js';
14
15
  import { buildContextPack, doctorContextBudget, scanContextBudget, writeContextBudgetReport, } from '../context/ContextBudget.js';
16
+ import { CerebrumManager } from '../knowledge/CerebrumManager.js';
15
17
  import { buildCodeGraphContext, createCodeGraphRoiReport, impactCodeGraph, inspectCodeIntelligence, queryCodeGraph, writeCodeIntelligenceConfig, } from '../codegraph/CodeIntelligence.js';
16
18
  import { WorkflowEvalStore, compareWorkflowEvalRuns, renderWorkflowEvalReport, runWorkflowEvalSuite, } from '../eval/WorkflowEval.js';
17
19
  import { FSMAgentBridge } from '../fsm/FSMAgentBridge.js';
@@ -36,6 +38,7 @@ import { ReviewStore } from '../workflow/ReviewStore.js';
36
38
  import { WorkflowEngine } from '../workflow/WorkflowEngine.js';
37
39
  import { resolveVerificationTargets, } from '../workflow/VerificationProfile.js';
38
40
  import { writeGovernanceTemplates } from '../workflow/GovernanceTemplates.js';
41
+ import { getProfile as getConfigProfile, generateConfigForProfile, listProfiles as listConfigProfiles } from '../config/profiles.js';
39
42
  import { computeGovernanceDrift } from '../workflow/GovernanceLock.js';
40
43
  import { applyUpgradePlan, createThirdPartyUpdateReport, createUpgradeCheckReport, createUpgradePlanReport, rollbackLatestUpgrade, writeUpgradePlanHtml, } from '../workflow/UpgradeManager.js';
41
44
  import { createGovernanceRoiReport } from '../governance/GovernanceRoi.js';
@@ -79,6 +82,19 @@ function governanceModeFromScenario(scenario) {
79
82
  return 'minimal';
80
83
  return 'standard';
81
84
  }
85
+ function profileFromScenario(scenario) {
86
+ if (scenario === 'sandbox')
87
+ return 'minimal';
88
+ if (scenario === 'critical')
89
+ return 'advanced';
90
+ return 'standard';
91
+ }
92
+ function writeConfigYaml(projectDir, profileId, projectName, agents) {
93
+ const configPath = join(projectDir, '.scale', 'config.yaml');
94
+ const content = generateConfigForProfile(profileId, { name: projectName, agents });
95
+ writeFileSync(configPath, content, 'utf-8');
96
+ return configPath;
97
+ }
82
98
  function ensureDir(dir) {
83
99
  if (!existsSync(dir))
84
100
  mkdirSync(dir, { recursive: true });
@@ -346,6 +362,60 @@ const gate = defineCommand({
346
362
  subCommands: { 'pre-tool': gatePreTool, 'post-tool': gatePostTool, 'before-stop': gateBeforeStop },
347
363
  });
348
364
  // ============================================================================
365
+ // meta-governance — å…ƒę²»ē†é—Øē¦ (G9-G15)
366
+ // ============================================================================
367
+ const metaGovernance = defineCommand({
368
+ meta: { name: 'meta-governance', description: 'Run meta-governance gates (G9-G15) — check if governance capabilities are actually used' },
369
+ args: {
370
+ 'scale-dir': { type: 'string', default: '.scale' },
371
+ json: { type: 'boolean', default: false, description: 'Output as JSON' },
372
+ },
373
+ async run({ args }) {
374
+ const { eventBus } = getEngine();
375
+ const { GateSystem } = await import('../workflow/gates/GateSystem.js');
376
+ const gateSystem = new GateSystem(eventBus);
377
+ const results = await gateSystem.executeMetaGovernance(args['scale-dir']);
378
+ if (args.json) {
379
+ console.log(JSON.stringify(results, null, 2));
380
+ return;
381
+ }
382
+ const stageNames = {
383
+ G9: 'Knowledge Utilization',
384
+ G10: 'Evolution Effectiveness',
385
+ G11: 'Guardrail Effectiveness',
386
+ G12: 'Workflow Thoroughness',
387
+ G13: 'Multi-Agent Coordination',
388
+ G14: 'Skill Utilization',
389
+ G15: 'Self-Improvement',
390
+ };
391
+ let allPassed = true;
392
+ for (const result of results) {
393
+ const icon = result.passed ? 'āœ…' : 'āŒ';
394
+ const name = stageNames[result.gate] ?? result.gate;
395
+ console.log(`${icon} ${result.gate} ${name}`);
396
+ if (result.evidence) {
397
+ for (const line of result.evidence.split('\n')) {
398
+ console.log(` ${line}`);
399
+ }
400
+ }
401
+ if (!result.passed) {
402
+ allPassed = false;
403
+ for (const blocker of result.blockers) {
404
+ console.log(` ā›” ${blocker}`);
405
+ }
406
+ }
407
+ console.log();
408
+ }
409
+ if (!allPassed) {
410
+ console.log('āŒ Meta-governance check FAILED — some capabilities are not being effectively used');
411
+ process.exit(1);
412
+ }
413
+ else {
414
+ console.log('āœ… All meta-governance gates passed');
415
+ }
416
+ },
417
+ });
418
+ // ============================================================================
349
419
  // artifact CRUD
350
420
  // ============================================================================
351
421
  const create = defineCommand({
@@ -1013,6 +1083,9 @@ const contextDoctor = defineCommand({
1013
1083
  dir: { type: 'string', default: PROJECT_DIR, description: 'Project directory' },
1014
1084
  'max-always': { type: 'string', description: 'Maximum Always-loaded estimated tokens' },
1015
1085
  'max-task': { type: 'string', description: 'Maximum task context estimated tokens' },
1086
+ task: { type: 'string', description: 'Task text for a representative lazy context pack probe' },
1087
+ level: { type: 'string', default: 'M', description: 'Task level for the context pack probe' },
1088
+ files: { type: 'string', description: 'Comma-separated scoped files for the context pack probe' },
1016
1089
  json: { type: 'boolean', default: false },
1017
1090
  },
1018
1091
  run({ args }) {
@@ -1023,6 +1096,9 @@ const contextDoctor = defineCommand({
1023
1096
  scaleDir,
1024
1097
  maxAlwaysTokens: parsePositiveIntArg(args['max-always'], '--max-always'),
1025
1098
  maxTaskTokens: parsePositiveIntArg(args['max-task'], '--max-task'),
1099
+ task: args.task ? String(args.task) : undefined,
1100
+ level: String(args.level ?? 'M'),
1101
+ files: parseCommaList(args.files),
1026
1102
  });
1027
1103
  if (args.json) {
1028
1104
  console.log(JSON.stringify(report, null, 2));
@@ -1038,9 +1114,55 @@ const contextDoctor = defineCommand({
1038
1114
  process.exitCode = 1;
1039
1115
  },
1040
1116
  });
1117
+ const contextAnatomy = defineCommand({
1118
+ meta: { name: 'anatomy', description: 'Scan the project and generate .scale/anatomy.md for file-map context' },
1119
+ args: {
1120
+ dir: { type: 'string', default: PROJECT_DIR, description: 'Project directory' },
1121
+ 'max-files': { type: 'string', description: 'Maximum files to include; defaults to 500' },
1122
+ exclude: { type: 'string', description: 'Comma-separated directory names to exclude' },
1123
+ write: { type: 'boolean', default: false, description: 'Write .scale/anatomy.md' },
1124
+ json: { type: 'boolean', default: false },
1125
+ },
1126
+ run({ args }) {
1127
+ const projectDir = resolve(String(args.dir ?? PROJECT_DIR));
1128
+ const scaleDir = resolveScaleDirForProject(projectDir);
1129
+ const maxFiles = parsePositiveIntArg(args['max-files'], '--max-files');
1130
+ const excludePatterns = parseCommaList(args.exclude);
1131
+ const anatomy = new ProjectAnatomy();
1132
+ const sections = anatomy.scan(projectDir, {
1133
+ maxFiles,
1134
+ excludePatterns: excludePatterns.length > 0 ? excludePatterns : undefined,
1135
+ });
1136
+ const content = anatomy.serialize(sections);
1137
+ const summary = [...sections.values()].reduce((acc, entries) => {
1138
+ acc.files += entries.length;
1139
+ acc.tokens += entries.reduce((sum, entry) => sum + entry.tokens, 0);
1140
+ return acc;
1141
+ }, { files: 0, tokens: 0 });
1142
+ const outputPath = join(scaleDir, 'anatomy.md');
1143
+ if (isTruthyFlag(args.write)) {
1144
+ ensureDir(scaleDir);
1145
+ writeFileSync(outputPath, content, 'utf-8');
1146
+ }
1147
+ if (args.json) {
1148
+ console.log(JSON.stringify({
1149
+ ok: true,
1150
+ projectDir,
1151
+ outputPath: isTruthyFlag(args.write) ? outputPath : undefined,
1152
+ summary,
1153
+ }, null, 2));
1154
+ return;
1155
+ }
1156
+ console.log('SCALE Project Anatomy');
1157
+ console.log(` Files: ${summary.files}`);
1158
+ console.log(` Estimated tokens: ${summary.tokens}`);
1159
+ if (isTruthyFlag(args.write))
1160
+ console.log(` Wrote: ${outputPath}`);
1161
+ },
1162
+ });
1041
1163
  const context = defineCommand({
1042
1164
  meta: { name: 'context', description: 'Context assembly' },
1043
- subCommands: { build: contextBuild, status: contextStatus, inject: contextInject, glossary: contextGlossary, init: contextInit, grill: contextGrill, budget: contextBudget, pack: contextPack, doctor: contextDoctor },
1165
+ subCommands: { build: contextBuild, status: contextStatus, inject: contextInject, glossary: contextGlossary, init: contextInit, grill: contextGrill, budget: contextBudget, pack: contextPack, doctor: contextDoctor, anatomy: contextAnatomy },
1044
1166
  });
1045
1167
  // ============================================================================
1046
1168
  // codegraph command - Adapter-first code intelligence
@@ -2230,6 +2352,7 @@ const init = defineCommand({
2230
2352
  },
2231
2353
  quick: { type: 'boolean', default: false, description: 'Quick start with auto-detection' },
2232
2354
  interactive: { type: 'boolean', default: false, description: 'Interactive configuration mode with prompts' },
2355
+ profile: { type: 'string', default: '', description: 'Configuration profile (minimal/standard/advanced). Auto-mapped from scenario if not specified' },
2233
2356
  'coverage-threshold': { type: 'string', default: '80', description: 'Coverage threshold (default 80%)' },
2234
2357
  'retry-threshold': { type: 'string', default: '3', description: 'Brute retry threshold (default 3)' },
2235
2358
  'block-severity': { type: 'string', default: 'CRITICAL', description: 'Block severity level (CRITICAL/HIGH/MEDIUM)' },
@@ -2292,7 +2415,11 @@ const init = defineCommand({
2292
2415
  });
2293
2416
  result.created.push(...governance.created);
2294
2417
  result.skipped.push(...governance.skipped);
2295
- console.log(`\nāœ… SCALE Engine initialized for ${agentType} (interactive mode)`);
2418
+ // Generate config.yaml from profile
2419
+ const profileId = args.profile || profileFromScenario(scenarioMode);
2420
+ const configPath = writeConfigYaml(args.dir, profileId, projectName, [agentType]);
2421
+ result.created.push(configPath);
2422
+ console.log(`\nāœ… SCALE Engine initialized for ${agentType} (interactive mode, profile: ${profileId})`);
2296
2423
  console.log(`\nšŸ“ Created:`);
2297
2424
  for (const f of result.created)
2298
2425
  console.log(` + ${f}`);
@@ -2305,8 +2432,10 @@ const init = defineCommand({
2305
2432
  console.log(` Settings: ${result.settingsPath}`);
2306
2433
  console.log(` Knowledge: ${result.knowledgeDocPath}`);
2307
2434
  console.log(` Thresholds: ${thresholdsPath}`);
2435
+ console.log(` Config: ${configPath}`);
2308
2436
  console.log(` Data dir: ${result.scaleDir}`);
2309
2437
  console.log(` Scenario: ${scenarioMode}`);
2438
+ console.log(` Profile: ${profileId}`);
2310
2439
  console.log(`\nšŸ“‹ Next steps:`);
2311
2440
  for (const step of governanceNextSteps())
2312
2441
  console.log(` → ${step}`);
@@ -2315,6 +2444,14 @@ const init = defineCommand({
2315
2444
  // One-click quick start mode
2316
2445
  if (!args.agent) {
2317
2446
  const qsResult = await quickStart(args.dir, { governancePack: args['governance-pack'] });
2447
+ // Generate config.yaml from profile
2448
+ if (qsResult.success) {
2449
+ const profileId = args.profile || profileFromScenario(args.scenario);
2450
+ const projectName = args.dir.split(/[/\\]/).pop() || 'Project';
2451
+ const detectedAgent = qsResult.platform ? [qsResult.platform] : [];
2452
+ const configPath = writeConfigYaml(args.dir, profileId, projectName, detectedAgent);
2453
+ qsResult.created.push(configPath);
2454
+ }
2318
2455
  if (args.json) {
2319
2456
  const detection = qsResult.success ? undefined : detectPlatform(args.dir);
2320
2457
  console.log(JSON.stringify({
@@ -2369,15 +2506,21 @@ const init = defineCommand({
2369
2506
  });
2370
2507
  result.created.push(...governance.created);
2371
2508
  result.skipped.push(...governance.skipped);
2509
+ // Generate config.yaml from profile
2510
+ const profileId = args.profile || profileFromScenario(args.scenario);
2511
+ const configPath = writeConfigYaml(args.dir, profileId, projectName, [args.agent]);
2512
+ result.created.push(configPath);
2372
2513
  if (args.json) {
2373
2514
  console.log(JSON.stringify({
2374
2515
  ok: true,
2375
2516
  mode: args.quick ? 'quick-agent' : 'manual',
2376
2517
  agent: args.agent,
2377
2518
  scenario: args.scenario,
2519
+ profile: profileId,
2378
2520
  governancePack: args['governance-pack'],
2379
2521
  settingsPath: result.settingsPath,
2380
2522
  knowledgeDocPath: result.knowledgeDocPath,
2523
+ configPath,
2381
2524
  scaleDir: result.scaleDir,
2382
2525
  created: result.created,
2383
2526
  skipped: result.skipped,
@@ -2385,7 +2528,7 @@ const init = defineCommand({
2385
2528
  }, null, 2));
2386
2529
  return;
2387
2530
  }
2388
- console.log(`\nāœ… SCALE Engine initialized for ${args.agent} (scenario: ${args.scenario})`);
2531
+ console.log(`\nāœ… SCALE Engine initialized for ${args.agent} (scenario: ${args.scenario}, profile: ${profileId})`);
2389
2532
  console.log(`\nšŸ“ Created:`);
2390
2533
  for (const f of result.created)
2391
2534
  console.log(` + ${f}`);
@@ -2396,6 +2539,7 @@ const init = defineCommand({
2396
2539
  }
2397
2540
  console.log(`\nšŸ”§ Settings: ${result.settingsPath}`);
2398
2541
  console.log(`\nšŸ“– Knowledge: ${result.knowledgeDocPath}`);
2542
+ console.log(`\nšŸ“„ Config: ${configPath}`);
2399
2543
  console.log(`\nšŸ“‚ Data dir: ${result.scaleDir}`);
2400
2544
  console.log(`\nšŸ“‹ Next steps:`);
2401
2545
  for (const step of governanceNextSteps())
@@ -2403,8 +2547,70 @@ const init = defineCommand({
2403
2547
  },
2404
2548
  });
2405
2549
  // ============================================================================
2406
- // governance command — Generated governance asset tooling
2550
+ // config command — Configuration profile management
2407
2551
  // ============================================================================
2552
+ const configProfile = defineCommand({
2553
+ meta: { name: 'profile', description: 'View or switch configuration profile' },
2554
+ args: {
2555
+ set: { type: 'string', default: '', description: 'Switch to profile (minimal/standard/advanced)' },
2556
+ list: { type: 'boolean', default: false, description: 'List all available profiles' },
2557
+ json: { type: 'boolean', default: false, description: 'Output as JSON' },
2558
+ },
2559
+ async run({ args }) {
2560
+ if (args.list) {
2561
+ const profiles = listConfigProfiles();
2562
+ if (args.json) {
2563
+ console.log(JSON.stringify(profiles, null, 2));
2564
+ return;
2565
+ }
2566
+ console.log('\nAvailable profiles:\n');
2567
+ for (const p of profiles) {
2568
+ console.log(` ${p.id.padEnd(12)} ${p.name} — ${p.description}`);
2569
+ }
2570
+ console.log(`\nUse: scale config profile --set <id>`);
2571
+ return;
2572
+ }
2573
+ if (args.set) {
2574
+ const profile = getConfigProfile(args.set);
2575
+ if (profile.id !== args.set) {
2576
+ console.log(`\nāš ļø Profile "${args.set}" not found. Available: minimal, standard, advanced`);
2577
+ return;
2578
+ }
2579
+ // Update config.yaml
2580
+ const configPath = join('.scale', 'config.yaml');
2581
+ const projectName = process.cwd().split(/[/\\]/).pop() || 'Project';
2582
+ const content = generateConfigForProfile(args.set, { name: projectName });
2583
+ ensureDir('.scale');
2584
+ writeFileSync(configPath, content, 'utf-8');
2585
+ console.log(`\nāœ… Profile switched to: ${profile.name}`);
2586
+ console.log(` ${profile.description}`);
2587
+ console.log(`\nšŸ“„ Config updated: ${configPath}`);
2588
+ return;
2589
+ }
2590
+ // Show current profile
2591
+ const configPath = join('.scale', 'config.yaml');
2592
+ if (!existsSync(configPath)) {
2593
+ console.log('\nāš ļø No config.yaml found. Run: scale init');
2594
+ return;
2595
+ }
2596
+ const content = readFileSync(configPath, 'utf-8');
2597
+ const match = content.match(/^profile:\s*(.+)$/m);
2598
+ const currentProfile = match?.[1]?.trim() || 'standard';
2599
+ const profile = getConfigProfile(currentProfile);
2600
+ if (args.json) {
2601
+ console.log(JSON.stringify({ profile: profile.id, name: profile.name, description: profile.description, sections: profile.sections }, null, 2));
2602
+ return;
2603
+ }
2604
+ console.log(`\nCurrent profile: ${profile.name} (${profile.id})`);
2605
+ console.log(` ${profile.description}`);
2606
+ console.log(`\nSections: ${profile.sections.join(', ')}`);
2607
+ console.log(`\nUse: scale config profile --set <id> to switch`);
2608
+ },
2609
+ });
2610
+ const config = defineCommand({
2611
+ meta: { name: 'config', description: 'Configuration management' },
2612
+ subCommands: { profile: configProfile },
2613
+ });
2408
2614
  const governanceDiff = defineCommand({
2409
2615
  meta: { name: 'diff', description: 'Check generated governance files for drift' },
2410
2616
  args: {
@@ -3612,6 +3818,75 @@ const memoryDoctor = defineCommand({
3612
3818
  process.exitCode = 1;
3613
3819
  },
3614
3820
  });
3821
+ const memoryCerebrum = defineCommand({
3822
+ meta: { name: 'cerebrum', description: 'Maintain .scale/cerebrum.md do-not-repeat rules and preferences' },
3823
+ args: {
3824
+ type: { type: 'string', description: 'Optional entry type: preference or do-not-repeat' },
3825
+ pattern: { type: 'string', description: 'Pattern for do-not-repeat entries' },
3826
+ description: { type: 'string', description: 'Entry description or preference text' },
3827
+ tags: { type: 'string', description: 'Comma-separated tags for preferences' },
3828
+ write: { type: 'boolean', default: false, description: 'Write .scale/cerebrum.md' },
3829
+ json: { type: 'boolean', default: false },
3830
+ },
3831
+ async run({ args }) {
3832
+ const { kb } = getEngine();
3833
+ const manager = new CerebrumManager(kb);
3834
+ const type = args.type ? String(args.type).toLowerCase() : '';
3835
+ let created;
3836
+ if (type) {
3837
+ if (type === 'do-not-repeat' || type === 'do_not_repeat' || type === 'dnr') {
3838
+ const pattern = String(args.pattern ?? '').trim();
3839
+ const description = String(args.description ?? '').trim();
3840
+ if (!pattern || !description) {
3841
+ console.error('memory cerebrum --type do-not-repeat requires --pattern and --description.');
3842
+ process.exit(1);
3843
+ return;
3844
+ }
3845
+ created = await manager.addDoNotRepeat(pattern, description);
3846
+ }
3847
+ else if (type === 'preference' || type === 'pref') {
3848
+ const description = String(args.description ?? args.pattern ?? '').trim();
3849
+ if (!description) {
3850
+ console.error('memory cerebrum --type preference requires --description.');
3851
+ process.exit(1);
3852
+ return;
3853
+ }
3854
+ created = await manager.addPreference(description, parseCommaList(args.tags));
3855
+ }
3856
+ else {
3857
+ console.error('memory cerebrum --type must be preference or do-not-repeat.');
3858
+ process.exit(1);
3859
+ return;
3860
+ }
3861
+ }
3862
+ const entries = await manager.loadAll();
3863
+ const outputPath = join(SCALE_DIR, 'cerebrum.md');
3864
+ const shouldWrite = isTruthyFlag(args.write) || Boolean(created);
3865
+ if (shouldWrite) {
3866
+ ensureDir(SCALE_DIR);
3867
+ writeFileSync(outputPath, manager.toMarkdown(), 'utf-8');
3868
+ }
3869
+ const summary = {
3870
+ total: entries.length,
3871
+ doNotRepeat: entries.filter(entry => entry.type === 'do_not_repeat').length,
3872
+ preferences: entries.filter(entry => entry.type === 'preference').length,
3873
+ };
3874
+ if (args.json) {
3875
+ console.log(JSON.stringify({
3876
+ ok: true,
3877
+ outputPath: shouldWrite ? outputPath : undefined,
3878
+ created,
3879
+ summary,
3880
+ }, null, 2));
3881
+ return;
3882
+ }
3883
+ console.log('SCALE Cerebrum');
3884
+ console.log(` Do-not-repeat: ${summary.doNotRepeat}`);
3885
+ console.log(` Preferences: ${summary.preferences}`);
3886
+ if (shouldWrite)
3887
+ console.log(` Wrote: ${outputPath}`);
3888
+ },
3889
+ });
3615
3890
  const memorySettle = defineCommand({
3616
3891
  meta: { name: 'settle', description: 'Settle runtime evidence into a reviewable memory learning candidate' },
3617
3892
  args: {
@@ -3876,6 +4151,7 @@ const memory = defineCommand({
3876
4151
  subCommands: {
3877
4152
  pack: memoryPack,
3878
4153
  doctor: memoryDoctor,
4154
+ cerebrum: memoryCerebrum,
3879
4155
  settle: memorySettle,
3880
4156
  ingest: memoryIngest,
3881
4157
  query: memoryQuery,
@@ -4755,6 +5031,7 @@ const team = defineCommand({
4755
5031
  // Phase-Aligned Commands (v0.10.1) - agent-skills style
4756
5032
  // ============================================================================
4757
5033
  import * as phaseCommands from '../cli/phaseCommands.js';
5034
+ import { runCommand } from '../cli/runCommand.js';
4758
5035
  import * as liteCommands from '../cli/liteCommands.js';
4759
5036
  import * as vibeCommands from '../cli/vibeCommands.js';
4760
5037
  const main = defineCommand({
@@ -4773,11 +5050,13 @@ const main = defineCommand({
4773
5050
  verify: phaseCommands.phaseVerify,
4774
5051
  review: phaseCommands.phaseReview,
4775
5052
  ship: phaseCommands.phaseShip,
5053
+ run: runCommand,
4776
5054
  // Original commands (preserved)
4777
5055
  init,
4778
5056
  doctor,
4779
5057
  session,
4780
5058
  gate,
5059
+ 'meta-governance': metaGovernance,
4781
5060
  create,
4782
5061
  list,
4783
5062
  show,
@@ -4814,6 +5093,7 @@ const main = defineCommand({
4814
5093
  team,
4815
5094
  'create-prd': createPRD,
4816
5095
  'out-of-scope': outOfScope,
5096
+ config,
4817
5097
  },
4818
5098
  });
4819
5099
  runMain(main);