spec-gen-cli 1.2.2 → 1.2.4
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/README.md +272 -25
- package/dist/api/generate.d.ts.map +1 -1
- package/dist/api/generate.js +11 -7
- package/dist/api/generate.js.map +1 -1
- package/dist/api/run.d.ts.map +1 -1
- package/dist/api/run.js +5 -3
- package/dist/api/run.js.map +1 -1
- package/dist/api/types.d.ts +4 -4
- package/dist/api/types.d.ts.map +1 -1
- package/dist/cli/commands/analyze.d.ts.map +1 -1
- package/dist/cli/commands/analyze.js +101 -41
- package/dist/cli/commands/analyze.js.map +1 -1
- package/dist/cli/commands/generate.d.ts.map +1 -1
- package/dist/cli/commands/generate.js +28 -23
- package/dist/cli/commands/generate.js.map +1 -1
- package/dist/cli/commands/mcp.d.ts +353 -10
- package/dist/cli/commands/mcp.d.ts.map +1 -1
- package/dist/cli/commands/mcp.js +241 -48
- package/dist/cli/commands/mcp.js.map +1 -1
- package/dist/cli/commands/view.d.ts.map +1 -1
- package/dist/cli/commands/view.js +33 -4
- package/dist/cli/commands/view.js.map +1 -1
- package/dist/constants.d.ts +11 -0
- package/dist/constants.d.ts.map +1 -1
- package/dist/constants.js +11 -0
- package/dist/constants.js.map +1 -1
- package/dist/core/analyzer/artifact-generator.d.ts.map +1 -1
- package/dist/core/analyzer/artifact-generator.js +11 -3
- package/dist/core/analyzer/artifact-generator.js.map +1 -1
- package/dist/core/analyzer/ast-chunker.d.ts +24 -0
- package/dist/core/analyzer/ast-chunker.d.ts.map +1 -0
- package/dist/core/analyzer/ast-chunker.js +198 -0
- package/dist/core/analyzer/ast-chunker.js.map +1 -0
- package/dist/core/analyzer/call-graph.d.ts +52 -5
- package/dist/core/analyzer/call-graph.d.ts.map +1 -1
- package/dist/core/analyzer/call-graph.js +769 -48
- package/dist/core/analyzer/call-graph.js.map +1 -1
- package/dist/core/analyzer/code-shaper.d.ts.map +1 -1
- package/dist/core/analyzer/code-shaper.js +5 -0
- package/dist/core/analyzer/code-shaper.js.map +1 -1
- package/dist/core/analyzer/codebase-digest.d.ts +40 -0
- package/dist/core/analyzer/codebase-digest.d.ts.map +1 -0
- package/dist/core/analyzer/codebase-digest.js +194 -0
- package/dist/core/analyzer/codebase-digest.js.map +1 -0
- package/dist/core/analyzer/cpp-header-resolver.d.ts +30 -0
- package/dist/core/analyzer/cpp-header-resolver.d.ts.map +1 -0
- package/dist/core/analyzer/cpp-header-resolver.js +71 -0
- package/dist/core/analyzer/cpp-header-resolver.js.map +1 -0
- package/dist/core/analyzer/dependency-graph.d.ts +19 -0
- package/dist/core/analyzer/dependency-graph.d.ts.map +1 -1
- package/dist/core/analyzer/dependency-graph.js +76 -0
- package/dist/core/analyzer/dependency-graph.js.map +1 -1
- package/dist/core/analyzer/duplicate-detector.d.ts.map +1 -1
- package/dist/core/analyzer/duplicate-detector.js +7 -1
- package/dist/core/analyzer/duplicate-detector.js.map +1 -1
- package/dist/core/analyzer/function-registry-trie.d.ts +21 -0
- package/dist/core/analyzer/function-registry-trie.d.ts.map +1 -0
- package/dist/core/analyzer/function-registry-trie.js +39 -0
- package/dist/core/analyzer/function-registry-trie.js.map +1 -0
- package/dist/core/analyzer/import-resolver-bridge.d.ts +25 -0
- package/dist/core/analyzer/import-resolver-bridge.d.ts.map +1 -0
- package/dist/core/analyzer/import-resolver-bridge.js +99 -0
- package/dist/core/analyzer/import-resolver-bridge.js.map +1 -0
- package/dist/core/analyzer/signature-extractor.d.ts.map +1 -1
- package/dist/core/analyzer/signature-extractor.js +131 -3
- package/dist/core/analyzer/signature-extractor.js.map +1 -1
- package/dist/core/analyzer/subgraph-extractor.d.ts +10 -2
- package/dist/core/analyzer/subgraph-extractor.d.ts.map +1 -1
- package/dist/core/analyzer/subgraph-extractor.js +25 -7
- package/dist/core/analyzer/subgraph-extractor.js.map +1 -1
- package/dist/core/analyzer/type-inference-engine.d.ts +23 -0
- package/dist/core/analyzer/type-inference-engine.d.ts.map +1 -0
- package/dist/core/analyzer/type-inference-engine.js +130 -0
- package/dist/core/analyzer/type-inference-engine.js.map +1 -0
- package/dist/core/analyzer/vector-index.d.ts +35 -6
- package/dist/core/analyzer/vector-index.d.ts.map +1 -1
- package/dist/core/analyzer/vector-index.js +308 -54
- package/dist/core/analyzer/vector-index.js.map +1 -1
- package/dist/core/generator/spec-pipeline.d.ts +31 -11
- package/dist/core/generator/spec-pipeline.d.ts.map +1 -1
- package/dist/core/generator/spec-pipeline.js +170 -39
- package/dist/core/generator/spec-pipeline.js.map +1 -1
- package/dist/core/generator/stages/stage2-entities.d.ts.map +1 -1
- package/dist/core/generator/stages/stage2-entities.js +2 -1
- package/dist/core/generator/stages/stage2-entities.js.map +1 -1
- package/dist/core/generator/stages/stage3-services.d.ts.map +1 -1
- package/dist/core/generator/stages/stage3-services.js +2 -1
- package/dist/core/generator/stages/stage3-services.js.map +1 -1
- package/dist/core/generator/stages/stage4-api.d.ts.map +1 -1
- package/dist/core/generator/stages/stage4-api.js +2 -1
- package/dist/core/generator/stages/stage4-api.js.map +1 -1
- package/dist/core/generator/stages/stage5-architecture.d.ts +2 -1
- package/dist/core/generator/stages/stage5-architecture.d.ts.map +1 -1
- package/dist/core/generator/stages/stage5-architecture.js +15 -3
- package/dist/core/generator/stages/stage5-architecture.js.map +1 -1
- package/dist/core/services/chat-agent.d.ts +5 -0
- package/dist/core/services/chat-agent.d.ts.map +1 -1
- package/dist/core/services/chat-agent.js +14 -0
- package/dist/core/services/chat-agent.js.map +1 -1
- package/dist/core/services/chat-tools.d.ts.map +1 -1
- package/dist/core/services/chat-tools.js +172 -50
- package/dist/core/services/chat-tools.js.map +1 -1
- package/dist/core/services/llm-service.d.ts +23 -1
- package/dist/core/services/llm-service.d.ts.map +1 -1
- package/dist/core/services/llm-service.js +94 -2
- package/dist/core/services/llm-service.js.map +1 -1
- package/dist/core/services/mcp-handlers/analysis.d.ts +12 -0
- package/dist/core/services/mcp-handlers/analysis.d.ts.map +1 -1
- package/dist/core/services/mcp-handlers/analysis.js +138 -2
- package/dist/core/services/mcp-handlers/analysis.js.map +1 -1
- package/dist/core/services/mcp-handlers/graph.d.ts +21 -1
- package/dist/core/services/mcp-handlers/graph.d.ts.map +1 -1
- package/dist/core/services/mcp-handlers/graph.js +142 -2
- package/dist/core/services/mcp-handlers/graph.js.map +1 -1
- package/dist/core/services/mcp-handlers/orient.d.ts +17 -0
- package/dist/core/services/mcp-handlers/orient.d.ts.map +1 -0
- package/dist/core/services/mcp-handlers/orient.js +200 -0
- package/dist/core/services/mcp-handlers/orient.js.map +1 -0
- package/dist/core/services/mcp-handlers/semantic.d.ts +18 -4
- package/dist/core/services/mcp-handlers/semantic.d.ts.map +1 -1
- package/dist/core/services/mcp-handlers/semantic.js +161 -17
- package/dist/core/services/mcp-handlers/semantic.js.map +1 -1
- package/dist/core/services/mcp-handlers/utils.d.ts +43 -0
- package/dist/core/services/mcp-handlers/utils.d.ts.map +1 -1
- package/dist/core/services/mcp-handlers/utils.js +66 -1
- package/dist/core/services/mcp-handlers/utils.js.map +1 -1
- package/dist/core/services/mcp-watcher.d.ts +41 -0
- package/dist/core/services/mcp-watcher.d.ts.map +1 -0
- package/dist/core/services/mcp-watcher.js +177 -0
- package/dist/core/services/mcp-watcher.js.map +1 -0
- package/dist/types/index.d.ts +2 -2
- package/dist/types/index.d.ts.map +1 -1
- package/dist/types/pipeline.d.ts +7 -0
- package/dist/types/pipeline.d.ts.map +1 -1
- package/package.json +4 -2
- package/src/viewer/InteractiveGraphViewer.jsx +39 -10
- package/src/viewer/components/ChatPanel.jsx +8 -5
- package/src/viewer/components/ClassGraph.jsx +782 -0
- package/src/viewer/components/FlatGraph.jsx +3 -3
- package/src/viewer/utils/graph-helpers.js +9 -1
- package/src/viewer/utils/themes.js +36 -0
package/README.md
CHANGED
|
@@ -6,7 +6,7 @@ Reverse-engineer [OpenSpec](https://github.com/Fission-AI/OpenSpec) specificatio
|
|
|
6
6
|
|
|
7
7
|
Most software has no specification. The code is the spec, scattered across thousands of files, tribal knowledge, and stale documentation. Tools like `openspec init` create empty scaffolding, but someone still has to write everything. By the time specs are written manually, the code has already changed.
|
|
8
8
|
|
|
9
|
-
spec-gen automates this. It analyzes your codebase through static analysis, generates structured specifications using an LLM, and continuously detects when code and specs fall out of sync.
|
|
9
|
+
spec-gen automates this. It analyzes your codebase through static analysis, generates structured specifications using an LLM, and continuously detects when code and specs fall out of sync. It also exposes the analysis as an MCP server so AI agents can navigate your codebase with GraphRAG-style retrieval — semantic search combined with call-graph expansion and spec-linked peer discovery.
|
|
10
10
|
|
|
11
11
|
## Quick Start
|
|
12
12
|
|
|
@@ -89,9 +89,10 @@ npm run dev
|
|
|
89
89
|
|
|
90
90
|
Scans your codebase using pure static analysis:
|
|
91
91
|
- Walks the directory tree, respects .gitignore, scores files by significance
|
|
92
|
-
- Parses imports and exports to build a dependency graph (TypeScript, JavaScript, Python, Go, Rust, Ruby, Java, C
|
|
92
|
+
- Parses imports and exports to build a dependency graph (TypeScript, JavaScript, Python, Go, Rust, Ruby, Java, C++, Swift)
|
|
93
93
|
- Detects HTTP cross-language edges: matches `fetch`/`axios`/`ky`/`got` calls in JS/TS files to FastAPI/Flask/Django route definitions in Python files, creating cross-language dependency edges with `exact`, `path`, or `fuzzy` confidence
|
|
94
94
|
- Resolves Python absolute imports (`from services.retriever import X`) to local files
|
|
95
|
+
- Synthesizes cross-file dependency edges from call-graph data for languages without file-level imports (Swift, C++), so the dependency graph and viewer are meaningful even in single-module projects
|
|
95
96
|
- Clusters related files into structural business domains automatically
|
|
96
97
|
- Produces structured context that makes LLM generation more accurate
|
|
97
98
|
|
|
@@ -308,14 +309,18 @@ spec-gen drift --no-color # Plain output for CI logs
|
|
|
308
309
|
|
|
309
310
|
## LLM Providers
|
|
310
311
|
|
|
311
|
-
spec-gen supports
|
|
312
|
+
spec-gen supports eight providers. The default is Anthropic Claude.
|
|
312
313
|
|
|
313
314
|
| Provider | `provider` value | API key env var | Default model |
|
|
314
315
|
|----------|-----------------|-----------------|---------------|
|
|
315
316
|
| Anthropic Claude | `anthropic` *(default)* | `ANTHROPIC_API_KEY` | `claude-sonnet-4-20250514` |
|
|
316
317
|
| OpenAI | `openai` | `OPENAI_API_KEY` | `gpt-4o` |
|
|
317
318
|
| OpenAI-compatible *(Mistral, Groq, Ollama...)* | `openai-compat` | `OPENAI_COMPAT_API_KEY` | `mistral-large-latest` |
|
|
319
|
+
| GitHub Copilot *(via copilot-api proxy)* | `copilot` | *(none)* | `gpt-4o` |
|
|
318
320
|
| Google Gemini | `gemini` | `GEMINI_API_KEY` | `gemini-2.0-flash` |
|
|
321
|
+
| Gemini CLI | `gemini-cli` | *(none)* | *(CLI default)* |
|
|
322
|
+
| Claude Code | `claude-code` | *(none)* | *(CLI default)* |
|
|
323
|
+
| Mistral Vibe | `mistral-vibe` | *(none)* | *(CLI default)* |
|
|
319
324
|
|
|
320
325
|
### Selecting a provider
|
|
321
326
|
|
|
@@ -378,6 +383,57 @@ Or in `config.json`:
|
|
|
378
383
|
Works with: Ollama, LM Studio, Mistral AI, Groq, Together AI, LiteLLM, vLLM,
|
|
379
384
|
text-generation-inference, LocalAI, Azure OpenAI, and any `/v1/chat/completions` server.
|
|
380
385
|
|
|
386
|
+
### GitHub Copilot (via copilot-api proxy)
|
|
387
|
+
|
|
388
|
+
Use `provider: "copilot"` to generate specs using your GitHub Copilot subscription via the
|
|
389
|
+
[copilot-api](https://github.com/ericc-ch/copilot-api) proxy, which exposes an OpenAI-compatible
|
|
390
|
+
endpoint from your Copilot credentials.
|
|
391
|
+
|
|
392
|
+
**Setup:**
|
|
393
|
+
1. Install and start the copilot-api proxy:
|
|
394
|
+
```bash
|
|
395
|
+
npx copilot-api
|
|
396
|
+
```
|
|
397
|
+
By default it listens on `http://localhost:4141`.
|
|
398
|
+
|
|
399
|
+
2. Configure spec-gen:
|
|
400
|
+
```json
|
|
401
|
+
{
|
|
402
|
+
"generation": {
|
|
403
|
+
"provider": "copilot",
|
|
404
|
+
"model": "gpt-4o",
|
|
405
|
+
"domains": "auto"
|
|
406
|
+
}
|
|
407
|
+
}
|
|
408
|
+
```
|
|
409
|
+
|
|
410
|
+
**Environment variables** (optional):
|
|
411
|
+
```bash
|
|
412
|
+
export COPILOT_API_BASE_URL=http://localhost:4141/v1 # default
|
|
413
|
+
export COPILOT_API_KEY=copilot # default, only needed if proxy requires auth
|
|
414
|
+
```
|
|
415
|
+
|
|
416
|
+
No API key is required — the copilot-api proxy handles authentication via your GitHub Copilot session.
|
|
417
|
+
|
|
418
|
+
### CLI-based providers (no API key)
|
|
419
|
+
|
|
420
|
+
Three providers route LLM calls through local CLI tools instead of HTTP APIs. No API key or configuration is needed — just have the CLI installed and on your PATH.
|
|
421
|
+
|
|
422
|
+
| Provider | CLI binary | Install |
|
|
423
|
+
|----------|-----------|---------|
|
|
424
|
+
| `claude-code` | `claude` | [Claude Code](https://docs.anthropic.com/en/docs/claude-code) (requires Claude Max/Pro subscription) |
|
|
425
|
+
| `gemini-cli` | `gemini` | [Gemini CLI](https://github.com/google-gemini/gemini-cli) (free tier with Google account) |
|
|
426
|
+
| `mistral-vibe` | `vibe` | [Mistral Vibe](https://github.com/mistralai/mistral-vibe) (standalone binary) |
|
|
427
|
+
|
|
428
|
+
```json
|
|
429
|
+
{
|
|
430
|
+
"generation": {
|
|
431
|
+
"provider": "claude-code",
|
|
432
|
+
"domains": "auto"
|
|
433
|
+
}
|
|
434
|
+
}
|
|
435
|
+
```
|
|
436
|
+
|
|
381
437
|
### Custom base URL for Anthropic or OpenAI
|
|
382
438
|
|
|
383
439
|
To redirect the built-in Anthropic or OpenAI provider to a proxy or self-hosted endpoint:
|
|
@@ -492,7 +548,7 @@ spec-gen analyze [options]
|
|
|
492
548
|
--include <glob> # Additional include patterns
|
|
493
549
|
--exclude <glob> # Additional exclude patterns
|
|
494
550
|
--force # Force re-analysis (bypass 1-hour cache)
|
|
495
|
-
--embed
|
|
551
|
+
--no-embed # Skip building the semantic vector index (index is built by default when embedding is configured)
|
|
496
552
|
--reindex-specs # Re-index OpenSpec specs into the vector index without re-running full analysis
|
|
497
553
|
```
|
|
498
554
|
|
|
@@ -531,6 +587,95 @@ Checks performed:
|
|
|
531
587
|
|
|
532
588
|
Run `spec-gen doctor` whenever setup instructions aren't working — it tells you exactly what to fix and how.
|
|
533
589
|
|
|
590
|
+
## Agent Setup
|
|
591
|
+
|
|
592
|
+
### Passive context vs active tools
|
|
593
|
+
|
|
594
|
+
Agents have two ways to acquire knowledge about your codebase:
|
|
595
|
+
|
|
596
|
+
- **Passive (zero friction):** files referenced in `CLAUDE.md` / `.clinerules` are read automatically at session start, before the agent even processes your first message. No decision required, no tool call to make.
|
|
597
|
+
- **Active (friction):** MCP tools must be consciously selected from a list, called, and their output integrated into context. Even when the information would help, agents often skip this step and read files directly instead — it's always the safe fallback.
|
|
598
|
+
|
|
599
|
+
This means architectural context delivered passively is far more reliably absorbed than context behind a tool call. `spec-gen analyze` generates `.spec-gen/analysis/CODEBASE.md` specifically for this purpose: a compact, agent-optimized digest (~100 lines) that agents absorb at session start without any decision cost.
|
|
600
|
+
|
|
601
|
+
### What CODEBASE.md contains
|
|
602
|
+
|
|
603
|
+
Generated from the static analysis artifacts, it surfaces what an agent most needs before touching code:
|
|
604
|
+
|
|
605
|
+
- **Entry points** — functions with no internal callers (where execution starts)
|
|
606
|
+
- **Critical hubs** — highest fan-in functions (most risky to modify)
|
|
607
|
+
- **Spec domains** — which `openspec/specs/` domains exist and what they cover
|
|
608
|
+
- **Most coupled files** — high in-degree in the dependency graph (touch with care)
|
|
609
|
+
- **God functions / oversized orchestrators** — complexity hotspots
|
|
610
|
+
- **Layer violations** — if any
|
|
611
|
+
|
|
612
|
+
This is structural signal, not prose. It complements `openspec/specs/overview/spec.md`, which provides the functional view (what the system does, what domains exist). Together they give agents both the architectural topology and the business intent.
|
|
613
|
+
|
|
614
|
+
### Setup
|
|
615
|
+
|
|
616
|
+
After running `spec-gen analyze`, wire the generated digest into your agent's context:
|
|
617
|
+
|
|
618
|
+
**Claude Code** — add to `CLAUDE.md`:
|
|
619
|
+
|
|
620
|
+
```markdown
|
|
621
|
+
@.spec-gen/analysis/CODEBASE.md
|
|
622
|
+
@openspec/specs/overview/spec.md
|
|
623
|
+
|
|
624
|
+
## spec-gen MCP tools — when to use them
|
|
625
|
+
|
|
626
|
+
| Situation | Tool |
|
|
627
|
+
|-----------|------|
|
|
628
|
+
| Starting any new task | `orient` — returns functions, files, specs, call paths, and insertion points in one call |
|
|
629
|
+
| Don't know which file/function handles a concept | `search_code` |
|
|
630
|
+
| Need call topology across many files | `get_subgraph` / `analyze_impact` |
|
|
631
|
+
| Planning where to add a feature | `suggest_insertion_points` |
|
|
632
|
+
| Reading a spec before writing code | `get_spec` |
|
|
633
|
+
| Checking if code still matches spec | `check_spec_drift` |
|
|
634
|
+
| Finding spec requirements by meaning | `search_specs` |
|
|
635
|
+
|
|
636
|
+
For all other cases (reading a file, grepping, listing files) use native tools directly.
|
|
637
|
+
```
|
|
638
|
+
|
|
639
|
+
**Cline / Roo Code / Kilocode** — create `.clinerules/spec-gen.md`:
|
|
640
|
+
|
|
641
|
+
```markdown
|
|
642
|
+
# spec-gen
|
|
643
|
+
|
|
644
|
+
spec-gen provides static analysis artifacts and MCP tools to help you navigate this codebase.
|
|
645
|
+
Always use these before writing or modifying code.
|
|
646
|
+
|
|
647
|
+
## Before starting any task
|
|
648
|
+
|
|
649
|
+
- Read `.spec-gen/analysis/CODEBASE.md` — architectural digest: entry points, critical hubs,
|
|
650
|
+
god functions, most-coupled files, and available spec domains. Generated locally by `spec-gen analyze`.
|
|
651
|
+
- Read `openspec/specs/overview/spec.md` — functional domain map: what the system does,
|
|
652
|
+
which domains exist, data-flow requirements.
|
|
653
|
+
|
|
654
|
+
## MCP tools — use these instead of grep/read when exploring
|
|
655
|
+
|
|
656
|
+
- **Orient first**: call `orient` at the start of every task — it returns relevant functions,
|
|
657
|
+
files, specs, call paths, and insertion points in one shot.
|
|
658
|
+
- **Finding code**: use `search_code` when you don't know which file or function handles a concept.
|
|
659
|
+
- **Call topology**: use `get_subgraph` or `analyze_impact` when you need to understand
|
|
660
|
+
how calls flow across multiple files (not just a single file).
|
|
661
|
+
- **Adding a feature**: call `suggest_insertion_points` before deciding where to add code —
|
|
662
|
+
it accounts for the dependency graph, not just filenames.
|
|
663
|
+
- **Reading specs**: call `get_spec <domain>` before writing code in that domain;
|
|
664
|
+
use `search_specs` to find requirements by meaning when you don't know the domain name.
|
|
665
|
+
- **Checking drift**: call `check_spec_drift` after modifying a file to verify it still
|
|
666
|
+
matches its spec — do not skip this step before opening a PR.
|
|
667
|
+
|
|
668
|
+
Use native tools (Read, Grep, Glob) only for cases not covered above.
|
|
669
|
+
```
|
|
670
|
+
|
|
671
|
+
`CODEBASE.md` gives the agent passive architectural context. `overview/spec.md` gives the functional domain map. The table tells it when the passive context isn't enough and an active MCP tool call is warranted.
|
|
672
|
+
|
|
673
|
+
> **Tip:** `spec-gen analyze` prints these snippets after every run as a reminder.
|
|
674
|
+
|
|
675
|
+
> **Note:** `.spec-gen/analysis/` is git-ignored — each developer generates it locally. Re-run `spec-gen analyze` after significant structural changes to keep the digest current.
|
|
676
|
+
|
|
677
|
+
---
|
|
678
|
+
|
|
534
679
|
## MCP Server
|
|
535
680
|
|
|
536
681
|
`spec-gen mcp` starts spec-gen as a [Model Context Protocol](https://modelcontextprotocol.io/) server over stdio, exposing static analysis as tools that any MCP-compatible AI agent (Cline, Roo Code, Kilocode, Claude Code, Cursor...) can call directly -- no API key required.
|
|
@@ -565,6 +710,31 @@ or for local development:
|
|
|
565
710
|
|
|
566
711
|
**Cline / Roo Code / Kilocode** -- add the same block under `mcpServers` in the MCP settings JSON of your editor.
|
|
567
712
|
|
|
713
|
+
### Watch mode (keep search_code and orient fresh)
|
|
714
|
+
|
|
715
|
+
By default the MCP server reads `llm-context.json` from the last `analyze` run. With `--watch-auto`, it also watches source files for changes and incrementally re-indexes signatures so `search_code` and `orient` reflect your latest edits without waiting for the next commit.
|
|
716
|
+
|
|
717
|
+
Add `--watch-auto` to your MCP config args:
|
|
718
|
+
|
|
719
|
+
```json
|
|
720
|
+
{
|
|
721
|
+
"mcpServers": {
|
|
722
|
+
"spec-gen": {
|
|
723
|
+
"command": "spec-gen",
|
|
724
|
+
"args": ["mcp", "--watch-auto"]
|
|
725
|
+
}
|
|
726
|
+
}
|
|
727
|
+
}
|
|
728
|
+
```
|
|
729
|
+
|
|
730
|
+
The watcher starts automatically on the first tool call — no hardcoded path needed. It re-extracts signatures for any changed source file and patches `llm-context.json` within ~500 ms of a save. If an embedding server is reachable, it also re-embeds changed functions into the vector index automatically. The call graph is not rebuilt on every change; it stays current via the [post-commit hook](#cicd-integration) (`spec-gen analyze --force`).
|
|
731
|
+
|
|
732
|
+
| Option | Default | Description |
|
|
733
|
+
|---|---|---|
|
|
734
|
+
| `--watch-auto` | off | Auto-detect project root from first tool call |
|
|
735
|
+
| `--watch <dir>` | — | Watch a fixed directory (alternative to `--watch-auto`) |
|
|
736
|
+
| `--watch-debounce <ms>` | 400 | Delay before re-indexing after a file change |
|
|
737
|
+
|
|
568
738
|
### Cline / Roo Code / Kilocode
|
|
569
739
|
|
|
570
740
|
For editors with MCP support, after adding the `mcpServers` block to your settings, download the slash command workflows:
|
|
@@ -621,7 +791,7 @@ All tools run on **pure static analysis** -- no LLM quota consumed.
|
|
|
621
791
|
| Tool | Description | Requires prior analysis |
|
|
622
792
|
|------|-------------|:---:|
|
|
623
793
|
| `analyze_codebase` | Run full static analysis: repo structure, dependency graph, call graph (hub functions, entry points, layer violations), and top refactoring priorities. Results cached for 1 hour (`force: true` to bypass). | No |
|
|
624
|
-
| `get_call_graph` | Hub functions (high fan-in), entry points (no internal callers), and architectural layer violations. Supports TypeScript, JavaScript, Python, Go, Rust, Ruby, Java, C
|
|
794
|
+
| `get_call_graph` | Hub functions (high fan-in), entry points (no internal callers), and architectural layer violations. Supports TypeScript, JavaScript, Python, Go, Rust, Ruby, Java, C++, Swift. | Yes |
|
|
625
795
|
| `get_signatures` | Compact function/class signatures per file. Filter by path substring with `filePattern`. Useful for understanding a module's public API without reading full source. | Yes |
|
|
626
796
|
| `get_duplicate_report` | Detect duplicate code: Type 1 (exact clones), Type 2 (structural -- renamed variables), Type 3 (near-clones with Jaccard similarity >= 0.7). Groups sorted by impact. | Yes |
|
|
627
797
|
|
|
@@ -640,23 +810,36 @@ All tools run on **pure static analysis** -- no LLM quota consumed.
|
|
|
640
810
|
|
|
641
811
|
| Tool | Description | Requires prior analysis |
|
|
642
812
|
|------|-------------|:---:|
|
|
813
|
+
| `orient` | **Single entry point for any new task.** Given a natural-language task description, returns in one call: relevant functions, source files, spec domains, call neighbourhoods, insertion-point candidates, and matching spec sections. Start here. | Yes (+ embedding) |
|
|
643
814
|
| `get_subgraph` | Depth-limited subgraph centred on a function. Direction: `downstream` (what it calls), `upstream` (who calls it), or `both`. Output as JSON or Mermaid diagram. | Yes |
|
|
644
815
|
| `get_architecture_overview` | High-level cluster map: roles (entry layer, orchestrator, core utilities, API layer, internal), inter-cluster dependencies, global entry points, and critical hubs. No LLM required. | Yes |
|
|
645
816
|
| `get_function_skeleton` | Noise-stripped view of a source file: logs, inline comments, and non-JSDoc block comments removed. Signatures, control flow, return/throw, and call expressions preserved. Returns reduction %. | No |
|
|
646
|
-
| `
|
|
647
|
-
| `
|
|
817
|
+
| `get_function_body` | Return the exact source code of a named function in a file. | No |
|
|
818
|
+
| `get_file_dependencies` | Return the file-level import dependencies for a given source file (imports, imported-by, or both). | Yes |
|
|
819
|
+
| `trace_execution_path` | Find all call-graph paths between two functions (DFS, configurable depth/max-paths). Use this when debugging: "how does request X reach function Y?" Returns shortest path, all paths sorted by hops, and a step-by-step chain per path. | Yes |
|
|
820
|
+
| `suggest_insertion_points` | Semantic search over the vector index to find the best existing functions to extend or hook into when implementing a new feature. Returns ranked candidates with role and strategy. Falls back to BM25 keyword search when no embedding server is configured. | Yes (+ embedding) |
|
|
821
|
+
| `search_code` | Natural-language semantic search over indexed functions. Returns the closest matches by meaning with similarity score, call-graph neighbourhood enrichment, and spec-linked peer functions. Falls back to BM25 keyword search when no embedding server is configured. | Yes (+ embedding) |
|
|
648
822
|
|
|
649
823
|
**Specs**
|
|
650
824
|
|
|
651
825
|
| Tool | Description | Requires prior analysis |
|
|
652
826
|
|------|-------------|:---:|
|
|
827
|
+
| `get_spec` | Read the full content of an OpenSpec domain spec by domain name. | Yes (generate) |
|
|
653
828
|
| `get_mapping` | Requirement->function mapping produced by `spec-gen generate`. Shows which functions implement which spec requirements, confidence level, and orphan functions with no spec coverage. | Yes (generate) |
|
|
829
|
+
| `get_decisions` | List or search Architecture Decision Records (ADRs) stored in `openspec/decisions/`. Optional keyword query. | Yes (generate) |
|
|
654
830
|
| `check_spec_drift` | Detect code changes not reflected in OpenSpec specs. Compares git-changed files against spec coverage maps. Issues: gap / stale / uncovered / orphaned-spec / adr-gap. | Yes (generate) |
|
|
655
|
-
| `search_specs` | Semantic search over OpenSpec specifications to find requirements, design notes, and architecture decisions by meaning. Returns linked source files for graph highlighting. Use this when asked "which spec covers X?" or "where should we implement Z?". Requires a spec index built with `spec-gen analyze
|
|
831
|
+
| `search_specs` | Semantic search over OpenSpec specifications to find requirements, design notes, and architecture decisions by meaning. Returns linked source files for graph highlighting. Use this when asked "which spec covers X?" or "where should we implement Z?". Requires a spec index built with `spec-gen analyze` or `--reindex-specs`. | Yes (generate) |
|
|
656
832
|
| `list_spec_domains` | List all OpenSpec domains available in this project. Use this to discover what domains exist before doing a targeted `search_specs` call. | Yes (generate) |
|
|
657
833
|
|
|
658
834
|
### Parameters
|
|
659
835
|
|
|
836
|
+
**`orient`**
|
|
837
|
+
```
|
|
838
|
+
directory string Absolute path to the project directory
|
|
839
|
+
task string Natural-language description of the task, e.g. "add rate limiting to the API"
|
|
840
|
+
limit number Max relevant functions to return (default: 5, max: 20)
|
|
841
|
+
```
|
|
842
|
+
|
|
660
843
|
**`analyze_codebase`**
|
|
661
844
|
```
|
|
662
845
|
directory string Absolute path to the project directory
|
|
@@ -754,6 +937,41 @@ directory string Absolute path to the project directory
|
|
|
754
937
|
filePath string Path to the file, relative to the project directory
|
|
755
938
|
```
|
|
756
939
|
|
|
940
|
+
**`get_function_body`**
|
|
941
|
+
```
|
|
942
|
+
directory string Absolute path to the project directory
|
|
943
|
+
filePath string Path to the file, relative to the project directory
|
|
944
|
+
functionName string Name of the function to extract
|
|
945
|
+
```
|
|
946
|
+
|
|
947
|
+
**`get_file_dependencies`**
|
|
948
|
+
```
|
|
949
|
+
directory string Absolute path to the project directory
|
|
950
|
+
filePath string Path to the file, relative to the project directory
|
|
951
|
+
direction string "imports" | "importedBy" | "both" (default: "both")
|
|
952
|
+
```
|
|
953
|
+
|
|
954
|
+
**`trace_execution_path`**
|
|
955
|
+
```
|
|
956
|
+
directory string Absolute path to the project directory
|
|
957
|
+
entryFunction string Name of the starting function (case-insensitive partial match)
|
|
958
|
+
targetFunction string Name of the target function (case-insensitive partial match)
|
|
959
|
+
maxDepth number Maximum path length in hops (default: 6)
|
|
960
|
+
maxPaths number Maximum number of paths to return (default: 10, max: 50)
|
|
961
|
+
```
|
|
962
|
+
|
|
963
|
+
**`get_decisions`**
|
|
964
|
+
```
|
|
965
|
+
directory string Absolute path to the project directory
|
|
966
|
+
query string Optional keyword to filter ADRs by title or content
|
|
967
|
+
```
|
|
968
|
+
|
|
969
|
+
**`get_spec`**
|
|
970
|
+
```
|
|
971
|
+
directory string Absolute path to the project directory
|
|
972
|
+
domain string Domain name (e.g. "auth", "user", "api")
|
|
973
|
+
```
|
|
974
|
+
|
|
757
975
|
**`get_god_functions`**
|
|
758
976
|
```
|
|
759
977
|
directory string Absolute path to the project directory
|
|
@@ -813,6 +1031,20 @@ section string Filter by section type: "requirements" | "purpose" | "design
|
|
|
813
1031
|
2. get_mapping({ directory, orphansOnly: true }) # functions with no spec coverage
|
|
814
1032
|
```
|
|
815
1033
|
|
|
1034
|
+
**Scenario D -- Starting a new task (fastest orientation)**
|
|
1035
|
+
```
|
|
1036
|
+
1. orient({ directory, task: "add rate limiting to the API" })
|
|
1037
|
+
# Returns in one call:
|
|
1038
|
+
# - relevant functions (semantic search or BM25 fallback)
|
|
1039
|
+
# - source files and spec domains that cover them
|
|
1040
|
+
# - call-graph neighbourhood for each top function
|
|
1041
|
+
# - best insertion-point candidates
|
|
1042
|
+
# - spec-linked peer functions (cross-graph traversal)
|
|
1043
|
+
# - matching spec sections
|
|
1044
|
+
2. get_spec({ directory, domain: "..." }) # read full spec before writing code
|
|
1045
|
+
3. check_spec_drift({ directory }) # verify after implementation
|
|
1046
|
+
```
|
|
1047
|
+
|
|
816
1048
|
## Interactive Graph Viewer
|
|
817
1049
|
|
|
818
1050
|
`spec-gen view` launches a local React app that visualises your codebase analysis and lets you explore spec requirements side-by-side with the dependency graph.
|
|
@@ -837,8 +1069,9 @@ spec-gen view --spec <path> # custom spec dir (default: ./openspec/specs/
|
|
|
837
1069
|
| View | Description |
|
|
838
1070
|
|------|-------------|
|
|
839
1071
|
| **Clusters** | Colour-coded architectural clusters with expandable member nodes |
|
|
840
|
-
| **Flat** | Force-directed dependency graph (all nodes) |
|
|
1072
|
+
| **Flat** | Force-directed dependency graph (all nodes); call edges shown as cyan dashes |
|
|
841
1073
|
| **Architecture** | High-level cluster map: role-coloured boxes, inter-cluster dependency arrows |
|
|
1074
|
+
| **Classes** | Component-aware force layout of class/struct relationships with coloured groupings |
|
|
842
1075
|
|
|
843
1076
|
### Diagram Chat
|
|
844
1077
|
|
|
@@ -936,9 +1169,19 @@ Static analysis output is stored in `.spec-gen/analysis/`:
|
|
|
936
1169
|
|
|
937
1170
|
`spec-gen analyze` also writes **`ARCHITECTURE.md`** to your project root -- a Markdown overview of module clusters, entry points, and critical hubs, refreshed on every run.
|
|
938
1171
|
|
|
939
|
-
## Semantic Search
|
|
1172
|
+
## Semantic Search & GraphRAG
|
|
940
1173
|
|
|
941
|
-
`spec-gen analyze
|
|
1174
|
+
`spec-gen analyze` builds a vector index over all functions in the call graph, enabling natural-language search via the `search_code`, `orient`, and `suggest_insertion_points` MCP tools, and the search bar in the viewer.
|
|
1175
|
+
|
|
1176
|
+
### GraphRAG retrieval expansion
|
|
1177
|
+
|
|
1178
|
+
Semantic search is only the starting point. spec-gen combines three retrieval layers into every search result — this is what makes it genuinely useful for AI agents navigating unfamiliar codebases:
|
|
1179
|
+
|
|
1180
|
+
1. **Semantic seed** — dense vector search (or BM25 keyword fallback) finds the top-N functions closest in meaning to the query.
|
|
1181
|
+
2. **Call-graph expansion** — BFS up to depth 2 follows callee edges from every seed function, pulling in the files those functions depend on. During `generate`, this ensures the LLM sees the full call neighbourhood, not just the most obvious files.
|
|
1182
|
+
3. **Spec-linked peer functions** — each seed function's spec domain is looked up in the requirement→function mapping. Functions from the same spec domain that live in *different files* are surfaced as `specLinkedFunctions`. This crosses the call-graph boundary: implementations that share a spec requirement but are not directly connected by calls are retrieved automatically.
|
|
1183
|
+
|
|
1184
|
+
The result: a single `orient` or `search_code` call returns not just "functions that mention this concept" but the interconnected cluster of code and specs that collectively implement it. Agents spend less time chasing cross-file references manually and more time making changes with confidence.
|
|
942
1185
|
|
|
943
1186
|
### Embedding configuration
|
|
944
1187
|
|
|
@@ -950,8 +1193,8 @@ EMBED_BASE_URL=https://api.openai.com/v1
|
|
|
950
1193
|
EMBED_MODEL=text-embedding-3-small
|
|
951
1194
|
EMBED_API_KEY=sk-... # optional for local servers
|
|
952
1195
|
|
|
953
|
-
# Then run:
|
|
954
|
-
spec-gen analyze
|
|
1196
|
+
# Then run (embedding is automatic when configured):
|
|
1197
|
+
spec-gen analyze
|
|
955
1198
|
```
|
|
956
1199
|
|
|
957
1200
|
**Config file (`.spec-gen/config.json`):**
|
|
@@ -1001,6 +1244,8 @@ The index is stored in `.spec-gen/analysis/vector-index/` and is automatically u
|
|
|
1001
1244
|
| `OPENAI_COMPAT_API_KEY` | `openai-compat` | API key for OpenAI-compatible server |
|
|
1002
1245
|
| `OPENAI_COMPAT_BASE_URL` | `openai-compat` | Base URL, e.g. `https://api.mistral.ai/v1` |
|
|
1003
1246
|
| `GEMINI_API_KEY` | `gemini` | Google Gemini API key |
|
|
1247
|
+
| `COPILOT_API_BASE_URL` | `copilot` | Base URL of the copilot-api proxy (default: `http://localhost:4141/v1`) |
|
|
1248
|
+
| `COPILOT_API_KEY` | `copilot` | API key if the proxy requires auth (default: `copilot`) |
|
|
1004
1249
|
| `EMBED_BASE_URL` | embedding | Base URL for the embedding API (e.g. `http://localhost:11434/v1`) |
|
|
1005
1250
|
| `EMBED_MODEL` | embedding | Embedding model name (e.g. `nomic-embed-text`) |
|
|
1006
1251
|
| `EMBED_API_KEY` | embedding | API key for the embedding service (defaults to `OPENAI_API_KEY`) |
|
|
@@ -1017,21 +1262,23 @@ The index is stored in `.spec-gen/analysis/vector-index/` and is automatically u
|
|
|
1017
1262
|
export OPENAI_COMPAT_API_KEY=ollama # OpenAI-compatible local server
|
|
1018
1263
|
export GEMINI_API_KEY=... # Google Gemini
|
|
1019
1264
|
```
|
|
1265
|
+
Or use a CLI-based provider (`claude-code`, `gemini-cli`, `mistral-vibe`) which requires no API key — just the CLI tool on your PATH.
|
|
1020
1266
|
- `analyze`, `drift`, and `init` require no API key
|
|
1021
1267
|
|
|
1022
1268
|
## Supported Languages
|
|
1023
1269
|
|
|
1024
|
-
| Language | Signatures | Call Graph |
|
|
1025
|
-
|
|
1026
|
-
| TypeScript / JavaScript | Full | Full |
|
|
1027
|
-
| Python | Full | Full |
|
|
1028
|
-
| Go | Full | Full |
|
|
1029
|
-
| Rust | Full | Full |
|
|
1030
|
-
| Ruby | Full | Full |
|
|
1031
|
-
| Java | Full | Full |
|
|
1032
|
-
| C++ | Full | Full |
|
|
1270
|
+
| Language | Signatures | Call Graph | Import Parsing |
|
|
1271
|
+
|----------|-----------|------------|----------------|
|
|
1272
|
+
| TypeScript / JavaScript | Full | Full | Full |
|
|
1273
|
+
| Python | Full | Full | Full |
|
|
1274
|
+
| Go | Full | Full | Full |
|
|
1275
|
+
| Rust | Full | Full | Full |
|
|
1276
|
+
| Ruby | Full | Full | Full |
|
|
1277
|
+
| Java | Full | Full | Full |
|
|
1278
|
+
| C++ | Full | Full | Cross-file edges synthesized from call graph |
|
|
1279
|
+
| Swift | Full | Full | Cross-file edges synthesized from call graph |
|
|
1033
1280
|
|
|
1034
|
-
TypeScript projects get the best results due to richer type information.
|
|
1281
|
+
TypeScript projects get the best results due to richer type information. Swift and C++ projects use call-graph-based edge synthesis instead of import parsing, since these languages have no file-level imports within a module.
|
|
1035
1282
|
|
|
1036
1283
|
## Usage Options
|
|
1037
1284
|
|
|
@@ -1146,11 +1393,11 @@ for (const [key, req] of Object.entries(requirements)) {
|
|
|
1146
1393
|
npm install # Install dependencies
|
|
1147
1394
|
npm run dev # Development mode (watch)
|
|
1148
1395
|
npm run build # Build
|
|
1149
|
-
npm run test:run # Run tests (
|
|
1396
|
+
npm run test:run # Run tests (2050+ unit tests)
|
|
1150
1397
|
npm run typecheck # Type check
|
|
1151
1398
|
```
|
|
1152
1399
|
|
|
1153
|
-
|
|
1400
|
+
2050+ unit tests covering static analysis, call graph (including Swift), refactor analysis, spec mapping, drift detection, LLM enhancement, ADR generation, MCP handlers, cross-file edge synthesis, and the full CLI.
|
|
1154
1401
|
|
|
1155
1402
|
## Links
|
|
1156
1403
|
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"generate.d.ts","sourceRoot":"","sources":["../../src/api/generate.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;
|
|
1
|
+
{"version":3,"file":"generate.d.ts","sourceRoot":"","sources":["../../src/api/generate.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAkBH,OAAO,KAAK,EAAE,kBAAkB,EAAE,cAAc,EAAoB,MAAM,YAAY,CAAC;AA4DvF;;;;;;;;GAQG;AACH,wBAAsB,eAAe,CAAC,OAAO,GAAE,kBAAuB,GAAG,OAAO,CAAC,cAAc,CAAC,CAkN/F"}
|
package/dist/api/generate.js
CHANGED
|
@@ -13,7 +13,7 @@ import { OpenSpecFormatGenerator } from '../core/generator/openspec-format-gener
|
|
|
13
13
|
import { OpenSpecWriter } from '../core/generator/openspec-writer.js';
|
|
14
14
|
import { ADRGenerator } from '../core/generator/adr-generator.js';
|
|
15
15
|
import { MappingGenerator } from '../core/generator/mapping-generator.js';
|
|
16
|
-
import { DEFAULT_ANTHROPIC_MODEL, DEFAULT_OPENAI_MODEL, DEFAULT_OPENAI_COMPAT_MODEL, DEFAULT_GEMINI_MODEL, SPEC_GEN_DIR, SPEC_GEN_ANALYSIS_SUBDIR, SPEC_GEN_LOGS_SUBDIR, SPEC_GEN_ANALYSIS_REL_PATH, SPEC_GEN_GENERATION_SUBDIR, OPENSPEC_DIR, ARTIFACT_REPO_STRUCTURE, ARTIFACT_LLM_CONTEXT, ARTIFACT_DEPENDENCY_GRAPH, } from '../constants.js';
|
|
16
|
+
import { DEFAULT_ANTHROPIC_MODEL, DEFAULT_OPENAI_MODEL, DEFAULT_OPENAI_COMPAT_MODEL, DEFAULT_COPILOT_MODEL, DEFAULT_GEMINI_MODEL, SPEC_GEN_DIR, SPEC_GEN_ANALYSIS_SUBDIR, SPEC_GEN_LOGS_SUBDIR, SPEC_GEN_ANALYSIS_REL_PATH, SPEC_GEN_GENERATION_SUBDIR, OPENSPEC_DIR, ARTIFACT_REPO_STRUCTURE, ARTIFACT_LLM_CONTEXT, ARTIFACT_DEPENDENCY_GRAPH, ARTIFACT_REFACTOR_PRIORITIES, } from '../constants.js';
|
|
17
17
|
function progress(onProgress, step, status, detail) {
|
|
18
18
|
onProgress?.({ phase: 'generate', step, status, detail });
|
|
19
19
|
}
|
|
@@ -27,7 +27,8 @@ async function loadAnalysisData(analysisPath) {
|
|
|
27
27
|
phase3_validation: { purpose: 'Validation', files: [], totalTokens: 0 },
|
|
28
28
|
};
|
|
29
29
|
const depGraph = await readJsonFile(join(analysisPath, ARTIFACT_DEPENDENCY_GRAPH), ARTIFACT_DEPENDENCY_GRAPH) ?? undefined;
|
|
30
|
-
|
|
30
|
+
const refactorReport = await readJsonFile(join(analysisPath, ARTIFACT_REFACTOR_PRIORITIES), ARTIFACT_REFACTOR_PRIORITIES) ?? undefined;
|
|
31
|
+
return { repoStructure, llmContext, depGraph, refactorReport };
|
|
31
32
|
}
|
|
32
33
|
/**
|
|
33
34
|
* Generate OpenSpec specification files from analysis results using LLM.
|
|
@@ -60,25 +61,28 @@ export async function specGenGenerate(options = {}) {
|
|
|
60
61
|
if (!analysisData) {
|
|
61
62
|
throw new Error('No analysis found. Run specGenAnalyze() first.');
|
|
62
63
|
}
|
|
63
|
-
const { repoStructure, llmContext, depGraph } = analysisData;
|
|
64
|
+
const { repoStructure, llmContext, depGraph, refactorReport } = analysisData;
|
|
64
65
|
progress(onProgress, 'Loading analysis', 'complete', `${repoStructure.statistics.analyzedFiles} files`);
|
|
65
66
|
// Resolve provider
|
|
66
67
|
const anthropicKey = process.env.ANTHROPIC_API_KEY;
|
|
67
68
|
const openaiKey = process.env.OPENAI_API_KEY;
|
|
68
69
|
const openaiCompatKey = process.env.OPENAI_COMPAT_API_KEY;
|
|
69
70
|
const geminiKey = process.env.GEMINI_API_KEY;
|
|
70
|
-
|
|
71
|
-
|
|
71
|
+
const configuredProvider = options.provider ?? specGenConfig.generation.provider;
|
|
72
|
+
const noKeyProviders = ['claude-code', 'mistral-vibe', 'copilot'];
|
|
73
|
+
if (!noKeyProviders.includes(configuredProvider ?? '') && !anthropicKey && !openaiKey && !openaiCompatKey && !geminiKey) {
|
|
74
|
+
throw new Error('No LLM API key found. Set ANTHROPIC_API_KEY, OPENAI_API_KEY, GEMINI_API_KEY, OPENAI_COMPAT_API_KEY, or use provider "copilot".');
|
|
72
75
|
}
|
|
73
76
|
const envDetectedProvider = anthropicKey ? 'anthropic'
|
|
74
77
|
: geminiKey ? 'gemini'
|
|
75
78
|
: openaiCompatKey ? 'openai-compat'
|
|
76
79
|
: 'openai';
|
|
77
|
-
const effectiveProvider =
|
|
80
|
+
const effectiveProvider = configuredProvider ?? envDetectedProvider;
|
|
78
81
|
const defaultModels = {
|
|
79
82
|
anthropic: DEFAULT_ANTHROPIC_MODEL,
|
|
80
83
|
gemini: DEFAULT_GEMINI_MODEL,
|
|
81
84
|
'openai-compat': DEFAULT_OPENAI_COMPAT_MODEL,
|
|
85
|
+
copilot: DEFAULT_COPILOT_MODEL,
|
|
82
86
|
openai: DEFAULT_OPENAI_MODEL,
|
|
83
87
|
};
|
|
84
88
|
const effectiveModel = options.model || specGenConfig.generation.model || defaultModels[effectiveProvider];
|
|
@@ -142,7 +146,7 @@ export async function specGenGenerate(options = {}) {
|
|
|
142
146
|
});
|
|
143
147
|
let pipelineResult;
|
|
144
148
|
try {
|
|
145
|
-
pipelineResult = await pipeline.run(repoStructure, llmContext, depGraph);
|
|
149
|
+
pipelineResult = await pipeline.run(repoStructure, llmContext, depGraph, refactorReport);
|
|
146
150
|
}
|
|
147
151
|
catch (error) {
|
|
148
152
|
await llm.saveLogs().catch(() => { });
|
package/dist/api/generate.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"generate.js","sourceRoot":"","sources":["../../src/api/generate.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAEH,OAAO,EAAE,IAAI,EAAE,MAAM,WAAW,CAAC;AACjC,OAAO,EAAE,YAAY,EAAE,MAAM,6BAA6B,CAAC;AAC3D,OAAO,EACL,iBAAiB,EACjB,kBAAkB,GACnB,MAAM,oCAAoC,CAAC;AAC5C,OAAO,EAAE,gBAAgB,EAAE,MAAM,iCAAiC,CAAC;AAEnE,OAAO,EAAE,sBAAsB,EAAE,MAAM,oCAAoC,CAAC;AAC5E,OAAO,EAAE,uBAAuB,EAAE,MAAM,gDAAgD,CAAC;AACzF,OAAO,EAAE,cAAc,EAAkB,MAAM,sCAAsC,CAAC;AACtF,OAAO,EAAE,YAAY,EAAE,MAAM,oCAAoC,CAAC;AAClE,OAAO,EAAE,gBAAgB,EAAE,MAAM,wCAAwC,CAAC;
|
|
1
|
+
{"version":3,"file":"generate.js","sourceRoot":"","sources":["../../src/api/generate.ts"],"names":[],"mappings":"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"}
|
package/dist/api/run.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"run.d.ts","sourceRoot":"","sources":["../../src/api/run.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAiCH,OAAO,KAAK,EAAE,aAAa,EAAE,SAAS,EAA+C,MAAM,YAAY,CAAC;AA0BxG;;;;;;;;GAQG;AACH,wBAAsB,UAAU,CAAC,OAAO,GAAE,aAAkB,GAAG,OAAO,CAAC,SAAS,CAAC,
|
|
1
|
+
{"version":3,"file":"run.d.ts","sourceRoot":"","sources":["../../src/api/run.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAiCH,OAAO,KAAK,EAAE,aAAa,EAAE,SAAS,EAA+C,MAAM,YAAY,CAAC;AA0BxG;;;;;;;;GAQG;AACH,wBAAsB,UAAU,CAAC,OAAO,GAAE,aAAkB,GAAG,OAAO,CAAC,SAAS,CAAC,CA6ShF"}
|
package/dist/api/run.js
CHANGED
|
@@ -7,7 +7,7 @@
|
|
|
7
7
|
*/
|
|
8
8
|
import { join } from 'node:path';
|
|
9
9
|
import { readFile, stat, mkdir, writeFile } from 'node:fs/promises';
|
|
10
|
-
import { ANALYSIS_REUSE_THRESHOLD_MS, DEFAULT_MAX_FILES, DEFAULT_ANTHROPIC_MODEL, DEFAULT_OPENAI_MODEL, DEFAULT_GEMINI_MODEL, DEFAULT_OPENAI_COMPAT_MODEL, SPEC_GEN_DIR, SPEC_GEN_ANALYSIS_SUBDIR, SPEC_GEN_LOGS_SUBDIR, SPEC_GEN_CONFIG_REL_PATH, SPEC_GEN_GENERATION_SUBDIR, SPEC_GEN_RUNS_SUBDIR, DEFAULT_OPENSPEC_PATH, ARTIFACT_REPO_STRUCTURE, ARTIFACT_DEPENDENCY_GRAPH, ARTIFACT_LLM_CONTEXT } from '../constants.js';
|
|
10
|
+
import { ANALYSIS_REUSE_THRESHOLD_MS, DEFAULT_MAX_FILES, DEFAULT_ANTHROPIC_MODEL, DEFAULT_OPENAI_MODEL, DEFAULT_GEMINI_MODEL, DEFAULT_OPENAI_COMPAT_MODEL, DEFAULT_COPILOT_MODEL, SPEC_GEN_DIR, SPEC_GEN_ANALYSIS_SUBDIR, SPEC_GEN_LOGS_SUBDIR, SPEC_GEN_CONFIG_REL_PATH, SPEC_GEN_GENERATION_SUBDIR, SPEC_GEN_RUNS_SUBDIR, DEFAULT_OPENSPEC_PATH, ARTIFACT_REPO_STRUCTURE, ARTIFACT_DEPENDENCY_GRAPH, ARTIFACT_LLM_CONTEXT } from '../constants.js';
|
|
11
11
|
import { fileExists, readJsonFile } from '../utils/command-helpers.js';
|
|
12
12
|
import { detectProjectType, getProjectTypeName, } from '../core/services/project-detector.js';
|
|
13
13
|
import { getDefaultConfig, readSpecGenConfig, writeSpecGenConfig, specGenConfigExists, openspecDirExists, createOpenSpecStructure, } from '../core/services/config-manager.js';
|
|
@@ -195,8 +195,9 @@ export async function specGenRun(options = {}) {
|
|
|
195
195
|
const openaiKey = process.env.OPENAI_API_KEY;
|
|
196
196
|
const openaiCompatKey = process.env.OPENAI_COMPAT_API_KEY;
|
|
197
197
|
const geminiKey = process.env.GEMINI_API_KEY;
|
|
198
|
-
|
|
199
|
-
|
|
198
|
+
const noKeyProviders = ['claude-code', 'mistral-vibe', 'copilot'];
|
|
199
|
+
if (!noKeyProviders.includes(options.provider ?? '') && !anthropicKey && !openaiKey && !openaiCompatKey && !geminiKey) {
|
|
200
|
+
throw new Error('No LLM API key found. Set ANTHROPIC_API_KEY, OPENAI_API_KEY, GEMINI_API_KEY, OPENAI_COMPAT_API_KEY, or use provider "copilot".');
|
|
200
201
|
}
|
|
201
202
|
// Create LLM service
|
|
202
203
|
const envDetectedProvider = anthropicKey ? 'anthropic'
|
|
@@ -208,6 +209,7 @@ export async function specGenRun(options = {}) {
|
|
|
208
209
|
anthropic: DEFAULT_ANTHROPIC_MODEL,
|
|
209
210
|
gemini: DEFAULT_GEMINI_MODEL,
|
|
210
211
|
'openai-compat': DEFAULT_OPENAI_COMPAT_MODEL,
|
|
212
|
+
copilot: DEFAULT_COPILOT_MODEL,
|
|
211
213
|
openai: DEFAULT_OPENAI_MODEL,
|
|
212
214
|
};
|
|
213
215
|
const model = options.model ?? defaultModels[provider] ?? DEFAULT_ANTHROPIC_MODEL;
|