sigmap 5.0.0 → 5.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.
- package/AGENTS.md +45 -32
- package/CHANGELOG.md +10 -0
- package/gen-context.js +59 -22
- package/package.json +1 -1
- package/packages/cli/package.json +1 -1
- package/packages/core/package.json +1 -1
- package/src/format/dashboard.js +20 -0
- package/src/mcp/server.js +1 -1
package/AGENTS.md
CHANGED
|
@@ -12,20 +12,23 @@ Use this marker block for all appendable context files:
|
|
|
12
12
|
## Auto-generated signatures
|
|
13
13
|
<!-- Updated by gen-context.js -->
|
|
14
14
|
You are a coding assistant with full knowledge of this codebase.
|
|
15
|
-
Below are the code signatures extracted by SigMap
|
|
15
|
+
Below are the code signatures extracted by SigMap v5.1.0 on 2026-04-16T21:33:38.411Z.
|
|
16
16
|
|
|
17
17
|
Use these signatures to answer questions about the code accurately.
|
|
18
18
|
|
|
19
19
|
## Code Signatures
|
|
20
20
|
|
|
21
|
-
<!-- Generated by SigMap gen-context.js
|
|
21
|
+
<!-- Generated by SigMap gen-context.js v5.1.0 -->
|
|
22
22
|
<!-- DO NOT EDIT below the marker line — run gen-context.js to regenerate -->
|
|
23
23
|
|
|
24
24
|
# Code signatures
|
|
25
25
|
|
|
26
|
-
## changes (last 5 commits —
|
|
26
|
+
## changes (last 5 commits — 16 minutes ago)
|
|
27
27
|
```
|
|
28
|
-
src/
|
|
28
|
+
src/config/loader.js +loadBaseConfig ~loadConfig ~deepClone
|
|
29
|
+
src/format/dashboard.js ~computeExtractorCoverage ~readBenchmarkTrend
|
|
30
|
+
src/judge/judge-engine.js +tokenize +groundedness +judge
|
|
31
|
+
src/retrieval/ranker.js +detectIntent ~formatRankJSON
|
|
29
32
|
```
|
|
30
33
|
|
|
31
34
|
## packages
|
|
@@ -146,9 +149,41 @@ function adapt(context, adapterName, opts = {}) → string
|
|
|
146
149
|
|
|
147
150
|
## src
|
|
148
151
|
|
|
149
|
-
### src/config/
|
|
152
|
+
### src/config/loader.js
|
|
150
153
|
```
|
|
151
|
-
module.exports = {
|
|
154
|
+
module.exports = { loadConfig, loadBaseConfig }
|
|
155
|
+
function loadBaseConfig(extendsVal, cwd)
|
|
156
|
+
function detectAutoSrcDirs(cwd, excludeList) → string[]
|
|
157
|
+
function loadConfig(cwd) → object
|
|
158
|
+
function deepClone(obj)
|
|
159
|
+
```
|
|
160
|
+
|
|
161
|
+
### src/format/dashboard.js
|
|
162
|
+
```
|
|
163
|
+
module.exports = { generateDashboardHtml, renderHistoryCharts, computeExtractorCoverage, percentile, overBudgetStreak }
|
|
164
|
+
function toNumber(v)
|
|
165
|
+
function percentile(values, p)
|
|
166
|
+
function overBudgetStreak(entries)
|
|
167
|
+
function loadConfig(cwd)
|
|
168
|
+
function shouldExclude(rel, excludeSet)
|
|
169
|
+
function detectLanguage(filePath)
|
|
170
|
+
function walkFiles(dir, maxDepth, depth, out, excludeSet)
|
|
171
|
+
function computeExtractorCoverage(cwd)
|
|
172
|
+
function readBenchmarkTrend(cwd)
|
|
173
|
+
function lineChartSvg(values, title, ySuffix)
|
|
174
|
+
function barChartSvg(perLanguage)
|
|
175
|
+
function sparkline(values)
|
|
176
|
+
function buildDashboardData(cwd, health)
|
|
177
|
+
function generateDashboardHtml(cwd, health)
|
|
178
|
+
function renderHistoryCharts(cwd, health)
|
|
179
|
+
```
|
|
180
|
+
|
|
181
|
+
### src/judge/judge-engine.js
|
|
182
|
+
```
|
|
183
|
+
module.exports = { groundedness, judge }
|
|
184
|
+
function tokenize(text)
|
|
185
|
+
function groundedness(response, context)
|
|
186
|
+
function judge(response, context, opts = {})
|
|
152
187
|
```
|
|
153
188
|
|
|
154
189
|
### src/mcp/server.js
|
|
@@ -162,13 +197,14 @@ function start(cwd)
|
|
|
162
197
|
|
|
163
198
|
### src/retrieval/ranker.js
|
|
164
199
|
```
|
|
165
|
-
module.exports = { rank, buildSigIndex, scoreFile, formatRankTable, formatRankJSON, DEFAULT_WEIGHTS }
|
|
200
|
+
module.exports = { rank, buildSigIndex, scoreFile, formatRankTable, formatRankJSON, DEFAULT_WEIGHTS, detectIntent }
|
|
166
201
|
function scoreFile(filePath, sigs, queryTokens, weights) → number
|
|
167
202
|
function rank(query, sigIndex, opts) → { file: string, score: nu
|
|
168
203
|
function _parseContextFile(contextPath) → Map<string, string[]>
|
|
169
204
|
function buildSigIndex(cwd, opts) → Map<string, string[]>
|
|
170
205
|
function formatRankTable(results, query) → string
|
|
171
206
|
function formatRankJSON(results, query) → object
|
|
207
|
+
function detectIntent(query)
|
|
172
208
|
```
|
|
173
209
|
|
|
174
210
|
### src/analysis/coverage-score.js
|
|
@@ -178,12 +214,9 @@ function coverageScore(cwd, fileEntries, config) → { * score: number, * grad
|
|
|
178
214
|
function _walk(dir, excludeSet, out)
|
|
179
215
|
```
|
|
180
216
|
|
|
181
|
-
### src/config/
|
|
217
|
+
### src/config/defaults.js
|
|
182
218
|
```
|
|
183
|
-
module.exports = {
|
|
184
|
-
function detectAutoSrcDirs(cwd, excludeList) → string[]
|
|
185
|
-
function loadConfig(cwd) → object
|
|
186
|
-
function deepClone(obj)
|
|
219
|
+
module.exports = { DEFAULTS }
|
|
187
220
|
```
|
|
188
221
|
|
|
189
222
|
### src/eval/analyzer.js
|
|
@@ -527,26 +560,6 @@ function formatCache(content) → string
|
|
|
527
560
|
function formatCachePayload(content, model) → string
|
|
528
561
|
```
|
|
529
562
|
|
|
530
|
-
### src/format/dashboard.js
|
|
531
|
-
```
|
|
532
|
-
module.exports = { generateDashboardHtml, renderHistoryCharts, computeExtractorCoverage, percentile, overBudgetStreak }
|
|
533
|
-
function toNumber(v)
|
|
534
|
-
function percentile(values, p)
|
|
535
|
-
function overBudgetStreak(entries)
|
|
536
|
-
function loadConfig(cwd)
|
|
537
|
-
function shouldExclude(rel, excludeSet)
|
|
538
|
-
function detectLanguage(filePath)
|
|
539
|
-
function walkFiles(dir, maxDepth, depth, out, excludeSet)
|
|
540
|
-
function computeExtractorCoverage(cwd)
|
|
541
|
-
function readBenchmarkTrend(cwd)
|
|
542
|
-
function lineChartSvg(values, title, ySuffix)
|
|
543
|
-
function barChartSvg(perLanguage)
|
|
544
|
-
function sparkline(values)
|
|
545
|
-
function buildDashboardData(cwd, health)
|
|
546
|
-
function generateDashboardHtml(cwd, health)
|
|
547
|
-
function renderHistoryCharts(cwd, health)
|
|
548
|
-
```
|
|
549
|
-
|
|
550
563
|
### src/format/llm-txt.js
|
|
551
564
|
```
|
|
552
565
|
module.exports = { format, outputPath }
|
package/CHANGELOG.md
CHANGED
|
@@ -10,6 +10,16 @@ Format: [Semantic Versioning](https://semver.org/)
|
|
|
10
10
|
|
|
11
11
|
---
|
|
12
12
|
|
|
13
|
+
## [5.1.0] — 2026-04-16
|
|
14
|
+
|
|
15
|
+
### Added
|
|
16
|
+
|
|
17
|
+
- **Benchmark history tracking** — all three benchmark scripts (`run-retrieval-benchmark.mjs`, `run-benchmark.mjs`, `run-task-benchmark.mjs`) now append a structured NDJSON entry to `.context/benchmark-history.ndjson` after each run (`type: "retrieval" | "token-reduction" | "task"`).
|
|
18
|
+
- **`sigmap history` benchmark trend rows** — when `.context/benchmark-history.ndjson` exists, `sigmap history` prints a retrieval `hit@5` sparkline row and a token-reduction sparkline row below the usage table. The command no longer exits early when the usage log is empty.
|
|
19
|
+
- **Dashboard `readBenchmarkTrend` uses local history** — `src/format/dashboard.js` now prefers `.context/benchmark-history.ndjson` over the CI-only `benchmarks/results/` directory, so the dashboard hit@5 trend chart populates for all users after running any benchmark locally.
|
|
20
|
+
|
|
21
|
+
---
|
|
22
|
+
|
|
13
23
|
## [5.0.0] — 2026-04-16
|
|
14
24
|
|
|
15
25
|
### Added
|
package/gen-context.js
CHANGED
|
@@ -3152,6 +3152,25 @@ __factories["./src/format/cache"] = function(module, exports) {
|
|
|
3152
3152
|
}
|
|
3153
3153
|
|
|
3154
3154
|
function readBenchmarkTrend(cwd) {
|
|
3155
|
+
// Prefer per-user history file written by benchmark scripts
|
|
3156
|
+
const histPath = path.join(cwd, '.context', 'benchmark-history.ndjson');
|
|
3157
|
+
if (fs.existsSync(histPath)) {
|
|
3158
|
+
const histValues = [];
|
|
3159
|
+
try {
|
|
3160
|
+
for (const line of fs.readFileSync(histPath, 'utf8').trim().split('\n').filter(Boolean)) {
|
|
3161
|
+
try {
|
|
3162
|
+
const obj = JSON.parse(line);
|
|
3163
|
+
if (obj.type === 'retrieval') {
|
|
3164
|
+
const v = toNumber(obj.hitAt5Pct);
|
|
3165
|
+
if (v !== null) histValues.push(v);
|
|
3166
|
+
}
|
|
3167
|
+
} catch (_) {}
|
|
3168
|
+
}
|
|
3169
|
+
} catch (_) {}
|
|
3170
|
+
if (histValues.length > 0) return histValues.slice(-30);
|
|
3171
|
+
}
|
|
3172
|
+
|
|
3173
|
+
// Fallback: legacy benchmarks/results directory (CI artifacts)
|
|
3155
3174
|
const resultDir = path.join(cwd, 'benchmarks', 'results');
|
|
3156
3175
|
if (!fs.existsSync(resultDir)) return [];
|
|
3157
3176
|
const files = [];
|
|
@@ -4708,7 +4727,7 @@ __factories["./src/mcp/server"] = function(module, exports) {
|
|
|
4708
4727
|
|
|
4709
4728
|
const SERVER_INFO = {
|
|
4710
4729
|
name: 'sigmap',
|
|
4711
|
-
version: '5.
|
|
4730
|
+
version: '5.1.0',
|
|
4712
4731
|
description: 'SigMap MCP server — code signatures on demand',
|
|
4713
4732
|
};
|
|
4714
4733
|
|
|
@@ -6371,7 +6390,7 @@ const path = require('path');
|
|
|
6371
6390
|
const os = require('os');
|
|
6372
6391
|
const { execSync } = require('child_process');
|
|
6373
6392
|
|
|
6374
|
-
const VERSION = '5.
|
|
6393
|
+
const VERSION = '5.1.0';
|
|
6375
6394
|
const MARKER = '\n\n## Auto-generated signatures\n<!-- Updated by gen-context.js -->\n';
|
|
6376
6395
|
|
|
6377
6396
|
function requireSourceOrBundled(key) {
|
|
@@ -8482,11 +8501,6 @@ function main() {
|
|
|
8482
8501
|
process.exit(0);
|
|
8483
8502
|
}
|
|
8484
8503
|
|
|
8485
|
-
if (last.length === 0) {
|
|
8486
|
-
console.log('[sigmap] No history found. Run sigmap to generate entries (enable tracking: true in config).');
|
|
8487
|
-
process.exit(0);
|
|
8488
|
-
}
|
|
8489
|
-
|
|
8490
8504
|
const SPARK_CHARS = '▁▂▃▄▅▆▇█';
|
|
8491
8505
|
function sparkline(values) {
|
|
8492
8506
|
if (values.length === 0) return '';
|
|
@@ -8499,25 +8513,48 @@ function main() {
|
|
|
8499
8513
|
}).join('');
|
|
8500
8514
|
}
|
|
8501
8515
|
|
|
8502
|
-
const tokens = last.map((e) => e.finalTokens || 0);
|
|
8503
|
-
const spark = sparkline(tokens);
|
|
8504
|
-
|
|
8505
8516
|
const bar = '─'.repeat(62);
|
|
8506
8517
|
console.log(bar);
|
|
8507
|
-
console.log(` sigmap history (last ${last.length} runs)`);
|
|
8518
|
+
console.log(` sigmap history (last ${Math.max(last.length, 1)} runs)`);
|
|
8508
8519
|
console.log(bar);
|
|
8509
|
-
|
|
8510
|
-
|
|
8511
|
-
|
|
8512
|
-
|
|
8513
|
-
|
|
8514
|
-
|
|
8515
|
-
const
|
|
8516
|
-
|
|
8517
|
-
|
|
8520
|
+
|
|
8521
|
+
if (last.length === 0) {
|
|
8522
|
+
console.log(' No usage log entries. Enable tracking: true in config to start recording runs.');
|
|
8523
|
+
} else {
|
|
8524
|
+
console.log(` ${'Date'.padEnd(24)} ${'Files'.padStart(5)} ${'Tokens'.padStart(7)} ${'Reduction'.padStart(9)} ${'Budget?'.padStart(7)}`);
|
|
8525
|
+
console.log(` ${'─'.repeat(24)} ${'─'.repeat(5)} ${'─'.repeat(7)} ${'─'.repeat(9)} ${'─'.repeat(7)}`);
|
|
8526
|
+
for (const e of last) {
|
|
8527
|
+
const date = (e.ts || '').slice(0, 19).replace('T', ' ');
|
|
8528
|
+
const files = String(e.fileCount || 0).padStart(5);
|
|
8529
|
+
const tok = String(e.finalTokens || 0).padStart(7);
|
|
8530
|
+
const red = `${e.reductionPct || 0}%`.padStart(9);
|
|
8531
|
+
const over = (e.overBudget ? ' ⚠ yes' : ' no').padStart(7);
|
|
8532
|
+
console.log(` ${date.padEnd(24)} ${files} ${tok} ${red} ${over}`);
|
|
8533
|
+
}
|
|
8534
|
+
console.log(bar);
|
|
8535
|
+
const tokens = last.map((e) => e.finalTokens || 0);
|
|
8536
|
+
console.log(` Token trend: ${sparkline(tokens)}`);
|
|
8537
|
+
}
|
|
8538
|
+
|
|
8539
|
+
// Show benchmark trend row if .context/benchmark-history.ndjson exists
|
|
8540
|
+
const benchHistPath = path.join(cwd, '.context', 'benchmark-history.ndjson');
|
|
8541
|
+
if (fs.existsSync(benchHistPath)) {
|
|
8542
|
+
try {
|
|
8543
|
+
const benchEntries = fs.readFileSync(benchHistPath, 'utf8').trim().split('\n')
|
|
8544
|
+
.map((l) => { try { return JSON.parse(l); } catch (_) { return null; } }).filter(Boolean);
|
|
8545
|
+
const retrieval = benchEntries.filter((e) => e.type === 'retrieval').slice(-n);
|
|
8546
|
+
if (retrieval.length > 0) {
|
|
8547
|
+
const hits = retrieval.map((e) => e.hitAt5Pct || 0);
|
|
8548
|
+
console.log(` hit@5 trend: ${sparkline(hits)} ${hits.at(-1)}% (latest)`);
|
|
8549
|
+
}
|
|
8550
|
+
const tokenBench = benchEntries.filter((e) => e.type === 'token-reduction').slice(-n);
|
|
8551
|
+
if (tokenBench.length > 0) {
|
|
8552
|
+
const reds = tokenBench.map((e) => e.reduction || e.avgReductionPct || 0);
|
|
8553
|
+
console.log(` tok reduce : ${sparkline(reds)} ${reds.at(-1)}% (latest)`);
|
|
8554
|
+
}
|
|
8555
|
+
} catch (_) {}
|
|
8518
8556
|
}
|
|
8519
|
-
|
|
8520
|
-
console.log(` Token trend: ${spark}`);
|
|
8557
|
+
|
|
8521
8558
|
console.log(bar);
|
|
8522
8559
|
process.exit(0);
|
|
8523
8560
|
}
|
package/package.json
CHANGED
package/src/format/dashboard.js
CHANGED
|
@@ -140,6 +140,26 @@ function computeExtractorCoverage(cwd) {
|
|
|
140
140
|
}
|
|
141
141
|
|
|
142
142
|
function readBenchmarkTrend(cwd) {
|
|
143
|
+
// Prefer per-user history file written by benchmark scripts
|
|
144
|
+
const histPath = path.join(cwd, '.context', 'benchmark-history.ndjson');
|
|
145
|
+
if (fs.existsSync(histPath)) {
|
|
146
|
+
const values = [];
|
|
147
|
+
try {
|
|
148
|
+
const lines = fs.readFileSync(histPath, 'utf8').trim().split('\n').filter(Boolean);
|
|
149
|
+
for (const line of lines) {
|
|
150
|
+
try {
|
|
151
|
+
const obj = JSON.parse(line);
|
|
152
|
+
if (obj.type === 'retrieval') {
|
|
153
|
+
const v = toNumber(obj.hitAt5Pct);
|
|
154
|
+
if (v !== null) values.push(v);
|
|
155
|
+
}
|
|
156
|
+
} catch (_) {}
|
|
157
|
+
}
|
|
158
|
+
} catch (_) {}
|
|
159
|
+
if (values.length > 0) return values.slice(-30);
|
|
160
|
+
}
|
|
161
|
+
|
|
162
|
+
// Fallback: legacy benchmarks/results directory (CI artifacts)
|
|
143
163
|
const resultDir = path.join(cwd, 'benchmarks', 'results');
|
|
144
164
|
if (!fs.existsSync(resultDir)) return [];
|
|
145
165
|
|
package/src/mcp/server.js
CHANGED