token-pilot 0.24.2 → 0.26.6
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-plugin/marketplace.json +29 -12
- package/.claude-plugin/plugin.json +23 -5
- package/CHANGELOG.md +179 -0
- package/README.md +54 -3
- package/dist/agents/tp-api-surface-tracker.md +4 -3
- package/dist/agents/tp-audit-scanner.md +1 -1
- package/dist/agents/tp-commit-writer.md +1 -1
- package/dist/agents/tp-dead-code-finder.md +22 -7
- package/dist/agents/tp-debugger.md +1 -1
- package/dist/agents/tp-dep-health.md +3 -2
- package/dist/agents/tp-history-explorer.md +1 -1
- package/dist/agents/tp-impact-analyzer.md +1 -1
- package/dist/agents/tp-incident-timeline.md +1 -1
- package/dist/agents/tp-migration-scout.md +1 -1
- package/dist/agents/tp-onboard.md +1 -1
- package/dist/agents/tp-pr-reviewer.md +1 -1
- package/dist/agents/tp-refactor-planner.md +1 -1
- package/dist/agents/tp-review-impact.md +1 -1
- package/dist/agents/tp-run.md +1 -1
- package/dist/agents/tp-session-restorer.md +1 -1
- package/dist/agents/tp-test-coverage-gapper.md +1 -1
- package/dist/agents/tp-test-triage.md +1 -1
- package/dist/agents/tp-test-writer.md +1 -1
- package/dist/cli/detect-client.d.ts +39 -0
- package/dist/cli/detect-client.js +106 -0
- package/dist/cli/install-agents.d.ts +1 -0
- package/dist/cli/install-agents.js +31 -1
- package/dist/cli/tool-audit.d.ts +58 -0
- package/dist/cli/tool-audit.js +123 -0
- package/dist/cli/typo-guard.d.ts +1 -1
- package/dist/cli/typo-guard.js +1 -0
- package/dist/core/tool-call-log.d.ts +63 -0
- package/dist/core/tool-call-log.js +171 -0
- package/dist/handlers/read-symbols.js +23 -1
- package/dist/hooks/installer.js +27 -12
- package/dist/index.js +71 -0
- package/dist/server/profile-recommender.d.ts +48 -0
- package/dist/server/profile-recommender.js +102 -0
- package/dist/server/token-estimates.d.ts +17 -3
- package/dist/server/token-estimates.js +77 -45
- package/dist/server/tool-definitions.js +1 -1
- package/dist/server/tool-profiles.d.ts +46 -0
- package/dist/server/tool-profiles.js +81 -0
- package/dist/server.js +38 -1
- package/package.json +1 -1
- package/start.sh +0 -0
- package/.mcp.json +0 -8
|
@@ -0,0 +1,81 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* v0.26.3 — tool profiles.
|
|
3
|
+
*
|
|
4
|
+
* Idea lifted honestly from Token Savior's TOKEN_SAVIOR_PROFILE. When an
|
|
5
|
+
* MCP server advertises 22 tools, every tools/list response costs the
|
|
6
|
+
* agent ~3 k tokens before it does anything. Most sessions don't need
|
|
7
|
+
* every tool — a code-review agent uses smart_read + find_usages +
|
|
8
|
+
* outline and nothing else. A profile lets the user ship a narrower
|
|
9
|
+
* tools/list while keeping the handlers live (so a subagent or another
|
|
10
|
+
* user in the same server can still reach the full set if they know
|
|
11
|
+
* the name).
|
|
12
|
+
*
|
|
13
|
+
* Three profiles:
|
|
14
|
+
* - full (default): everything, same as pre-v0.26.3.
|
|
15
|
+
* - nav : read-only exploration. smart_read, outline, find_usages,
|
|
16
|
+
* read_symbol, project_overview, module_info, related_files,
|
|
17
|
+
* explore_area, smart_log, smart_diff.
|
|
18
|
+
* - edit : nav + batch reads + everything Edit needs to hit a symbol
|
|
19
|
+
* precisely. Adds read_symbols, read_range, read_section,
|
|
20
|
+
* read_diff, read_for_edit, smart_read_many.
|
|
21
|
+
*
|
|
22
|
+
* Selection: TOKEN_PILOT_PROFILE=nav|edit|full env var. Unknown values
|
|
23
|
+
* fall back to full with a stderr warning. Silent on missing env.
|
|
24
|
+
*/
|
|
25
|
+
export const PROFILE_NAMES = [
|
|
26
|
+
"full",
|
|
27
|
+
"nav",
|
|
28
|
+
"edit",
|
|
29
|
+
];
|
|
30
|
+
/** Minimum nav profile — exploration only, no editing support. */
|
|
31
|
+
export const NAV_TOOLS = new Set([
|
|
32
|
+
"smart_read",
|
|
33
|
+
"read_symbol",
|
|
34
|
+
"outline",
|
|
35
|
+
"find_usages",
|
|
36
|
+
"project_overview",
|
|
37
|
+
"module_info",
|
|
38
|
+
"related_files",
|
|
39
|
+
"explore_area",
|
|
40
|
+
"smart_log",
|
|
41
|
+
"smart_diff",
|
|
42
|
+
]);
|
|
43
|
+
/** Edit profile adds batch reads + edit-preparation tools. */
|
|
44
|
+
export const EDIT_EXTRAS = new Set([
|
|
45
|
+
"read_symbols",
|
|
46
|
+
"read_range",
|
|
47
|
+
"read_section",
|
|
48
|
+
"read_diff",
|
|
49
|
+
"read_for_edit",
|
|
50
|
+
"smart_read_many",
|
|
51
|
+
]);
|
|
52
|
+
/**
|
|
53
|
+
* Decide which tools the LLM sees in tools/list given a profile.
|
|
54
|
+
* Pure — safe to unit-test without spinning up the server.
|
|
55
|
+
*
|
|
56
|
+
* Tool names NOT matched by any profile rule (e.g. future additions)
|
|
57
|
+
* fall into 'full' only, to stay conservative by default.
|
|
58
|
+
*/
|
|
59
|
+
export function filterToolsByProfile(tools, profile) {
|
|
60
|
+
if (profile === "full")
|
|
61
|
+
return [...tools];
|
|
62
|
+
if (profile === "nav")
|
|
63
|
+
return tools.filter((t) => NAV_TOOLS.has(t.name));
|
|
64
|
+
// edit = nav + extras
|
|
65
|
+
return tools.filter((t) => NAV_TOOLS.has(t.name) || EDIT_EXTRAS.has(t.name));
|
|
66
|
+
}
|
|
67
|
+
/**
|
|
68
|
+
* Parse the TOKEN_PILOT_PROFILE env value. Unknown values get a warning
|
|
69
|
+
* and fall back to full — we never silently apply a guess.
|
|
70
|
+
*/
|
|
71
|
+
export function parseProfileEnv(envValue, warn = () => { }) {
|
|
72
|
+
if (!envValue)
|
|
73
|
+
return "full";
|
|
74
|
+
const lower = envValue.trim().toLowerCase();
|
|
75
|
+
if (lower === "full" || lower === "nav" || lower === "edit") {
|
|
76
|
+
return lower;
|
|
77
|
+
}
|
|
78
|
+
warn(`[token-pilot] Unknown TOKEN_PILOT_PROFILE="${envValue}". Expected full|nav|edit. Falling back to full.`);
|
|
79
|
+
return "full";
|
|
80
|
+
}
|
|
81
|
+
//# sourceMappingURL=tool-profiles.js.map
|
package/dist/server.js
CHANGED
|
@@ -44,7 +44,9 @@ import { handleReadSection } from "./handlers/read-section.js";
|
|
|
44
44
|
import { detectContextMode } from "./integration/context-mode-detector.js";
|
|
45
45
|
import { estimateTokens } from "./core/token-estimator.js";
|
|
46
46
|
import { checkPolicy, isFullReadTool } from "./core/policy-engine.js";
|
|
47
|
+
import { appendToolCall } from "./core/tool-call-log.js";
|
|
47
48
|
import { MCP_INSTRUCTIONS, TOOL_DEFINITIONS, } from "./server/tool-definitions.js";
|
|
49
|
+
import { filterToolsByProfile, parseProfileEnv, } from "./server/tool-profiles.js";
|
|
48
50
|
import { createTokenEstimates } from "./server/token-estimates.js";
|
|
49
51
|
import { validateSmartReadArgs, validateReadSymbolArgs, validateReadSymbolsArgs, validateReadRangeArgs, validateReadDiffArgs, validateFindUsagesArgs, validateSmartReadManyArgs, validateReadForEditArgs, validateRelatedFilesArgs, validateOutlineArgs, validateFindUnusedArgs, validateCodeAuditArgs, validateProjectOverviewArgs, validateModuleInfoArgs, validateSmartDiffArgs, validateExploreAreaArgs, validateSmartLogArgs, validateTestSummaryArgs, validateReadSectionArgs, } from "./core/validation.js";
|
|
50
52
|
export async function createServer(projectRoot, options) {
|
|
@@ -240,14 +242,33 @@ export async function createServer(projectRoot, options) {
|
|
|
240
242
|
capabilities: { tools: {} },
|
|
241
243
|
instructions: MCP_INSTRUCTIONS,
|
|
242
244
|
});
|
|
245
|
+
// v0.26.3 — tool profiles. TOKEN_PILOT_PROFILE=nav|edit|full (default
|
|
246
|
+
// full) trims the advertised tools/list payload. Handlers stay live,
|
|
247
|
+
// so a subagent that explicitly names a filtered-out tool still gets
|
|
248
|
+
// a response — we just don't brag about every tool upfront.
|
|
249
|
+
const activeProfile = parseProfileEnv(process.env.TOKEN_PILOT_PROFILE, (m) => process.stderr.write(m + "\n"));
|
|
250
|
+
const advertisedTools = filterToolsByProfile(TOOL_DEFINITIONS, activeProfile);
|
|
251
|
+
if (activeProfile !== "full") {
|
|
252
|
+
process.stderr.write(`[token-pilot] Profile: ${activeProfile} — advertising ${advertisedTools.length}/${TOOL_DEFINITIONS.length} tools. Unset TOKEN_PILOT_PROFILE for the full set.\n`);
|
|
253
|
+
}
|
|
243
254
|
server.setRequestHandler(ListToolsRequestSchema, () => ({
|
|
244
|
-
tools:
|
|
255
|
+
tools: advertisedTools,
|
|
245
256
|
}));
|
|
246
257
|
// Token estimation functions (extracted to server/token-estimates.ts)
|
|
247
258
|
const { fullFileTokens, estimateProjectOverviewWorkflowTokens, estimateOutlineWorkflowTokens, estimateRelatedFilesWorkflowTokens, estimateFindUsagesWorkflowTokens, estimateExploreAreaWorkflowTokens, detectSavingsCategory, } = createTokenEstimates(() => projectRoot, fileCache);
|
|
248
259
|
/** Record analytics with intent classification and decision trace. Returns policy advisory if any. */
|
|
249
260
|
function recordWithTrace(call) {
|
|
250
261
|
const { absPath, args, recentlyEdited, ...rest } = call;
|
|
262
|
+
// v0.26.1 — honest accounting. When a handler signals 'none' as
|
|
263
|
+
// the savings category (e.g. smart_read small-file pass-through),
|
|
264
|
+
// we weren't compressing anything — the caller got the file back
|
|
265
|
+
// verbatim plus a tiny header. Claiming wouldBe = fullFile here
|
|
266
|
+
// produced the -2% "negative savings" line on Opus 4.7's
|
|
267
|
+
// session_analytics. Zero the delta: 0% savings claimed, no ghost
|
|
268
|
+
// overhead.
|
|
269
|
+
if (rest.savingsCategory === "none") {
|
|
270
|
+
rest.tokensWouldBe = rest.tokensReturned;
|
|
271
|
+
}
|
|
251
272
|
analytics.record({
|
|
252
273
|
...rest,
|
|
253
274
|
intent: classifyIntent(rest.tool),
|
|
@@ -279,6 +300,22 @@ export async function createServer(projectRoot, options) {
|
|
|
279
300
|
totalCallCount,
|
|
280
301
|
totalTokensReturned,
|
|
281
302
|
});
|
|
303
|
+
// v0.26.2 — persist for cumulative tool-audit. Fire-and-forget;
|
|
304
|
+
// disk failures must not block the tool-response path. The audit
|
|
305
|
+
// CLI reads all archives + current to build a per-tool savings
|
|
306
|
+
// distribution across sessions, which is the foundation for any
|
|
307
|
+
// future prune/fix decision.
|
|
308
|
+
void appendToolCall(projectRoot, {
|
|
309
|
+
ts: rest.timestamp,
|
|
310
|
+
session_id: call.sessionId ?? "",
|
|
311
|
+
tool: rest.tool,
|
|
312
|
+
path: rest.path,
|
|
313
|
+
tokensReturned: rest.tokensReturned,
|
|
314
|
+
tokensWouldBe: rest.tokensWouldBe,
|
|
315
|
+
savingsCategory: rest.savingsCategory ?? "compression",
|
|
316
|
+
sessionCacheHit: rest.sessionCacheHit,
|
|
317
|
+
delegatedToContextMode: rest.delegatedToContextMode,
|
|
318
|
+
});
|
|
282
319
|
return advisory ? `\n${advisory.message}` : null;
|
|
283
320
|
}
|
|
284
321
|
// Handle tool calls with validated arguments
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "token-pilot",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.26.6",
|
|
4
4
|
"description": "Save up to 80% tokens when AI reads code — MCP server for token-efficient code navigation, AST-aware structural reading instead of dumping full files into context window",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"main": "dist/index.js",
|
package/start.sh
CHANGED
|
File without changes
|