sinapse-ai 1.9.0 → 1.10.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.
- package/.claude/rules/mandatory-delegation.md +1 -1
- package/.codex/delegation-matrix.json +4 -3
- package/.codex/delegation-parity.json +4 -3
- package/.codex/instructions.md +2 -2
- package/.sinapse-ai/constitution.md +2 -2
- package/.sinapse-ai/core/doctor/checks/git-hooks.js +76 -10
- package/.sinapse-ai/core/execution/subagent-dispatcher.js +1 -1
- package/.sinapse-ai/core/synapse/engine.js +15 -0
- package/.sinapse-ai/data/entity-registry.yaml +13 -13
- package/.sinapse-ai/development/agents/snps-orqx.md +4 -4
- package/.sinapse-ai/git-hooks/lib/secret-scanner-core.js +76 -4
- package/.sinapse-ai/git-hooks/pre-push +7 -1
- package/.sinapse-ai/install-manifest.yaml +9 -9
- package/AGENTS.md +4 -4
- package/CHANGELOG.md +1257 -0
- package/README.en.md +4 -3
- package/README.md +5 -6
- package/bin/commands/install.js +6 -3
- package/bin/commands/uninstall.js +2 -2
- package/bin/sinapse.js +20 -0
- package/bin/utils/secret-scanner-core.js +76 -4
- package/docs/agent-reference-guide.md +1 -1
- package/docs/framework/architecture-overview.md +4 -4
- package/docs/framework/guiding-principles.md +9 -9
- package/docs/getting-started.md +1 -1
- package/docs/guides/agent-reference.md +1 -1
- package/docs/guides/codex-config.md +4 -5
- package/docs/pt/architecture/sub-orqx-pattern.md +20 -18
- package/package.json +8 -2
- package/packages/installer/src/installer/git-hooks-installer.js +3 -1
- package/packages/installer/src/installer/sinapse-ai-installer.js +32 -7
- package/packages/installer/src/wizard/ide-config-generator.js +9 -1
- package/packages/installer/src/wizard/index.js +3 -4
- package/scripts/regenerate-orqx-stubs.ps1 +0 -1
- package/scripts/sync-counts.js +10 -2
- package/scripts/sync-squad-yaml-components.js +108 -6
- package/scripts/validate-article-vii.js +68 -7
- package/scripts/validate-squad-orqx.js +19 -9
- package/sinapse/agents/sinapse-orqx.md +4 -4
- package/sinapse/agents/snps-orqx.md +4 -4
- package/sinapse/knowledge-base/routing-catalog.md +1 -1
- package/sinapse/tasks/diagnose-and-route.md +1 -1
- package/sinapse/tasks/squad-status-report.md +1 -1
- package/squads/claude-code-mastery/agents/claude-mastery-chief.md +1 -1
- package/squads/claude-code-mastery/agents/hooks-architect.md +60 -68
- package/squads/claude-code-mastery/knowledge-base/swarm-orchestration-patterns.md +1 -1
- package/squads/claude-code-mastery/tasks/audit-setup.md +1 -1
- package/squads/claude-code-mastery/workflows/optimization-cycle.yaml +4 -4
- package/squads/claude-code-mastery/workflows/project-setup-cycle.yaml +4 -4
- package/squads/squad-animations/README.md +1 -1
- package/squads/squad-cloning/README.md +1 -1
- package/squads/squad-commercial/README.md +1 -1
- package/squads/squad-content/README.md +1 -1
- package/squads/squad-copy/README.md +1 -1
- package/squads/squad-council/README.md +1 -1
- package/squads/squad-courses/README.md +1 -1
- package/squads/squad-cybersecurity/README.md +1 -1
- package/squads/squad-design/README.md +1 -1
- package/squads/squad-finance/README.md +1 -1
- package/squads/squad-growth/README.md +1 -1
- package/squads/squad-paidmedia/README.md +1 -1
- package/squads/squad-product/README.md +1 -1
- package/squads/squad-research/README.md +1 -1
- package/squads/squad-storytelling/README.md +1 -1
- package/.sinapse-ai/core/memory/__tests__/active-modules.verify.js +0 -265
- package/.sinapse-ai/core/permissions/__tests__/permission-mode.test.js +0 -293
- package/.sinapse-ai/infrastructure/tests/project-status-loader.test.js +0 -569
- package/.sinapse-ai/infrastructure/tests/regression-suite-v2.md +0 -622
- package/.sinapse-ai/infrastructure/tests/validate-module.js +0 -98
- package/.sinapse-ai/infrastructure/tests/worktree-manager.test.js +0 -620
- package/.sinapse-ai/workflow-intelligence/__tests__/confidence-scorer.test.js +0 -335
- package/.sinapse-ai/workflow-intelligence/__tests__/integration.test.js +0 -340
- package/.sinapse-ai/workflow-intelligence/__tests__/suggestion-engine.test.js +0 -438
- package/.sinapse-ai/workflow-intelligence/__tests__/wave-analyzer.test.js +0 -448
- package/.sinapse-ai/workflow-intelligence/__tests__/workflow-registry.test.js +0 -303
- package/packages/installer/src/__tests__/performance-benchmark.js +0 -383
- package/packages/installer/tests/integration/environment-configuration.test.js +0 -332
- package/packages/installer/tests/integration/wizard-detection.test.js +0 -352
- package/packages/installer/tests/unit/artifact-copy-pipeline/artifact-copy-pipeline.test.js +0 -402
- package/packages/installer/tests/unit/claude-md-template-v5/claude-md-template-v5.test.js +0 -193
- package/packages/installer/tests/unit/config-validator.test.js +0 -315
- package/packages/installer/tests/unit/detection/detect-project-type.test.js +0 -539
- package/packages/installer/tests/unit/doctor/doctor-checks.test.js +0 -675
- package/packages/installer/tests/unit/doctor/doctor-orchestrator.test.js +0 -192
- package/packages/installer/tests/unit/entity-registry-bootstrap.test.js +0 -192
- package/packages/installer/tests/unit/env-template.test.js +0 -187
- package/packages/installer/tests/unit/generate-settings-json/generate-settings-json.test.js +0 -310
- package/packages/installer/tests/unit/git-hooks-installer.test.js +0 -262
- package/packages/installer/tests/unit/ide-sync-integration/ide-sync-integration.test.js +0 -231
- package/packages/installer/tests/unit/merger/env-merger.test.js +0 -191
- package/packages/installer/tests/unit/merger/markdown-merger.test.js +0 -262
- package/packages/installer/tests/unit/merger/strategies.test.js +0 -154
- package/packages/installer/tests/unit/merger/yaml-merger.test.js +0 -328
- package/packages/sinapse-install/tests/unit/chrome-brain.smoke.test.js +0 -66
package/README.en.md
CHANGED
|
@@ -33,7 +33,7 @@ Generative AI has a known problem: the more you ask of it, the worse it gets. A
|
|
|
33
33
|
|
|
34
34
|
SINAPSE solves this the way human teams solve it: **coordinated specialization**. Instead of one tired generalist, you have 172 agents in 17 squads, each with a defined role, its own knowledge base, and executable tasks. An orchestrator routes your request to whoever actually knows how to solve it -- automatically, without you needing to memorize agent names or commands.
|
|
35
35
|
|
|
36
|
-
The differential isn't just the quantity of agents. It's **real governance**: 19 active hooks intercept operations at runtime, a Constitution with
|
|
36
|
+
The differential isn't just the quantity of agents. It's **real governance**: 19 active hooks intercept operations at runtime, a Constitution with 11 articles governs the framework, and 7 of those articles are NON-NEGOTIABLE -- violations are blocked before execution, not detected afterwards. **Speed with rigor, without choosing between the two.**
|
|
37
37
|
|
|
38
38
|
---
|
|
39
39
|
|
|
@@ -174,7 +174,7 @@ Deny rules in `.claude/settings.json` enforce this deterministically. **Framewor
|
|
|
174
174
|
|
|
175
175
|
### Constitution
|
|
176
176
|
|
|
177
|
-
SINAPSE is governed by a formal Constitution with
|
|
177
|
+
SINAPSE is governed by a formal Constitution with 11 articles and 19 enforcement hooks:
|
|
178
178
|
|
|
179
179
|
| Article | Principle | Severity |
|
|
180
180
|
|---------|-----------|----------|
|
|
@@ -188,8 +188,9 @@ SINAPSE is governed by a formal Constitution with 10 articles and 19 enforcement
|
|
|
188
188
|
| VIII | Mandatory Delegation | NON-NEGOTIABLE |
|
|
189
189
|
| IX | Safe Collaboration | NON-NEGOTIABLE |
|
|
190
190
|
| X | Security & Data Protection | NON-NEGOTIABLE |
|
|
191
|
+
| XI | Conservative Default | MUST |
|
|
191
192
|
|
|
192
|
-
|
|
193
|
+
7 articles are NON-NEGOTIABLE -- violations are automatically blocked before execution.
|
|
193
194
|
|
|
194
195
|
---
|
|
195
196
|
|
package/README.md
CHANGED
|
@@ -3,7 +3,7 @@
|
|
|
3
3
|
[](https://nodejs.org/)
|
|
4
4
|
[](https://github.com/caioimori/sinapse-ai/actions/workflows/ci.yml)
|
|
5
5
|
[](https://github.com/caioimori/sinapse-ai/actions/workflows/ci.yml)
|
|
6
|
-
[](.sinapse-ai/constitution.md)
|
|
7
7
|
|
|
8
8
|
```
|
|
9
9
|
____ ___ _ _ _ ____ ____ _____
|
|
@@ -35,7 +35,7 @@ IA generativa tem um problema conhecido: quanto mais voce pede, pior fica. Um un
|
|
|
35
35
|
|
|
36
36
|
SINAPSE resolve isso do jeito que times humanos resolvem: **especializacao coordenada**. Em vez de um generalista cansado, voce tem 172 agentes em 17 squads, cada um com papel definido, knowledge base propria e tasks executaveis. Um orquestrador roteia seu pedido para quem realmente sabe resolver — automaticamente, sem voce precisar decorar agent names ou comandos.
|
|
37
37
|
|
|
38
|
-
O diferencial nao e apenas quantidade de agentes. E **governanca real**: 13 hooks ativos interceptam operacoes em tempo de execucao, uma Constitution com
|
|
38
|
+
O diferencial nao e apenas quantidade de agentes. E **governanca real**: 13 hooks ativos interceptam operacoes em tempo de execucao, uma Constitution com 11 artigos rege o framework, e 7 desses artigos sao NON-NEGOTIABLE — violacoes sao bloqueadas antes de executar, nao detectadas depois. **Velocidade com rigor, sem escolher entre os dois.**
|
|
39
39
|
|
|
40
40
|
---
|
|
41
41
|
|
|
@@ -137,8 +137,6 @@ Cada release passa por uma matriz de instalacao de 27 combinacoes (3 OSes x 3 pa
|
|
|
137
137
|
|
|
138
138
|
**Sobre Yarn v1 no Windows:** Yarn v1 (Classic) esta em modo manutencao desde 2020, com Yarn v2+ (Berry) como sucessor oficial. A combinacao Windows + Yarn v1 apresenta falhas de resolucao de wrapper que nao compensam investigar por ser ecossistema em declinio. Usuarios Windows em Yarn v1 devem migrar para Yarn v2+ (recomendado) ou usar npm/pnpm. macOS e Linux em Yarn v1 continuam suportados.
|
|
139
139
|
|
|
140
|
-
Registro completo da decisao e resultados: [docs/audits/install-matrix-2026-04-16.md](docs/audits/install-matrix-2026-04-16.md).
|
|
141
|
-
|
|
142
140
|
### "Como atualizar sem perder minhas customizacoes?"
|
|
143
141
|
|
|
144
142
|
```bash
|
|
@@ -215,7 +213,7 @@ Deny rules em `.claude/settings.json` reforcam isso deterministicamente. **Updat
|
|
|
215
213
|
|
|
216
214
|
### Constitution
|
|
217
215
|
|
|
218
|
-
O SINAPSE e governado por uma Constitution formal com
|
|
216
|
+
O SINAPSE e governado por uma Constitution formal com 11 artigos e 13 hooks de enforcement:
|
|
219
217
|
|
|
220
218
|
| Artigo | Principio | Severidade |
|
|
221
219
|
|--------|-----------|------------|
|
|
@@ -229,8 +227,9 @@ O SINAPSE e governado por uma Constitution formal com 10 artigos e 13 hooks de e
|
|
|
229
227
|
| VIII | Mandatory Delegation | NON-NEGOTIABLE |
|
|
230
228
|
| IX | Safe Collaboration | NON-NEGOTIABLE |
|
|
231
229
|
| X | Security & Data Protection | NON-NEGOTIABLE |
|
|
230
|
+
| XI | Conservative Default | MUST |
|
|
232
231
|
|
|
233
|
-
|
|
232
|
+
7 artigos sao NON-NEGOTIABLE — violacoes sao bloqueadas automaticamente antes de executar.
|
|
234
233
|
|
|
235
234
|
---
|
|
236
235
|
|
package/bin/commands/install.js
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
// bin/commands/install.js — `sinapse-ai install` (global) command + helpers.
|
|
2
2
|
// Story GA-1.2 — extracted from bin/cli.js.
|
|
3
3
|
|
|
4
|
-
const { execSync } = require('child_process');
|
|
4
|
+
const { execSync, execFileSync } = require('child_process');
|
|
5
5
|
const fs = require('fs');
|
|
6
6
|
const path = require('path');
|
|
7
7
|
const { getLogger } = require('../../.sinapse-ai/core/logger');
|
|
@@ -893,11 +893,14 @@ function ensurePathWindows() {
|
|
|
893
893
|
return;
|
|
894
894
|
}
|
|
895
895
|
|
|
896
|
-
|
|
896
|
+
// execFileSync (no shell) — never interpolate the current PATH into a
|
|
897
|
+
// shell command string. A PATH value containing `"`/`&`/`^` would break
|
|
898
|
+
// the command or allow injection; passing args as an array avoids it.
|
|
899
|
+
execFileSync('setx', ['PATH', newPath], { encoding: 'utf8', stdio: 'pipe' });
|
|
897
900
|
logger.always(` ${GREEN}OK${NC} Added ~/bin to Windows User PATH`);
|
|
898
901
|
} catch {
|
|
899
902
|
try {
|
|
900
|
-
|
|
903
|
+
execFileSync('setx', ['PATH', '%USERPROFILE%\\bin'], { encoding: 'utf8', stdio: 'pipe' });
|
|
901
904
|
logger.always(` ${GREEN}OK${NC} Created Windows User PATH with ~/bin`);
|
|
902
905
|
} catch {
|
|
903
906
|
logger.always(` ${YELLOW}WARN${NC} Could not modify PATH. Add manually: ${BIN_DIR}`);
|
|
@@ -51,8 +51,8 @@ async function removeGitHooksConfig(projectDir = process.cwd()) {
|
|
|
51
51
|
// Story 10.40 — Remove SINAPSE-authored orqx agents from a global agents dir.
|
|
52
52
|
// Returns { removed: N } for reporting. Only touches files matching *-orqx.md
|
|
53
53
|
// so we don't accidentally remove user-authored agents.
|
|
54
|
-
// Audit 1 P0 (UN-1) — install writes ~
|
|
55
|
-
// ~/.codex/agents/ but uninstall historically removed only `*-orqx.md` (~
|
|
54
|
+
// Audit 1 P0 (UN-1) — install writes ~170 agent files to ~/.claude/agents/ +
|
|
55
|
+
// ~/.codex/agents/ but uninstall historically removed only `*-orqx.md` (~18
|
|
56
56
|
// files). Files were left orphaned. Fix: install records every authored
|
|
57
57
|
// filename in ~/.sinapse/installed-agents.json; uninstall reads that manifest
|
|
58
58
|
// and removes only those files (preserving anything the user added by hand).
|
package/bin/sinapse.js
CHANGED
|
@@ -73,6 +73,7 @@ USAGE:
|
|
|
73
73
|
sinapse install # Install SINAPSE in current project
|
|
74
74
|
sinapse init <name> # Create new project
|
|
75
75
|
sinapse update # Update to latest version
|
|
76
|
+
sinapse uninstall # Remove SINAPSE from the project (--keep-data)
|
|
76
77
|
sinapse brand # Re-apply SINAPSE branding (after Claude update)
|
|
77
78
|
sinapse validate # Validate installation integrity
|
|
78
79
|
sinapse info # Show system info
|
|
@@ -119,6 +120,25 @@ SERVICE DISCOVERY:
|
|
|
119
120
|
sinapse workers search "transform" --tags=etl,data
|
|
120
121
|
sinapse workers search "api" --format=json
|
|
121
122
|
|
|
123
|
+
GENERATE & CREATE:
|
|
124
|
+
sinapse generate <prd|adr|story|epic|task> # Generate a document from a template
|
|
125
|
+
sinapse create <agent|task|workflow> # Scaffold a new framework component
|
|
126
|
+
|
|
127
|
+
ORCHESTRATION:
|
|
128
|
+
sinapse orchestrate <story-id> # Run the autonomous dev pipeline for a story
|
|
129
|
+
sinapse orchestrate --status # Show / --stop / --resume a running pipeline
|
|
130
|
+
sinapse mode [explore|ask|auto] # Show or set the agent permission mode (--cycle)
|
|
131
|
+
|
|
132
|
+
INTELLIGENCE & HEALTH:
|
|
133
|
+
sinapse health # Framework health analytics (--deep for full scan)
|
|
134
|
+
sinapse graph --deps # Dependency & stats dashboard (--format, --watch)
|
|
135
|
+
sinapse performance # Squad & agent performance ranking (--top N)
|
|
136
|
+
sinapse routing-intel analyze # Routing intelligence analysis
|
|
137
|
+
|
|
138
|
+
INTEGRATIONS & LICENSE:
|
|
139
|
+
sinapse mcp setup # Configure global MCP servers (setup/link/status/add)
|
|
140
|
+
sinapse pro status # SINAPSE Pro license (activate/status/deactivate/features)
|
|
141
|
+
|
|
122
142
|
EXAMPLES:
|
|
123
143
|
# Install in current directory
|
|
124
144
|
npx sinapse-ai@latest
|
|
@@ -72,6 +72,17 @@ const NAMED_PATTERNS = [
|
|
|
72
72
|
{ name: 'Hardcoded Password', pattern: /(?:password|passwd|pwd)\s*[=:]\s*['"][^'"]{8,}['"]/i, lowConfidence: true },
|
|
73
73
|
{ name: 'Bearer Token', pattern: /[Bb]earer\s+[A-Za-z0-9_\-.]{20,}/, entropyGated: true, lowConfidence: true },
|
|
74
74
|
{ name: 'Basic Auth', pattern: /[Bb]asic\s+[A-Za-z0-9+/=]{20,}/, lowConfidence: true },
|
|
75
|
+
|
|
76
|
+
// Long pure-hex runs (32–64 chars). The 16-symbol hex alphabet caps Shannon
|
|
77
|
+
// entropy at ~4.0, BELOW ENTROPY_THRESHOLD (4.5), so the generic entropy
|
|
78
|
+
// backstop never sees them — Twilio auth tokens (32-hex), webhook signing
|
|
79
|
+
// secrets and SHA-style 64-hex digests slip through. This explicit rule closes
|
|
80
|
+
// that gap. It is `hashContextGated`: a hex run sitting in an integrity /
|
|
81
|
+
// checksum / lockfile / git-sha context (covered by HASH_CONTEXT_PATTERN) is a
|
|
82
|
+
// legitimate hash, NOT a secret, and is allowlisted. `lowConfidence` keeps it
|
|
83
|
+
// OUT of the release publish gate (entropy:false there would otherwise match
|
|
84
|
+
// every documented digest); the diff-scoped commit hook still enforces it.
|
|
85
|
+
{ name: 'Long Hex Token', pattern: /\b[a-f0-9]{32,64}\b/i, hashContextGated: true, lowConfidence: true },
|
|
75
86
|
];
|
|
76
87
|
|
|
77
88
|
const PLACEHOLDER_TOKENS = [
|
|
@@ -100,19 +111,48 @@ const PLACEHOLDER_PATTERNS = [
|
|
|
100
111
|
|
|
101
112
|
const EXAMPLE_HOST_PATTERN = /(?:example\.(?:com|org|net)|localhost|127\.0\.0\.1|host\b|your-host|placeholder)/i;
|
|
102
113
|
|
|
114
|
+
// A keyword placeholder only allowlists when it DOMINATES the value: once every
|
|
115
|
+
// placeholder occurrence is removed, the TOTAL alphanumeric length that remains
|
|
116
|
+
// is too short to be a secret on its own (< ENTROPY_MIN_LEN). A bare
|
|
117
|
+
// `lower.includes(token)` was a trivial bypass — ANY real secret that happened to
|
|
118
|
+
// contain "abcdef" / "123456" / "example" anywhere in its body got silently
|
|
119
|
+
// allowlisted (e.g. Xq9Zk2…abcdef…Fg5 passed). Measuring the *total* remainder
|
|
120
|
+
// (not just the longest contiguous run) closes that hole even when the buried
|
|
121
|
+
// placeholder splits the secret into two sub-threshold runs: the legitimate
|
|
122
|
+
// cases (your-key-here, placeholder123456, test-key-example, CHANGEME) strip down
|
|
123
|
+
// to nothing, while a 35-char random token minus a 6-char placeholder still has
|
|
124
|
+
// ~29 alphanumeric chars left and is NOT allowlisted.
|
|
125
|
+
function placeholderDominates(lower) {
|
|
126
|
+
let stripped = lower;
|
|
127
|
+
let matchedAny = false;
|
|
128
|
+
for (const token of PLACEHOLDER_TOKENS) {
|
|
129
|
+
if (stripped.includes(token)) {
|
|
130
|
+
matchedAny = true;
|
|
131
|
+
// Replace with a separator so adjacent runs aren't fused into a longer one.
|
|
132
|
+
stripped = stripped.split(token).join(' ');
|
|
133
|
+
}
|
|
134
|
+
}
|
|
135
|
+
if (!matchedAny) return false;
|
|
136
|
+
// Total alphanumeric chars left after removing every placeholder occurrence.
|
|
137
|
+
const remaining = (stripped.match(/[a-z0-9]/g) || []).length;
|
|
138
|
+
return remaining < ENTROPY_MIN_LEN;
|
|
139
|
+
}
|
|
140
|
+
|
|
103
141
|
function isAllowlistPlaceholder(value) {
|
|
104
142
|
if (value === null || value === undefined) return false;
|
|
105
143
|
const v = String(value).trim();
|
|
106
144
|
if (v.length === 0) return true;
|
|
107
145
|
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
if (lower.includes(token)) return true;
|
|
111
|
-
}
|
|
146
|
+
// Structural placeholders are always safe: <...>, [...], {token}, ${VAR},
|
|
147
|
+
// SCREAMING_SNAKE env-var names, and repeated single-symbol fillers.
|
|
112
148
|
for (const re of PLACEHOLDER_PATTERNS) {
|
|
113
149
|
if (re.test(v)) return true;
|
|
114
150
|
}
|
|
115
151
|
if (/^(.)\1{5,}$/.test(v)) return true; // repeated single char
|
|
152
|
+
|
|
153
|
+
// Keyword placeholders: word-boundary anchored + dominance, NOT raw includes().
|
|
154
|
+
if (placeholderDominates(v.toLowerCase())) return true;
|
|
155
|
+
|
|
116
156
|
return false;
|
|
117
157
|
}
|
|
118
158
|
|
|
@@ -204,6 +244,38 @@ function scanContent(content, options = {}) {
|
|
|
204
244
|
if (shannonEntropy(tail) < 2.0) continue; // clearly non-random
|
|
205
245
|
}
|
|
206
246
|
|
|
247
|
+
if (descriptor.hashContextGated) {
|
|
248
|
+
// Long hex runs are flagged as suspected secrets (Twilio token, webhook
|
|
249
|
+
// signing secret, SHA-style digest) EXCEPT when they sit in an integrity /
|
|
250
|
+
// checksum / lockfile / git-sha context — those are legitimate hashes, not
|
|
251
|
+
// leaked credentials. Reuse HASH_CONTEXT_PATTERN over a window around the
|
|
252
|
+
// match so package-lock integrity:, "resolved" tarball #sha, "checksum",
|
|
253
|
+
// and 40/64-hex git shas are NOT false-positived. A fully repeated/obvious
|
|
254
|
+
// placeholder hex (deadbeef…, 000…) is also allowlisted.
|
|
255
|
+
if (isAllowlistPlaceholder(matched)) continue;
|
|
256
|
+
if (isLockfilePath(filePath)) continue;
|
|
257
|
+
// Canonical digest lengths — git SHA-1 (40) and SHA-256 (64) — are
|
|
258
|
+
// overwhelmingly legitimate hashes (commit refs, file checksums, content
|
|
259
|
+
// digests) and appear bare in changelogs/docs/lockfiles. Treating every
|
|
260
|
+
// isolated 40/64-hex run as a leak would false-positive on the entire git
|
|
261
|
+
// ecosystem, so these exact lengths are hash-shaped by default. The
|
|
262
|
+
// headline real-secret case (Twilio auth token = 32-hex) and other
|
|
263
|
+
// non-digest lengths (33–39, 41–63) are NOT standard digests and stay
|
|
264
|
+
// flagged. A leaked literal hash secret of EXACTLY 40/64 hex is the
|
|
265
|
+
// accepted blind spot of this length-based heuristic (documented tradeoff
|
|
266
|
+
// favouring zero false-positives on git/checksum hashes).
|
|
267
|
+
const hexLen = matched.length;
|
|
268
|
+
if (hexLen === 40 || hexLen === 64) continue;
|
|
269
|
+
// For non-canonical lengths, allowlist only when the SURROUNDING context
|
|
270
|
+
// carries a hash marker (integrity:, sha256-, "resolved", "checksum"). The
|
|
271
|
+
// window is widened on the left so a marker earlier on the line
|
|
272
|
+
// (e.g. `"resolved": "https://…/x.tgz#<hex>"`) is still seen.
|
|
273
|
+
const mIdx = text.indexOf(matched);
|
|
274
|
+
const before = text.slice(Math.max(0, mIdx - 64), mIdx);
|
|
275
|
+
const after = text.slice(mIdx + matched.length, mIdx + matched.length + 4);
|
|
276
|
+
if (HASH_CONTEXT_PATTERN.test(before + ' ' + after)) continue;
|
|
277
|
+
}
|
|
278
|
+
|
|
207
279
|
findings.push({ name: descriptor.name, redacted: redactMatch(matched), kind: 'pattern' });
|
|
208
280
|
}
|
|
209
281
|
|
|
@@ -53,7 +53,7 @@ Localização: `.sinapse-ai/development/agents/`
|
|
|
53
53
|
| squad-courses | `@courses-orqx` | Cursos, mentorias, lançamento |
|
|
54
54
|
| squad-storytelling | `@storytelling-orqx` | Pitch, narrativa |
|
|
55
55
|
| squad-council | `@council-orqx` | Conselho estratégico (mental models) |
|
|
56
|
-
| claude-code-mastery | `@
|
|
56
|
+
| claude-code-mastery | `@swarm-orqx` | Claude Code mastery (hooks, MCP, skills) |
|
|
57
57
|
|
|
58
58
|
## Como descobrir agentes de um squad
|
|
59
59
|
|
|
@@ -27,13 +27,13 @@
|
|
|
27
27
|
| +------------------------------------------------------------+ |
|
|
28
28
|
| | Agent Ecosystem | |
|
|
29
29
|
| | | |
|
|
30
|
-
| | Core (12 agentes) Squads (
|
|
30
|
+
| | Core (12 agentes) Squads (17 dominios) | |
|
|
31
31
|
| | +--------+ +--------+ +--------+ +--------+ | |
|
|
32
32
|
| | | Pixel | | Litmus | | Brand | | Growth | ... | |
|
|
33
33
|
| | | (dev) | | (qa) | | Squad | | Squad | | |
|
|
34
34
|
| | +--------+ +--------+ +--------+ +--------+ | |
|
|
35
|
-
| | +--------+ +--------+
|
|
36
|
-
| | |Stratum | |Pipeline| em
|
|
35
|
+
| | +--------+ +--------+ 160 especialistas | |
|
|
36
|
+
| | |Stratum | |Pipeline| em 17 squads tematicos | |
|
|
37
37
|
| | | (arch) | |(devops)| | |
|
|
38
38
|
| | +--------+ +--------+ | |
|
|
39
39
|
| +------------------------------------------------------------+ |
|
|
@@ -54,7 +54,7 @@
|
|
|
54
54
|
Agentes sao personas especializadas com expertise, comandos e responsabilidades definidas. Cada agente opera dentro de um escopo de autoridade exclusivo.
|
|
55
55
|
|
|
56
56
|
- **12 agentes core** cobrem o ciclo completo de desenvolvimento de software
|
|
57
|
-
- **
|
|
57
|
+
- **160 agentes em 17 squads** expandem para dominios especializados
|
|
58
58
|
- Cada agente tem persona (nome, estilo), comandos (`*help`, `*task`) e dependencias
|
|
59
59
|
|
|
60
60
|
Ativacao: `@agent-name` ou `/SINAPSE:agents:agent-name`
|
|
@@ -22,9 +22,9 @@ Essa decisao nao e estetica --- e estrutural. Agentes de IA operam em terminais.
|
|
|
22
22
|
|
|
23
23
|
**Por que artigos formais com enforcement automatico?**
|
|
24
24
|
|
|
25
|
-
O SINAPSE possui 10 artigos constitucionais que governam o comportamento de todos os
|
|
25
|
+
O SINAPSE possui 10 artigos constitucionais que governam o comportamento de todos os 172 agentes. Cada artigo tem severidade definida (NON-NEGOTIABLE ou MUST) e gates automaticos que bloqueiam violacoes deterministicamente.
|
|
26
26
|
|
|
27
|
-
A alternativa --- guidelines aspiracionais --- falha em escala. Quando
|
|
27
|
+
A alternativa --- guidelines aspiracionais --- falha em escala. Quando 172 agentes operam em 17 dominios, regras que dependem de "boa vontade" sao violadas silenciosamente. Gates automaticos (hooks pre-commit, pre-push, validacoes de story) garantem que violacoes sao detectadas e bloqueadas antes de causar dano.
|
|
28
28
|
|
|
29
29
|
**Exemplo:** o hook `enforce-git-push-authority.sh` bloqueia qualquer agente que nao seja @devops (Pipeline) de executar `git push`. Nao e uma sugestao --- e um bloqueio deterministico.
|
|
30
30
|
|
|
@@ -66,9 +66,9 @@ A razao e separacao de responsabilidades em escala. Um orquestrador que "faz tud
|
|
|
66
66
|
|
|
67
67
|
## 5. Escala do Ecossistema de Agentes
|
|
68
68
|
|
|
69
|
-
**Por que
|
|
69
|
+
**Por que 172 agentes em 17 dominios?**
|
|
70
70
|
|
|
71
|
-
O SINAPSE nao e um agente generalista. E um ecossistema de
|
|
71
|
+
O SINAPSE nao e um agente generalista. E um ecossistema de 160 especialistas organizados em 17 squads tematicos. Cada agente tem persona, expertise e comandos especificos para seu dominio.
|
|
72
72
|
|
|
73
73
|
Essa arquitetura permite:
|
|
74
74
|
|
|
@@ -76,13 +76,13 @@ Essa arquitetura permite:
|
|
|
76
76
|
- **Contexto otimizado:** cada agente carrega apenas as dependencias necessarias para seu dominio, preservando a janela de contexto para o trabalho real.
|
|
77
77
|
- **Escalabilidade horizontal:** novos dominios sao adicionados como squads independentes, sem impactar o core.
|
|
78
78
|
|
|
79
|
-
Os 12 agentes core cobrem o ciclo completo de desenvolvimento de software. Os
|
|
79
|
+
Os 12 agentes core cobrem o ciclo completo de desenvolvimento de software. Os 17 squads expandem para dominios como branding, growth, financeiro, cybersecurity e mais.
|
|
80
80
|
|
|
81
81
|
| Camada | Agentes | Funcao |
|
|
82
82
|
|--------|---------|--------|
|
|
83
83
|
| Core | 12 agentes | Desenvolvimento de software completo |
|
|
84
|
-
| Squads |
|
|
85
|
-
| Total |
|
|
84
|
+
| Squads | 160 agentes em 17 dominios | Especializacao por dominio |
|
|
85
|
+
| Total | 172 agentes | Ecossistema completo |
|
|
86
86
|
|
|
87
87
|
> Constitution Art. VII --- metricas exatas, sempre sincronizadas
|
|
88
88
|
|
|
@@ -178,10 +178,10 @@ Isso garante que o framework mantem coerencia e qualidade mesmo com contribuicoe
|
|
|
178
178
|
| Principio | Por que existe | Enforcement |
|
|
179
179
|
|-----------|---------------|-------------|
|
|
180
180
|
| CLI First | Agentes operam em terminais | Hook WARN |
|
|
181
|
-
| Governanca Constitucional |
|
|
181
|
+
| Governanca Constitucional | 172 agentes precisam de regras deterministicas | 10 artigos + gates |
|
|
182
182
|
| Documentation-First | Codigo sem spec gera retrabalho | Hook BLOCK |
|
|
183
183
|
| Delegacao Obrigatoria | Separacao de responsabilidades em escala | Hook BLOCK |
|
|
184
|
-
| Ecossistema
|
|
184
|
+
| Ecossistema 172 Agentes | Especializacao profunda por dominio | Art. VII metricas |
|
|
185
185
|
| Hooks Deterministicos | Guidelines aspiracionais falham em escala | 5+ hooks ativos |
|
|
186
186
|
| Colaboracao Segura | Usuarios nao sao git experts | Auto-branch/sync/PR |
|
|
187
187
|
| Seguranca por Default | Licoes de vazamentos reais | 25 blockers |
|
package/docs/getting-started.md
CHANGED
|
@@ -65,4 +65,4 @@ npx sinapse-ai uninstall # remove tudo
|
|
|
65
65
|
|
|
66
66
|
---
|
|
67
67
|
|
|
68
|
-
*Próxima leitura sugerida: [Agent Reference Guide](agent-reference-guide.md) pra ver todos os
|
|
68
|
+
*Próxima leitura sugerida: [Agent Reference Guide](agent-reference-guide.md) pra ver todos os 172 agentes disponíveis.*
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
# Agent Reference — SINAPSE-AI
|
|
2
2
|
|
|
3
3
|
> Reference for the **10 framework agents** ship-loaded by SINAPSE-AI.
|
|
4
|
-
> For the wider squad agent universe (
|
|
4
|
+
> For the wider squad agent universe (172 agents across 17 squads), see
|
|
5
5
|
> the squads source-of-truth at `squads/` or run
|
|
6
6
|
> `npx sinapse-ai list` after install.
|
|
7
7
|
|
|
@@ -101,7 +101,7 @@ Resposta esperada ao ativar atalho:
|
|
|
101
101
|
2. Mostrar 3-6 comandos principais (`*help`, etc.)
|
|
102
102
|
3. Seguir na persona do agente
|
|
103
103
|
|
|
104
|
-
## Orquestradores (
|
|
104
|
+
## Orquestradores (18 orqx: 17 squad + 1 master)
|
|
105
105
|
|
|
106
106
|
Cada orqx coordena um squad completo de agentes especializados. Ative via `/skills` > `sinapse-<orqx>` ou `@<orqx>`:
|
|
107
107
|
|
|
@@ -124,14 +124,13 @@ Cada orqx coordena um squad completo de agentes especializados. Ative via `/skil
|
|
|
124
124
|
| `courses-orqx` | Courses | Curriculos, assessments, launch |
|
|
125
125
|
| `cloning-orqx` | Cloning | Clonagem cognitiva, mind synthesis |
|
|
126
126
|
| `council-orqx` | Council | Advisors estrategicos (Munger, Dalio, Thiel) |
|
|
127
|
-
| `
|
|
128
|
-
| `swarm-orqx` | Mastery | Dominio avancado do Claude Code |
|
|
127
|
+
| `swarm-orqx` | Mastery | Claude Code, MCP, integracao avancada |
|
|
129
128
|
|
|
130
129
|
Agents de arquivo: `.codex/agents/<orqx>.md` ou `.claude/agents/<orqx>.md`
|
|
131
130
|
|
|
132
|
-
## Agentes Especializados (
|
|
131
|
+
## Agentes Especializados (160)
|
|
133
132
|
|
|
134
|
-
Existem
|
|
133
|
+
Existem 172 agentes organizados em 17 squads (160 em squads + 12 framework agents, incluindo o master orchestrator). Eles sao acessiveis via:
|
|
135
134
|
- `.codex/agents/<agent-name>.md` - arquivo direto
|
|
136
135
|
- Chamada interna pelo orqx do squad
|
|
137
136
|
|
|
@@ -1,7 +1,14 @@
|
|
|
1
1
|
# Sub-Orqx 3-Level Pattern
|
|
2
2
|
|
|
3
|
-
> **Status:**
|
|
4
|
-
>
|
|
3
|
+
> **Status:** SUPERSEDED (2026-05-15 squad rename). This document describes the
|
|
4
|
+
> historical 3-level topology that existed BEFORE `claude-code-mastery` was
|
|
5
|
+
> flattened. The former parent layer `claude-orqx` was retired (see
|
|
6
|
+
> `squads/claude-code-mastery/_deprecated/`) and `swarm-orqx` (Nexus) was
|
|
7
|
+
> promoted to be the squad orchestrator itself. The current topology for
|
|
8
|
+
> `claude-code-mastery` is the standard 2-level model: `sinapse-orqx` →
|
|
9
|
+
> `swarm-orqx` → specialists. The `tools-orqx` sub-layer and `db-sage` were
|
|
10
|
+
> also deprecated. Retained for historical/architectural context only — do NOT
|
|
11
|
+
> treat the diagrams below as current routing truth.
|
|
5
12
|
> **Related:** Constitution Article XI (Conservative Default)
|
|
6
13
|
|
|
7
14
|
## Overview
|
|
@@ -21,18 +28,14 @@ sinapse-orqx (Imperator)
|
|
|
21
28
|
```
|
|
22
29
|
sinapse-orqx (Imperator)
|
|
23
30
|
|
|
|
24
|
-
+--
|
|
31
|
+
+-- swarm-orqx (squad orchestrator) # historically: claude-orqx (retired)
|
|
25
32
|
|
|
|
26
|
-
+--
|
|
27
|
-
|
|
|
28
|
-
|
|
|
29
|
-
| project-integrator, roadmap-sentinel
|
|
33
|
+
+-- (in the historical 3-level model, sub-orchestrators sat here:
|
|
34
|
+
| swarm-orqx for orchestration specialists, tools-orqx for
|
|
35
|
+
| tool-crafters — both since collapsed/retired)
|
|
30
36
|
|
|
|
31
|
-
+--
|
|
32
|
-
|
|
33
|
-
| +-- skill-craftsman, db-sage
|
|
34
|
-
|
|
|
35
|
-
+-- (direct specialists, when domain is narrow enough to skip sub-orqx)
|
|
37
|
+
+-- hooks-architect, mcp-integrator, config-engineer,
|
|
38
|
+
project-integrator, roadmap-sentinel, skill-craftsman
|
|
36
39
|
```
|
|
37
40
|
|
|
38
41
|
## Why This Exists
|
|
@@ -66,10 +69,9 @@ Only add a sub-orqx layer when ALL of these hold:
|
|
|
66
69
|
```
|
|
67
70
|
User: "Configure hooks + MCP servers + settings for this project"
|
|
68
71
|
-> sinapse-orqx
|
|
69
|
-
->
|
|
70
|
-
-> swarm-orqx (detects multi-specialist parallel work)
|
|
72
|
+
-> swarm-orqx (squad orchestrator; detects multi-specialist parallel work)
|
|
71
73
|
-> hooks-architect | mcp-integrator | config-engineer (parallel)
|
|
72
|
-
-> results merged back through swarm-orqx ->
|
|
74
|
+
-> results merged back through swarm-orqx -> user
|
|
73
75
|
```
|
|
74
76
|
|
|
75
77
|
### tools-orqx routing
|
|
@@ -77,9 +79,9 @@ User: "Configure hooks + MCP servers + settings for this project"
|
|
|
77
79
|
```
|
|
78
80
|
User: "Create a reusable skill for X and document the DB access pattern"
|
|
79
81
|
-> sinapse-orqx
|
|
80
|
-
->
|
|
81
|
-
->
|
|
82
|
-
|
|
82
|
+
-> swarm-orqx (squad orchestrator)
|
|
83
|
+
-> skill-craftsman (skill authoring; the former tools-orqx sub-layer and
|
|
84
|
+
db-sage are retired — DB work now routes via @data-engineer)
|
|
83
85
|
```
|
|
84
86
|
|
|
85
87
|
## Non-Normalization Rule
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "sinapse-ai",
|
|
3
|
-
"version": "1.
|
|
3
|
+
"version": "1.10.0",
|
|
4
4
|
"description": "SINAPSE AI: Framework de orquestracao de IA — 17 squads, 172 agentes especializados",
|
|
5
5
|
"bin": {
|
|
6
6
|
"sinapse": "bin/sinapse.js",
|
|
@@ -53,7 +53,13 @@
|
|
|
53
53
|
"docs/agent-reference-guide.md",
|
|
54
54
|
"docs/TELEMETRY.md",
|
|
55
55
|
"README.md",
|
|
56
|
-
"
|
|
56
|
+
"CHANGELOG.md",
|
|
57
|
+
"LICENSE",
|
|
58
|
+
"!**/__tests__/**",
|
|
59
|
+
"!**/tests/**",
|
|
60
|
+
"!**/*.test.js",
|
|
61
|
+
"!**/*.spec.js",
|
|
62
|
+
".sinapse-ai/development/templates/**"
|
|
57
63
|
],
|
|
58
64
|
"scripts": {
|
|
59
65
|
"format": "prettier --write \"**/*.md\"",
|
|
@@ -331,7 +331,9 @@ function pickValidateScript() {
|
|
|
331
331
|
const script = pickValidateScript();
|
|
332
332
|
if (script) {
|
|
333
333
|
const npmCmd = process.platform === 'win32' ? 'npm.cmd' : 'npm';
|
|
334
|
-
|
|
334
|
+
// shell:true on Windows — spawning npm.cmd without it throws EINVAL (CVE-2024-27980 /
|
|
335
|
+
// Node DEP0190). Args are fixed/literal here, so there is no shell-injection surface.
|
|
336
|
+
const res = spawnSync(npmCmd, ['run', '--silent', script], { stdio: 'inherit', cwd: projectRoot, shell: process.platform === 'win32' });
|
|
335
337
|
if (res.error) {
|
|
336
338
|
process.stderr.write('SINAPSE pre-push: could not run "npm run ' + script + '" — blocking push (fail-closed).\\n');
|
|
337
339
|
process.stderr.write(' ' + res.error.message + '\\n');
|
|
@@ -141,8 +141,29 @@ async function generateVersionJson(options) {
|
|
|
141
141
|
* @param {boolean} replaceRoot - Whether to replace {root} placeholders
|
|
142
142
|
* @returns {Promise<boolean>} Success status
|
|
143
143
|
*/
|
|
144
|
-
|
|
144
|
+
/**
|
|
145
|
+
* Predicate: is this destination a user-owned L3 file that must survive a
|
|
146
|
+
* re-install? Matches the boundary contract (core-config.yaml + agent
|
|
147
|
+
* MEMORY.md are L3 "mutable / user-owned") and the README promise that
|
|
148
|
+
* re-running install is an idempotent upsert that preserves customizations.
|
|
149
|
+
* @param {string} destPath - Absolute destination path
|
|
150
|
+
* @returns {boolean}
|
|
151
|
+
*/
|
|
152
|
+
function isUserOwnedL3(destPath) {
|
|
153
|
+
const norm = String(destPath).replace(/\\/g, '/');
|
|
154
|
+
if (norm.endsWith('/.sinapse-ai/core-config.yaml')) return true;
|
|
155
|
+
if (/\/\.sinapse-ai\/development\/agents\/[^/]+\/MEMORY\.md$/.test(norm)) return true;
|
|
156
|
+
return false;
|
|
157
|
+
}
|
|
158
|
+
|
|
159
|
+
async function copyFileWithRootReplacement(sourcePath, destPath, replaceRoot = true, preserveExisting = null) {
|
|
145
160
|
try {
|
|
161
|
+
// Preserve user-owned L3 files (core-config.yaml, agent MEMORY.md) when they
|
|
162
|
+
// already exist — a re-install must not silently wipe the user's config.
|
|
163
|
+
if (preserveExisting && preserveExisting(destPath) && await fs.pathExists(destPath)) {
|
|
164
|
+
return 'preserved';
|
|
165
|
+
}
|
|
166
|
+
|
|
146
167
|
await fs.ensureDir(path.dirname(destPath));
|
|
147
168
|
|
|
148
169
|
// Check if file needs {root} replacement (.md, .yaml, .yml)
|
|
@@ -171,7 +192,7 @@ async function copyFileWithRootReplacement(sourcePath, destPath, replaceRoot = t
|
|
|
171
192
|
* @param {Function} onProgress - Progress callback
|
|
172
193
|
* @returns {Promise<string[]>} List of copied files (relative paths)
|
|
173
194
|
*/
|
|
174
|
-
async function copyDirectoryWithRootReplacement(sourceDir, destDir, onProgress = null) {
|
|
195
|
+
async function copyDirectoryWithRootReplacement(sourceDir, destDir, onProgress = null, preserveExisting = null) {
|
|
175
196
|
const copiedFiles = [];
|
|
176
197
|
|
|
177
198
|
if (!await fs.pathExists(sourceDir)) {
|
|
@@ -193,11 +214,13 @@ async function copyDirectoryWithRootReplacement(sourceDir, destDir, onProgress =
|
|
|
193
214
|
}
|
|
194
215
|
|
|
195
216
|
if (item.isDirectory()) {
|
|
196
|
-
const subFiles = await copyDirectoryWithRootReplacement(sourcePath, destPath, onProgress);
|
|
217
|
+
const subFiles = await copyDirectoryWithRootReplacement(sourcePath, destPath, onProgress, preserveExisting);
|
|
197
218
|
copiedFiles.push(...subFiles);
|
|
198
219
|
} else {
|
|
199
|
-
const success = await copyFileWithRootReplacement(sourcePath, destPath);
|
|
200
|
-
|
|
220
|
+
const success = await copyFileWithRootReplacement(sourcePath, destPath, true, preserveExisting);
|
|
221
|
+
// Only count files actually written; 'preserved' (existing user-owned L3)
|
|
222
|
+
// and false (error) must not inflate the installed-files manifest.
|
|
223
|
+
if (success === true) {
|
|
201
224
|
copiedFiles.push(path.relative(destDir, destPath));
|
|
202
225
|
if (onProgress) {
|
|
203
226
|
onProgress({ file: item.name, copied: true });
|
|
@@ -290,6 +313,7 @@ async function installSinapseCore(options = {}) {
|
|
|
290
313
|
folderSource,
|
|
291
314
|
folderDest,
|
|
292
315
|
onProgress,
|
|
316
|
+
isUserOwnedL3,
|
|
293
317
|
);
|
|
294
318
|
|
|
295
319
|
if (copiedFiles.length > 0) {
|
|
@@ -306,8 +330,8 @@ async function installSinapseCore(options = {}) {
|
|
|
306
330
|
|
|
307
331
|
if (await fs.pathExists(fileSource)) {
|
|
308
332
|
spinner.text = `Copying ${file}...`;
|
|
309
|
-
const success = await copyFileWithRootReplacement(fileSource, fileDest);
|
|
310
|
-
if (success) {
|
|
333
|
+
const success = await copyFileWithRootReplacement(fileSource, fileDest, true, isUserOwnedL3);
|
|
334
|
+
if (success === true) {
|
|
311
335
|
result.installedFiles.push(file);
|
|
312
336
|
}
|
|
313
337
|
}
|
|
@@ -495,6 +519,7 @@ module.exports = {
|
|
|
495
519
|
getSinapseCoreSourcePath,
|
|
496
520
|
copyFileWithRootReplacement,
|
|
497
521
|
copyDirectoryWithRootReplacement,
|
|
522
|
+
isUserOwnedL3,
|
|
498
523
|
generateVersionJson,
|
|
499
524
|
generateFileHashes,
|
|
500
525
|
deliverCodexRootFiles,
|
|
@@ -929,7 +929,12 @@ async function linkGeminiExtension(projectRoot) {
|
|
|
929
929
|
return { status: 'skipped', reason: 'manifest-not-found' };
|
|
930
930
|
}
|
|
931
931
|
|
|
932
|
-
|
|
932
|
+
// On Windows, `gemini` is a .cmd/.ps1 shim — spawnSync without a shell throws
|
|
933
|
+
// EINVAL. Run through the shell on win32 so the shim resolves.
|
|
934
|
+
const versionCheck = spawnSync('gemini', ['--version'], {
|
|
935
|
+
encoding: 'utf8',
|
|
936
|
+
shell: process.platform === 'win32',
|
|
937
|
+
});
|
|
933
938
|
if (versionCheck.status !== 0) {
|
|
934
939
|
return { status: 'skipped', reason: 'gemini-cli-not-available' };
|
|
935
940
|
}
|
|
@@ -938,6 +943,7 @@ async function linkGeminiExtension(projectRoot) {
|
|
|
938
943
|
cwd: projectRoot,
|
|
939
944
|
encoding: 'utf8',
|
|
940
945
|
timeout: 30000,
|
|
946
|
+
shell: process.platform === 'win32',
|
|
941
947
|
});
|
|
942
948
|
|
|
943
949
|
if (linkResult.status === 0) {
|
|
@@ -952,6 +958,7 @@ async function linkGeminiExtension(projectRoot) {
|
|
|
952
958
|
cwd: projectRoot,
|
|
953
959
|
encoding: 'utf8',
|
|
954
960
|
timeout: 30000,
|
|
961
|
+
shell: process.platform === 'win32',
|
|
955
962
|
});
|
|
956
963
|
|
|
957
964
|
if (uninstall.status !== 0) {
|
|
@@ -962,6 +969,7 @@ async function linkGeminiExtension(projectRoot) {
|
|
|
962
969
|
cwd: projectRoot,
|
|
963
970
|
encoding: 'utf8',
|
|
964
971
|
timeout: 30000,
|
|
972
|
+
shell: process.platform === 'win32',
|
|
965
973
|
});
|
|
966
974
|
|
|
967
975
|
if (linkResult.status === 0) {
|