chati-dev 4.0.10 → 4.1.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 (107) hide show
  1. package/README.md +5 -0
  2. package/bin/chati.js +23 -2
  3. package/framework/agents/build/dev.md +43 -10
  4. package/framework/agents/discover/brief.md +38 -8
  5. package/framework/agents/discover/brownfield-wu.md +44 -3
  6. package/framework/agents/discover/greenfield-wu.md +14 -0
  7. package/framework/agents/plan/architect.md +6 -0
  8. package/framework/agents/plan/detail.md +25 -0
  9. package/framework/agents/plan/tasks.md +29 -1
  10. package/framework/agents/plan/ux-brand-architect.md +215 -0
  11. package/framework/agents/plan/ux-component-engineer.md +289 -0
  12. package/framework/agents/plan/ux-researcher.md +166 -0
  13. package/framework/agents/plan/ux.md +126 -1008
  14. package/framework/agents/quality/qa-implementation.md +121 -22
  15. package/framework/agents/quality/qa-planning.md +18 -0
  16. package/framework/config.yaml +15 -4
  17. package/framework/constitution.md +8 -2
  18. package/framework/context/root.md +1 -1
  19. package/framework/data/entity-registry.yaml +59 -3
  20. package/framework/hooks/constitution-guard.js +67 -1
  21. package/framework/hooks/license-guard.js +4 -4
  22. package/framework/hooks/model-governance.js +2 -1
  23. package/framework/hooks/prism-engine.js +74 -6
  24. package/framework/hooks/read-protection.js +1 -1
  25. package/framework/hooks/session-digest.js +159 -7
  26. package/framework/hooks/settings.json +16 -4
  27. package/framework/hooks/style-guard.js +134 -0
  28. package/framework/hooks/undercover-guard.js +220 -0
  29. package/framework/intelligence/context-engine.md +21 -0
  30. package/framework/intelligence/hooks-performance.md +54 -0
  31. package/framework/intelligence/memory-layer.md +47 -0
  32. package/framework/migrations/v4.0-to-v4.1.yaml +165 -0
  33. package/framework/orchestrator/chati.md +327 -1067
  34. package/framework/templates/brandbook-html-tmpl.md +107 -0
  35. package/framework/templates/session-memory-tmpl.yaml +68 -0
  36. package/package.json +1 -1
  37. package/src/autonomy/build-state.js +1 -1
  38. package/src/autonomy/worktree-manager.js +13 -13
  39. package/src/config/agent-customizer.js +1 -1
  40. package/src/config/gemini-hooks-generator.js +6 -6
  41. package/src/config/ide-configs.js +1 -1
  42. package/src/context/bracket-tracker.js +25 -4
  43. package/src/context/engine.js +37 -7
  44. package/src/context/formatter.js +45 -1
  45. package/src/context/index.js +3 -3
  46. package/src/dashboard/data-reader.js +7 -7
  47. package/src/decision/engine.js +2 -2
  48. package/src/decision/registry-healer.js +1 -1
  49. package/src/decision/registry-updater.js +2 -2
  50. package/src/extensions/loader.js +1 -1
  51. package/src/gates/g1-planning-complete.js +1 -1
  52. package/src/gates/g2-qa-planning.js +1 -1
  53. package/src/gates/g3-implementation.js +4 -4
  54. package/src/gates/g4-qa-implementation.js +2 -2
  55. package/src/health/auto-fix.js +3 -3
  56. package/src/health/engine.js +2 -2
  57. package/src/installer/brownfield-upgrader.js +3 -3
  58. package/src/installer/manifest.js +1 -1
  59. package/src/installer/transaction.js +1 -1
  60. package/src/installer/validator.js +2 -2
  61. package/src/intelligence/decision-engine.js +1 -1
  62. package/src/intelligence/memory-manager.js +1 -1
  63. package/src/intelligence/registry-manager.js +2 -2
  64. package/src/intelligence/timeline.js +1 -1
  65. package/src/license/client.js +20 -2
  66. package/src/license/commands.js +7 -7
  67. package/src/memory/agent-memory.js +3 -3
  68. package/src/memory/daily-digest.js +170 -0
  69. package/src/memory/dream.js +254 -0
  70. package/src/memory/gotchas.js +2 -2
  71. package/src/memory/index.js +18 -0
  72. package/src/memory/magic-docs.js +98 -0
  73. package/src/memory/memory-extractor.js +163 -0
  74. package/src/memory/session-digest.js +144 -6
  75. package/src/merger/yaml-merger.js +1 -1
  76. package/src/orchestrator/cli.js +980 -0
  77. package/src/orchestrator/handoff-engine.js +25 -4
  78. package/src/orchestrator/index.js +9 -0
  79. package/src/orchestrator/session-manager.js +1 -1
  80. package/src/preview/detector.js +3 -3
  81. package/src/preview/launcher.js +2 -2
  82. package/src/quality/metrics-collector.js +1 -1
  83. package/src/quality/test-runner.js +2 -4
  84. package/src/scanning/density-scanner.js +51 -0
  85. package/src/scanning/env-scanner.js +97 -0
  86. package/src/scanning/index.js +7 -0
  87. package/src/scanning/leakage-scanner.js +54 -0
  88. package/src/scanning/placeholder-scanner.js +40 -0
  89. package/src/scanning/security-scanner.js +94 -0
  90. package/src/security/bash-security.js +335 -0
  91. package/src/security/index.js +9 -0
  92. package/src/telemetry/config.js +3 -5
  93. package/src/telemetry/sender.js +19 -17
  94. package/src/terminal/cli-registry.js +1 -1
  95. package/src/terminal/cost-tracker.js +1 -2
  96. package/src/terminal/prompt-builder.js +11 -27
  97. package/src/terminal/rate-limiter.js +1 -2
  98. package/src/terminal/run-agent.js +3 -3
  99. package/src/terminal/spawner.js +41 -4
  100. package/src/upgrade/checker.js +2 -2
  101. package/src/upgrade/migrator.js +1 -1
  102. package/src/utils/config-parser.js +1 -1
  103. package/src/utils/file-lock.js +3 -3
  104. package/src/utils/provider-limits.js +35 -4
  105. package/src/wizard/i18n.js +2 -2
  106. package/src/wizard/index.js +2 -1
  107. package/src/wizard/questions.js +4 -2
@@ -78,9 +78,30 @@ Categories:
78
78
  9. Prototype Pollution
79
79
  10. Insecure Configuration
80
80
 
81
+ Language-Specific Patterns (scan for these exact patterns):
82
+
83
+ JavaScript/TypeScript:
84
+ - eval(), new Function(), setTimeout/setInterval with string arg: RCE risk
85
+ - innerHTML, outerHTML, document.write(): XSS risk
86
+ - dangerouslySetInnerHTML (React): XSS risk
87
+ - getElementById/querySelector without null check: runtime crash risk
88
+ - JSON.parse without try/catch: crash on malformed input
89
+
90
+ Python:
91
+ - eval(), exec(), compile(): RCE risk
92
+ - subprocess with shell=True: command injection
93
+ - pickle.loads from untrusted source: deserialization attack
94
+ - format strings with user input: injection
95
+
96
+ For ALL languages:
97
+ - Hardcoded secrets matching /api[_-]?key|secret|password|token.*[:=]\s*["'][^"']{8,}/i
98
+ - SQL with string interpolation (template literals, f-strings in queries)
99
+ - Missing input validation (direct req.body/req.params without validation)
100
+ - Insecure CORS (Access-Control-Allow-Origin: *)
101
+
81
102
  Severity Classification:
82
- - Critical: Immediate exploitation risk
83
- - High: Exploitable with some effort
103
+ - Critical: Immediate exploitation risk (eval, innerHTML, shell=True, hardcoded secrets)
104
+ - High: Exploitable with effort (null DOM, missing validation, insecure CORS)
84
105
  - Medium: Potential risk, lower probability
85
106
  - Low: Best practice improvement
86
107
 
@@ -101,6 +122,12 @@ Review code for:
101
122
  6. Code duplication detection
102
123
  7. Performance anti-patterns
103
124
  8. Accessibility compliance
125
+ 9. Client-side analysis (if project has frontend):
126
+ - DOM queries (getElementById, querySelector) have null checks
127
+ - Event listeners are cleaned up (removeEventListener on unmount)
128
+ - No memory leaks (intervals/timeouts cleared, subscriptions unsubscribed)
129
+ - Form validation exists on client side (not just server)
130
+ - Loading/error states handled (not just happy path)
104
131
 
105
132
  If CodeRabbit MCP available:
106
133
  - Run CodeRabbit review
@@ -120,23 +147,53 @@ For each completed task:
120
147
  Flag unverified criteria for manual review
121
148
  ```
122
149
 
123
- ### Phase 5: Adversarial Review (Mandatory)
150
+ ### Phase 4b: Evidence Validation (by change type)
151
+ ```
152
+ Validate that appropriate evidence exists for the type of change:
153
+
154
+ | Change Type | Required Evidence |
155
+ |-------------|-------------------|
156
+ | Bug fix | Before/after reproduction, root cause documented, regression test added |
157
+ | New feature | All acceptance criteria mapped to implementation, new tests cover feature |
158
+ | Refactor | No behavior change proof (same test results before/after), no new features |
159
+ | Performance | Benchmark data (before/after measurements with methodology) |
160
+ | Security fix | Vulnerability scan results, exploit reproduction steps |
161
+ | UI change | Visual comparison (screenshots or description of visual diff) |
162
+
163
+ If evidence is missing for the change type, flag as WARNING.
124
164
  ```
125
- RULE: Every QA pass MUST identify minimum 5 findings.
126
- Zero findings = suspiciously clean -> mandatory re-review.
127
165
 
128
- Process:
129
- 1. After Phases 1-4, count total findings across all categories
130
- 2. IF findings < 5:
131
- - Log: "Adversarial trigger: only {N} findings detected"
132
- - Re-run Phases 2-4 with DEEPER analysis:
133
- * Lower severity threshold (include INFO-level observations)
134
- * Check for implicit issues (poor naming, missing edge cases, weak error messages)
135
- * Look for "things that work but could fail under load/scale"
136
- - Findings now include: improvements, suggestions, best-practice deviations
137
- 3. IF findings still < 5 after deep re-review:
138
- - Document explicitly WHY the code is genuinely clean
139
- - This documentation itself counts as a finding (type: attestation)
166
+ ### Phase 5: Triple Review Protocol (Mandatory)
167
+ ```
168
+ Execute 3 review passes INDEPENDENTLY. Each pass has a different scope
169
+ and produces its own findings. Findings are merged at the end.
170
+
171
+ Pass 1 -- Shadow Review (zero-context adversarial):
172
+ Analyze ONLY the diff/changes. Do NOT read project context, architecture,
173
+ or acceptance criteria. Judge the code purely on its own merits:
174
+ - Does the code make sense in isolation?
175
+ - Are there obvious bugs, missing error handling, or logic flaws?
176
+ - Would a senior developer reject this in a PR review?
177
+ - Are there hardcoded values, magic numbers, or unclear naming?
178
+
179
+ Pass 2 -- Sentinel Review (edge case enumeration):
180
+ With full project access, enumerate ALL execution paths:
181
+ - What happens with null/undefined/empty inputs?
182
+ - What happens under concurrent access?
183
+ - What happens at scale (10x data, 100x users)?
184
+ - What happens when external services fail (timeout, 500, unreachable)?
185
+ - What happens with malformed/malicious input?
186
+ - Are there resource leaks (unclosed connections, streams, file handles)?
187
+
188
+ Pass 3 -- Compliance Review (spec alignment):
189
+ With spec + acceptance criteria + architecture:
190
+ - Does every Given-When-Then criterion have a matching implementation?
191
+ - Does the code follow architecture patterns from architecture.md?
192
+ - Are Design System tokens used (no hardcoded visual values)?
193
+ - Does the API contract match the spec?
194
+ - Are all component states implemented (not just happy path)?
195
+
196
+ After all 3 passes, execute the 5 Structural Checks:
140
197
 
141
198
  Structural Checks (5 mandatory):
142
199
  1. DEPENDENCY AUDIT: Scan for unused imports, circular dependencies,
@@ -154,8 +211,12 @@ Structural Checks (5 mandatory):
154
211
  prototype pollution, ReDoS (regex denial of service), path traversal,
155
212
  command injection via string interpolation, timing attacks.
156
213
 
214
+ Each check produces a classified finding (ERROR, WARNING, SUGGESTION, or ATTESTATION).
215
+ ATTESTATION documents WHY the check passed and what was verified. It is a quality
216
+ record proving thoroughness, not a padding finding.
217
+
157
218
  Devil's Advocate Pass:
158
- After initial review concludes APPROVED:
219
+ After the Triple Review concludes:
159
220
  1. Assume the opposite: "This code has a hidden flaw"
160
221
  2. Spend one focused pass actively seeking:
161
222
  - Race conditions, memory leaks, unhandled edge cases
@@ -172,6 +233,41 @@ Findings Classification:
172
233
  - ATTESTATION: Explicit documentation of why something is clean
173
234
  ```
174
235
 
236
+ ### Phase 5b: Cross-File Consistency (Mandatory)
237
+ ```
238
+ Check for inconsistencies ACROSS files (not just within code):
239
+
240
+ 1. ENV SYNC: Compare .env.example against all env references in code
241
+ (process.env.X, import.meta.env.X). Flag missing or extra vars.
242
+ 2. README ACCURACY: Verify that features described in README.md actually
243
+ exist in the codebase. Flag phantom features (documented but not implemented).
244
+ 3. API CONTRACT: Compare error response format across ALL endpoints.
245
+ Flag inconsistent error shapes ({error: ...} vs {message: ...}).
246
+ 4. CONFIG SYNC: Verify that config files (package.json scripts, tsconfig paths,
247
+ etc.) match actual file structure.
248
+ 5. DEPENDENCY AUDIT: Check for unused dependencies in package.json and
249
+ missing dependencies (imported but not in package.json).
250
+ 6. DOCUMENTATION SYNC: If API docs exist, verify endpoints match actual routes.
251
+ ```
252
+
253
+ ### Phase 5c: Causation Verification (for bug fixes)
254
+ ```
255
+ If the implementation includes a bug fix, verify causation:
256
+
257
+ 1. ROOT CAUSE: Is the fix addressing the root cause or just a symptom?
258
+ Ask: "If we remove this fix, does the original bug return?"
259
+ 2. PLACEBO CHECK: Does the fix actually change the execution path
260
+ that causes the bug? Or is it a cosmetic change nearby?
261
+ 3. COMPLETENESS: Does the fix handle ALL variations of the bug?
262
+ (different inputs, different timing, different environments)
263
+ 4. REGRESSION: Could this fix break existing functionality?
264
+ Check: are there tests that cover the changed behavior?
265
+ 5. ENVIRONMENT: Will this fix work in production? Or only in dev?
266
+ Check: hardcoded URLs, localhost references, debug flags.
267
+
268
+ If not a bug fix, skip this phase and document: "Not a bug fix -- causation verification N/A."
269
+ ```
270
+
175
271
  ### Phase 6: Score & Decide
176
272
  ```
177
273
  Calculate overall quality score:
@@ -382,13 +478,16 @@ Criteria (binary pass/fail):
382
478
  4. Zero High security vulnerabilities
383
479
  5. Code review completed (architecture adherence, patterns, error handling)
384
480
  6. All acceptance criteria from tasks verified
385
- 7. Adversarial review completed with minimum 5 findings
481
+ 7. Adversarial review completed: all 5 structural checks executed with classified outcomes
386
482
  8. Devil's Advocate pass documented
387
483
  9. Correction loops executed for all issues (or escalated with justification)
388
484
  10. No skipped tests without documented reason
485
+ 11. Triple Review Protocol completed (Shadow + Sentinel + Compliance passes)
486
+ 12. Cross-file consistency checks completed (ENV, README, API, Config, Deps, Docs)
487
+ 13. Evidence validation completed for change type (bug/feature/refactor/performance/security)
389
488
 
390
489
  Score = criteria met / total criteria
391
- Threshold: >= 95% (10/10 minimum, no criteria may fail)
490
+ Threshold: >= 95% (12/13 minimum)
392
491
  ```
393
492
 
394
493
  ---
@@ -410,7 +509,7 @@ Threshold: >= 95% (10/10 minimum, no criteria may fail)
410
509
  | `sast-scan` | SAST Security Scan | Scan codebase for security vulnerabilities across 10 categories | After run-tests |
411
510
  | `code-review` | Code Review | Review code for architecture adherence, patterns, error handling, Design System tokens | After sast-scan |
412
511
  | `verify-criteria` | Verify Acceptance Criteria | Check each task's Given-When-Then criteria against implementation | After code-review |
413
- | `adversarial` | Adversarial Review | Run mandatory adversarial review with 5 structural checks and Devil's Advocate pass (minimum 5 findings) | After verify-criteria |
512
+ | `adversarial` | Adversarial Review | Run 5 mandatory structural checks + Devil's Advocate pass. Each check produces classified finding (ERROR/WARNING/SUGGESTION/ATTESTATION) | After verify-criteria |
414
513
  | `score-decide` | Score and Decide | Calculate weighted quality score and issue APPROVED or NEEDS CORRECTION verdict | After adversarial |
415
514
 
416
515
  ---
@@ -453,7 +552,7 @@ Beyond self-validation (Protocol 5.1), the QA-Implementation agent enforces:
453
552
  2. **Full Acceptance Coverage**: Every task's Given-When-Then criteria must be verified against the implementation — unverified criteria block approval
454
553
  3. **Pattern Adherence**: Code must follow architecture patterns defined in the Architecture artifact — deviations must be justified
455
554
  4. **Token Enforcement**: Design System tokens must be used — hardcoded visual values (colors, spacing, typography) reduce the score
456
- 5. **Adversarial Completeness**: The adversarial review must produce minimum 5 findings (including 5 structural checks) zero findings trigger mandatory re-review
555
+ 5. **Adversarial Completeness**: All 5 structural checks must be executed, each producing a classified finding (ERROR, WARNING, SUGGESTION, or ATTESTATION). Attestations document verified quality, not filler.
457
556
 
458
557
  ---
459
558
 
@@ -122,6 +122,24 @@ For each agent that completed PLANNING:
122
122
  - Example: Brief said "Brief is well-written" (subjective, not binary)
123
123
  ```
124
124
 
125
+ ### Step 3b: Dimensional Validation (6 quality dimensions)
126
+ ```
127
+ Validate planning artifacts across 6 independent dimensions.
128
+ Each dimension produces PASS/FAIL with evidence.
129
+
130
+ | Dimension | What It Checks | FAIL Trigger |
131
+ |-----------|---------------|--------------|
132
+ | TRACEABILITY | Brief to PRD to Phases to Tasks chains complete | Any orphaned requirement |
133
+ | INFORMATION DENSITY | No filler phrases, padding, or LLM-generated fluff | "It is important to note", "Furthermore", "In conclusion", repetitive restatements |
134
+ | IMPLEMENTATION LEAKAGE | PRD says WHAT not HOW. No technology names in FRs | React, PostgreSQL, Tailwind, etc. found inside FR descriptions |
135
+ | MEASURABILITY | All success metrics and NFRs are quantifiable | "Fast", "responsive", "secure" without numeric thresholds |
136
+ | COMPLETENESS | All Brief categories covered, no gaps | Missing user personas, constraints, negative scope |
137
+ | SMART | Requirements are Specific, Measurable, Achievable, Relevant, Time-bound | Vague scope, unmeasurable criteria, unrealistic estimates |
138
+
139
+ Report as dimensional audit table in the QA report.
140
+ Apply penalties: -10 per FAIL dimension (in addition to existing per-item penalties).
141
+ ```
142
+
125
143
  ### Step 4: Adversarial Review (Mandatory)
126
144
 
127
145
  ```
@@ -1,8 +1,8 @@
1
1
  # chati.dev Configuration
2
- version: "4.0.4"
2
+ version: "4.1.0"
3
3
  installed_at: "2026-02-07T10:00:00Z"
4
- updated_at: "2026-03-22T00:00:00Z"
5
- installer_version: "4.0.4"
4
+ updated_at: "2026-04-02T00:00:00Z"
5
+ installer_version: "4.1.0"
6
6
  project_type: greenfield
7
7
  language: en
8
8
  ides: [claude-code]
@@ -28,7 +28,7 @@ providers:
28
28
  # provider: gemini
29
29
  # model: pro
30
30
 
31
- # Feature flags — toggle new capabilities (v4.0 Pegasus)
31
+ # Feature flags — toggle new capabilities (v4.0 Pegasus + Intelligence Upgrade)
32
32
  features:
33
33
  hybrid_budget: true
34
34
  anti_dash: true
@@ -42,6 +42,17 @@ features:
42
42
  tech_presets: true
43
43
  doctor_autofix: true
44
44
  brandbook: true
45
+ # Intelligence Upgrade (v4.0.5 — Claude Code patterns)
46
+ undercover_mode: true # Sanitize framework terms from deliverables
47
+ memory_extraction: true # Per-turn automatic memory capture
48
+ memory_consolidation: true # /chati dream — 4-phase memory consolidation
49
+ daily_digest: true # /chati digest — KAIROS Lite daily activity log
50
+ structured_session_memory: true # 8-section session digest with token budgets
51
+ static_prism_boundary: true # Static/Dynamic PRISM boundary for cache optimization
52
+ token_bracket_estimation: true # Token-based bracket estimation (replaces turn count)
53
+ model_fallback: true # Automatic opus→sonnet fallback on overload
54
+ frustration_detection: true # Detect user frustration and adapt response style
55
+ bash_security_checks: true # 23-point shell injection defense system
45
56
 
46
57
  # Telemetry — opt-in anonymous usage tracking
47
58
  telemetry:
@@ -322,6 +322,12 @@ The pipeline operates in three execution modes that control agent permissions. M
322
322
 
323
323
  7. Memory attention scoring SHALL use natural decay — memories not accessed lose relevance organically. No memory is permanent unless explicitly marked as durable by the user.
324
324
 
325
+ 8. The system SHALL support memory consolidation (`/chati dream`) to merge, deduplicate, and prune accumulated memories. Consolidation follows a 4-phase cycle (Orient, Gather, Consolidate, Prune) and archives removed entries rather than deleting them.
326
+
327
+ 9. Per-turn memory extraction MAY capture decisions, resolutions, corrections, and validated patterns automatically from agent output. Extracted memories start at warm tier (confidence 0.5) and are promoted through evidence accumulation.
328
+
329
+ 10. Daily activity digests (`/chati digest`) SHALL maintain append-only session logs for observability. Digests are cumulative per calendar day and include agent scores, decisions, and gotchas.
330
+
325
331
  **Enforcement: BLOCK** — Auto-modification of user files is a critical violation.
326
332
 
327
333
  ---
@@ -461,7 +467,7 @@ When multiple CLI providers are enabled, the system SHALL coordinate agent execu
461
467
 
462
468
  1. The CLI Provider Registry (`packages/chati-dev/src/terminal/cli-registry.js`) is the source of truth for provider capabilities: command syntax, model flags, stdin support, hook support, MCP support, and context file format.
463
469
 
464
- 2. The handoff format is provider-agnostic. All agents, regardless of which CLI executes them, produce handoffs in the same two-layer format (Article VIII). This ensures seamless inter-provider communication.
470
+ 2. The handoff format is provider-agnostic. All agents, regardless of which CLI executes them, produce handoffs in the same two-layer format (Article VIII). This ensures consistent inter-provider communication without format translation.
465
471
 
466
472
  3. Provider availability SHALL be validated by the health check engine before spawning. If a configured provider is unavailable, the system SHALL fall back to the primary provider (claude) with a warning.
467
473
 
@@ -481,5 +487,5 @@ When multiple CLI providers are enabled, the system SHALL coordinate agent execu
481
487
 
482
488
  ---
483
489
 
484
- *Chati.dev Constitution v4.0.1 — 19 Articles + Preamble*
490
+ *Chati.dev Constitution v4.1.0 — 19 Articles + Preamble*
485
491
  *All agents are bound by this Constitution. Violations are enforced per article.*
@@ -1,7 +1,7 @@
1
1
  # Chati.dev System Context
2
2
 
3
3
  ## Framework
4
- - **Version**: 4.0.0
4
+ - **Version**: 4.1.0
5
5
  - **Agents**: 13 (12 specialized + orchestrator)
6
6
  - **Constitution**: 19 Articles + Preamble
7
7
  - **Quality**: 5 pipeline gates + 3-tier verdicts (APPROVED / NEEDS_REVISION / BLOCKED)
@@ -3,9 +3,9 @@
3
3
  # and by the Health Check for system integrity validation.
4
4
 
5
5
  metadata:
6
- version: "4.0.0"
7
- last_updated: "2026-03-17T00:00:00Z"
8
- entity_count: 55
6
+ version: "4.1.0"
7
+ last_updated: "2026-04-02T00:00:00Z"
8
+ entity_count: 62
9
9
  checksum_algorithm: sha256
10
10
 
11
11
  entities:
@@ -195,6 +195,14 @@ entities:
195
195
  dependencies: [brandbook]
196
196
  adaptability: 0.8
197
197
 
198
+ session-memory:
199
+ path: chati.dev/templates/session-memory-tmpl.yaml
200
+ type: template
201
+ purpose: "8-section structured digest template for session memory capture"
202
+ keywords: [memory, digest, session, structured, sections, budget]
203
+ dependencies: [constitution]
204
+ adaptability: 0.6
205
+
198
206
  workflows:
199
207
  greenfield-fullstack:
200
208
  path: chati.dev/workflows/greenfield-fullstack.yaml
@@ -351,6 +359,54 @@ entities:
351
359
  dependencies: []
352
360
  adaptability: 0.7
353
361
 
362
+ memory-consolidation:
363
+ path: packages/chati-dev/src/memory/dream.js
364
+ type: module
365
+ purpose: "4-phase memory consolidation (Orient, Gather, Consolidate, Prune)"
366
+ keywords: [memory, consolidation, dream, deduplication, pruning, archive]
367
+ dependencies: [memory-layer]
368
+ adaptability: 0.3
369
+
370
+ memory-extraction:
371
+ path: packages/chati-dev/src/memory/memory-extractor.js
372
+ type: module
373
+ purpose: "Per-turn automatic memory extraction from agent output"
374
+ keywords: [memory, extraction, patterns, decisions, resolutions, corrections]
375
+ dependencies: [memory-layer]
376
+ adaptability: 0.4
377
+
378
+ daily-digest:
379
+ path: packages/chati-dev/src/memory/daily-digest.js
380
+ type: module
381
+ purpose: "KAIROS Lite daily activity digest with append-only entries"
382
+ keywords: [digest, daily, kairos, activity, summary, sessions]
383
+ dependencies: [memory-layer]
384
+ adaptability: 0.5
385
+
386
+ magic-docs:
387
+ path: packages/chati-dev/src/memory/magic-docs.js
388
+ type: module
389
+ purpose: "Auto-updating CLAUDE.md Current State section after handoffs"
390
+ keywords: [documentation, auto-update, claude-md, handoff, state]
391
+ dependencies: [constitution]
392
+ adaptability: 0.4
393
+
394
+ undercover-guard:
395
+ path: chati.dev/hooks/undercover-guard.js
396
+ type: hook
397
+ purpose: "Sanitize framework terminology from user-facing deliverables"
398
+ keywords: [security, sanitization, undercover, internal-terms, deliverables]
399
+ dependencies: [constitution]
400
+ adaptability: 0.2
401
+
402
+ bash-security:
403
+ path: packages/chati-dev/src/security/bash-security.js
404
+ type: module
405
+ purpose: "23-point shell injection defense system for bash commands"
406
+ keywords: [security, bash, injection, shell, defense, checks]
407
+ dependencies: [constitution]
408
+ adaptability: 0.1
409
+
354
410
  quality-gates:
355
411
  planning-gate:
356
412
  path: chati.dev/quality-gates/planning-gate.md
@@ -99,6 +99,25 @@ async function main() {
99
99
  }));
100
100
  return;
101
101
  }
102
+
103
+ // Run 23-point shell injection security checks
104
+ const injectionFindings = runShellInjectionChecks(command);
105
+ if (injectionFindings.length > 0) {
106
+ const critical = injectionFindings.filter(f => f.severity === 'critical');
107
+ if (critical.length > 0) {
108
+ process.stdout.write(JSON.stringify({
109
+ decision: 'block',
110
+ reason: `[Article IV] Shell injection risk detected (${critical.length} critical): ${critical.map(f => f.id).join(', ')}. Command: "${command.slice(0, 60)}..."`,
111
+ }));
112
+ return;
113
+ }
114
+ // High/medium findings: allow with warning (advisory)
115
+ process.stdout.write(JSON.stringify({
116
+ decision: 'allow',
117
+ reason: `[Security Advisory] ${injectionFindings.length} shell security finding(s): ${injectionFindings.map(f => f.id).join(', ')}`,
118
+ }));
119
+ return;
120
+ }
102
121
  }
103
122
 
104
123
  process.stdout.write(JSON.stringify({ decision: 'allow' }));
@@ -108,7 +127,54 @@ async function main() {
108
127
  }
109
128
  }
110
129
 
111
- export { containsSecrets, isDestructiveCommand, SECRET_PATTERNS, DESTRUCTIVE_COMMANDS };
130
+ /**
131
+ * 23-point shell injection security checks.
132
+ * Inline implementation (hooks are standalone — no imports from src/).
133
+ * Based on Claude Code's bashSecurity.ts patterns.
134
+ */
135
+ // SYNC: These 23 check IDs MUST match packages/chati-dev/src/security/bash-security.js
136
+ // Hooks are standalone (no imports from src/), so duplication is necessary.
137
+ // If you update here, update bash-security.js too. Run: npm test to verify both.
138
+ const SHELL_INJECTION_CHECKS = [
139
+ { id: 'INCOMPLETE_COMMANDS', pattern: /[|&;]\s*$/, severity: 'high' },
140
+ { id: 'JQ_SYSTEM_FUNCTION', pattern: /jq\b.*\bsystem\s*\(/i, severity: 'critical' },
141
+ { id: 'JQ_FILE_ARGUMENTS', pattern: /jq\b.*--from-file|jq\b.*-f\s+[^|&;]+/i, severity: 'high' },
142
+ { id: 'OBFUSCATED_FLAGS', pattern: /\$[({].*[)}].*-/, severity: 'high' },
143
+ { id: 'SHELL_METACHARACTERS', pattern: /[`]|(?:\$\((?!.*\becho\b))/, severity: 'critical' },
144
+ { id: 'DANGEROUS_VARIABLES', pattern: /(?:^|\s)(?:PATH|LD_PRELOAD|LD_LIBRARY_PATH|DYLD_INSERT_LIBRARIES|PYTHONPATH|NODE_PATH|RUBYLIB|PERL5LIB)\s*=/, severity: 'critical' },
145
+ { id: 'NEWLINES', pattern: /(?<!\\)\n.*(?:rm|curl|wget|chmod|chown|sudo|eval|exec)/, severity: 'high' },
146
+ { id: 'BACKSLASH_ESCAPED_WHITESPACE', pattern: /\\\s+(?:-|\/)/,severity: 'medium' },
147
+ // eslint-disable-next-line no-control-regex
148
+ { id: 'CONTROL_CHARACTERS', pattern: /[\x00-\x08\x0e-\x1f\x7f]/, severity: 'critical' },
149
+ { id: 'UNICODE_WHITESPACE', pattern: /[\u200B-\u200F\u2028-\u202F\uFEFF\u00A0\u2060\u180E]/, severity: 'critical' },
150
+ { id: 'DANGEROUS_PATTERNS_COMMAND_SUBSTITUTION', pattern: /\$\(.*(?:curl|wget|nc|bash|sh|python|perl|ruby|node)\b/i, severity: 'critical' },
151
+ { id: 'DANGEROUS_PATTERNS_INPUT_REDIRECTION', pattern: /<\s*(?:\/etc\/(?:passwd|shadow|sudoers)|\/proc\/|~\/\.ssh\/|~\/\.aws\/)/, severity: 'critical' },
152
+ { id: 'DANGEROUS_PATTERNS_OUTPUT_REDIRECTION', pattern: />\s*(?:\/etc\/|~\/\.ssh\/|~\/\.bashrc|~\/\.zshrc|~\/\.profile|~\/\.gitconfig)/, severity: 'critical' },
153
+ { id: 'IFS_INJECTION', pattern: /\bIFS\s*=/, severity: 'critical' },
154
+ { id: 'BRACE_EXPANSION', pattern: /\{.*(?:rm|curl|wget|chmod|eval|exec|sudo).*[,}]/, severity: 'high' },
155
+ { id: 'GIT_COMMIT_SUBSTITUTION', pattern: /git\s+(?:commit|push|tag).*\$[({]/, severity: 'high' },
156
+ { id: 'PROC_ENVIRON_ACCESS', pattern: /\/proc\/(?:self|\d+)\/(?:environ|cmdline|maps|mem)/, severity: 'critical' },
157
+ { id: 'MALFORMED_TOKEN_INJECTION', pattern: /\\x[0-9a-f]{2}|\\u[0-9a-f]{4}|\\[0-7]{3}/i, severity: 'high' },
158
+ { id: 'MID_WORD_HASH', pattern: /\w#\w/, severity: 'medium' },
159
+ { id: 'COMMENT_QUOTE_DESYNC', pattern: /#.*['"][^'"]*$/, severity: 'medium' },
160
+ { id: 'QUOTED_NEWLINE', pattern: /["'][^"']*\n[^"']*["']/, severity: 'high' },
161
+ { id: 'ZSH_DANGEROUS_COMMANDS', pattern: /\b(?:zmodload|sysopen|sysread|syswrite|zsystem|zselect|ztcp)\b/, severity: 'critical' },
162
+ { id: 'BACKSLASH_ESCAPED_OPERATORS', pattern: /\\[|;&]/, severity: 'medium' },
163
+ ];
164
+
165
+ function runShellInjectionChecks(command) {
166
+ if (!command || typeof command !== 'string') return [];
167
+ const findings = [];
168
+ for (const check of SHELL_INJECTION_CHECKS) {
169
+ check.pattern.lastIndex = 0;
170
+ if (check.pattern.test(command)) {
171
+ findings.push({ id: check.id, severity: check.severity });
172
+ }
173
+ }
174
+ return findings;
175
+ }
176
+
177
+ export { containsSecrets, isDestructiveCommand, runShellInjectionChecks, SECRET_PATTERNS, DESTRUCTIVE_COMMANDS, SHELL_INJECTION_CHECKS };
112
178
 
113
179
  // Only run main when executed directly (not imported by tests)
114
180
  import { fileURLToPath } from 'url';
@@ -89,11 +89,11 @@ async function main() {
89
89
  return;
90
90
  }
91
91
  block(buildMessage(data.status, data.reason));
92
- } catch {
93
- allow(); // Fail open — API unreachable
92
+ } catch { /* expected: API may be unreachable — fail open */
93
+ allow();
94
94
  }
95
- } catch {
96
- allow(); // Parse error — fail open
95
+ } catch { /* expected: stdin parse may fail — fail open */
96
+ allow();
97
97
  }
98
98
  }
99
99
 
@@ -88,7 +88,8 @@ async function main() {
88
88
  } else {
89
89
  process.stdout.write(JSON.stringify({ result: 'allow' }));
90
90
  }
91
- } catch {
91
+ } catch (err) {
92
+ process.stderr.write(`[chati] model-governance: ${err.message}\n`);
92
93
  process.stdout.write(JSON.stringify({ result: 'allow' }));
93
94
  }
94
95
  }
@@ -32,6 +32,7 @@ function readSessionState(projectDir) {
32
32
  workflow: extract('workflow') || null,
33
33
  pipelinePosition: extract('pipeline_position') || null,
34
34
  turnCount: parseInt(extract('turn_count') || '0', 10),
35
+ provider: extract('provider') || 'claude',
35
36
  };
36
37
  }
37
38
 
@@ -56,9 +57,39 @@ async function main() {
56
57
  return;
57
58
  }
58
59
 
59
- // Estimate remaining context from turn count
60
- const maxTurns = 40;
61
- const remainingPercent = Math.max(0, Math.round((1 - session.turnCount / maxTurns) * 100));
60
+ // Estimate remaining context prefer token-based estimation over turn count
61
+ // Token estimation: 1 token ≈ 4 characters (Claude Code pattern)
62
+ // SYNC: These limits MUST match packages/chati-dev/src/utils/provider-limits.js
63
+ const HOOK_MODEL_LIMITS = { opus: 1_000_000, sonnet: 200_000, haiku: 200_000, pro: 1_000_000, flash: 1_000_000, codex: 128_000 };
64
+ const HOOK_PROVIDER_LIMITS = { claude: 200_000, gemini: 1_000_000, codex: 128_000 };
65
+
66
+ // Infer model from current agent via AGENT_MODELS map
67
+ const HOOK_AGENT_MODELS = {
68
+ orchestrator: 'sonnet', 'greenfield-wu': 'haiku', 'brownfield-wu': 'opus',
69
+ brief: 'sonnet', detail: 'opus', architect: 'opus', ux: 'sonnet',
70
+ phases: 'sonnet', tasks: 'sonnet', 'qa-planning': 'opus',
71
+ 'qa-implementation': 'opus', dev: 'opus', devops: 'sonnet',
72
+ };
73
+ const inferredModel = session.currentAgent ? HOOK_AGENT_MODELS[session.currentAgent] : null;
74
+
75
+ // Resolve context limit: model > provider > default
76
+ function hookResolveLimit(model, provider) {
77
+ if (model && HOOK_MODEL_LIMITS[model]) return HOOK_MODEL_LIMITS[model];
78
+ if (provider && HOOK_PROVIDER_LIMITS[provider]) return HOOK_PROVIDER_LIMITS[provider];
79
+ return 200_000;
80
+ }
81
+
82
+ let remainingPercent;
83
+ const promptText = event.prompt || '';
84
+ if (promptText.length > 0) {
85
+ const estimatedTokens = Math.ceil(promptText.length / 4);
86
+ const contextLimit = hookResolveLimit(inferredModel, session.provider);
87
+ remainingPercent = Math.max(0, Math.round((1 - estimatedTokens / contextLimit) * 100));
88
+ } else {
89
+ // Fallback to turn-count heuristic when prompt text unavailable
90
+ const maxTurns = 40;
91
+ remainingPercent = Math.max(0, Math.round((1 - session.turnCount / maxTurns) * 100));
92
+ }
62
93
 
63
94
  // Determine bracket
64
95
  let bracket = 'FRESH';
@@ -79,6 +110,15 @@ async function main() {
79
110
  }
80
111
  }
81
112
 
113
+ // Frustration detection — adapt response style when user is frustrated
114
+ const frustrationDetected = detectFrustration(promptText);
115
+
116
+ // Microcompact advisory — hint to economize context when depleted + idle
117
+ let microcompactAdvisory = '';
118
+ if ((bracket === 'DEPLETED' || bracket === 'CRITICAL') && session.turnCount > 10) {
119
+ microcompactAdvisory = ' <advisory priority="medium">Context constrained. Avoid re-reading files already in context. Summarize stale outputs before proceeding.</advisory>';
120
+ }
121
+
82
122
  // Build minimal context block (full PRISM pipeline is used by orchestrator internally)
83
123
  const contextBlock = [
84
124
  `<chati-context bracket="${bracket}">`,
@@ -87,6 +127,8 @@ async function main() {
87
127
  session.pipelinePosition ? ` <pipeline-position>${session.pipelinePosition}</pipeline-position>` : '',
88
128
  memoryBlock,
89
129
  bracket === 'CRITICAL' ? ' <advisory>Context running low. Consider handoff or summary.</advisory>' : '',
130
+ microcompactAdvisory,
131
+ frustrationDetected ? ' <advisory priority="high">User shows signs of frustration. Be more direct, acknowledge the issue explicitly, focus on the solution, avoid repeating previous suggestions.</advisory>' : '',
90
132
  '</chati-context>',
91
133
  ].filter(Boolean).join('\n');
92
134
 
@@ -94,13 +136,39 @@ async function main() {
94
136
  result: 'allow',
95
137
  prefix: contextBlock,
96
138
  }));
97
- } catch {
98
- // On error, allow without injection
139
+ } catch (err) {
140
+ process.stderr.write(`[chati] prism-engine: ${err.message}\n`);
99
141
  process.stdout.write(JSON.stringify({ result: 'allow' }));
100
142
  }
101
143
  }
102
144
 
103
- export { readSessionState };
145
+ /**
146
+ * Frustration detection patterns.
147
+ * Inspired by Claude Code's regex-based emotion detection.
148
+ * Soft advisory only — never blocks or overrides behavior.
149
+ */
150
+ const FRUSTRATION_PATTERNS = [
151
+ /this (is|isn't|isnt) working/i,
152
+ /I (already|just) (told|said|asked)/i,
153
+ /why (won't|doesn't|can't|isn't|wont|doesnt|cant|isnt)/i,
154
+ /stop (doing|repeating|ignoring)/i,
155
+ /you('re| are) (not|never) (listening|reading|understanding)/i,
156
+ /for the (second|third|fourth|last) time/i,
157
+ /!!+/,
158
+ /\b(WTF|WHAT THE|FFS|OMG)\b/i,
159
+ ];
160
+
161
+ /**
162
+ * Detect user frustration from prompt text.
163
+ * @param {string} prompt - User prompt text
164
+ * @returns {boolean} True if frustration patterns detected
165
+ */
166
+ function detectFrustration(prompt) {
167
+ if (!prompt || prompt.length < 5) return false;
168
+ return FRUSTRATION_PATTERNS.some(p => p.test(prompt));
169
+ }
170
+
171
+ export { readSessionState, detectFrustration };
104
172
 
105
173
  // Only run main when executed directly (not imported by tests)
106
174
  import { fileURLToPath } from 'url';
@@ -52,7 +52,7 @@ function isSensitivePath(filePath, cwd) {
52
52
  let rel;
53
53
  try {
54
54
  rel = relative(cwd, filePath);
55
- } catch {
55
+ } catch { /* expected: path may be on different drive */
56
56
  rel = filePath;
57
57
  }
58
58