ctxman 3.1.1 → 3.2.8
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/.ctxman/llm-profiles.json +6 -6
- package/README.md +16 -10
- package/bin/cli.js +109 -10
- package/bin/cm-ask.js +64 -6
- package/bin/cm-audit.js +76 -0
- package/bin/cm-count.js +45 -6
- package/bin/cm-diagnose.js +199 -0
- package/bin/cm-focus.js +322 -0
- package/bin/cm-map.js +71 -18
- package/bin/cm-pack.js +36 -5
- package/bin/cm-policy.js +107 -2
- package/bin/cm-pr.js +18 -3
- package/bin/cm-search.js +84 -19
- package/bin/cm-task.js +192 -0
- package/bin/cm-who.js +119 -0
- package/bin/cm-why.js +41 -5
- package/index.d.ts +940 -1
- package/index.js +105 -1
- package/lib/analyzers/token-calculator.js +76 -4
- package/lib/api/mcp/server.js +843 -29
- package/lib/cache/CacheManager.js +161 -47
- package/lib/core/Analyzer.js +61 -5
- package/lib/count/index.js +74 -14
- package/lib/diagnose/index.js +712 -0
- package/lib/focus/index.js +790 -0
- package/lib/map/call-graph.js +570 -0
- package/lib/map/graph.js +30 -5
- package/lib/map/index.js +12 -4
- package/lib/map/rank.js +45 -7
- package/lib/map/render.js +89 -28
- package/lib/pack/index.js +20 -1
- package/lib/pack/select.js +8 -1
- package/lib/policy/audit.js +3 -1
- package/lib/policy/index.js +5 -0
- package/lib/policy/workspace.js +254 -0
- package/lib/pr/pr-context.js +292 -31
- package/lib/pr/pr-renderer.js +25 -10
- package/lib/rag/EmbeddingProvider.js +139 -2
- package/lib/rag/VectorStoreFactory.js +10 -4
- package/lib/rag/ask.js +186 -17
- package/lib/rag/stores/SqliteVectorStore.js +595 -0
- package/lib/search/hybrid.js +324 -0
- package/lib/search/symbols.js +75 -11
- package/lib/task/index.js +630 -0
- package/lib/utils/file-utils.js +1 -0
- package/lib/utils/multi-repo-manager.js +4 -1
- package/lib/watch/FileWatcher.js +121 -31
- package/lib/watch/IncrementalAnalyzer.js +964 -16
- package/lib/who/index.js +893 -0
- package/lib/why/analyzer-bridge.js +223 -0
- package/lib/why/discussions.js +314 -0
- package/lib/why/index.js +356 -30
- package/lib/why/render.js +154 -9
- package/lib/workspace/index.js +1274 -0
- package/package.json +1 -1
package/index.d.ts
CHANGED
|
@@ -20,6 +20,8 @@ export interface TokenCalculatorOptions {
|
|
|
20
20
|
gitingest?: boolean;
|
|
21
21
|
targetModel?: string;
|
|
22
22
|
dashboard?: boolean;
|
|
23
|
+
cache?: boolean | 'memory' | 'disk' | CacheManagerOptions | CacheManager;
|
|
24
|
+
cachePath?: string;
|
|
23
25
|
}
|
|
24
26
|
|
|
25
27
|
/**
|
|
@@ -852,6 +854,21 @@ export interface RepoMapMethod {
|
|
|
852
854
|
line: number;
|
|
853
855
|
/** Declaration on one line, secrets redacted unless `redact: false` */
|
|
854
856
|
signature: string;
|
|
857
|
+
/** Identifiers invoked inside this method body */
|
|
858
|
+
calls?: string[];
|
|
859
|
+
}
|
|
860
|
+
|
|
861
|
+
/**
|
|
862
|
+
* Cross-file symbol call edge, caller file/symbol -> callee file/symbol.
|
|
863
|
+
*/
|
|
864
|
+
export interface RepoGraphCallEdge {
|
|
865
|
+
from: string;
|
|
866
|
+
caller: string;
|
|
867
|
+
callerLine: number;
|
|
868
|
+
to: string;
|
|
869
|
+
callee: string;
|
|
870
|
+
calleeLine: number;
|
|
871
|
+
weight: number;
|
|
855
872
|
}
|
|
856
873
|
|
|
857
874
|
/**
|
|
@@ -884,6 +901,7 @@ export interface RepoGraph {
|
|
|
884
901
|
root: string;
|
|
885
902
|
nodes: RepoGraphNode[];
|
|
886
903
|
edges: RepoGraphEdge[];
|
|
904
|
+
callEdges?: RepoGraphCallEdge[];
|
|
887
905
|
history: {
|
|
888
906
|
available: boolean;
|
|
889
907
|
requested: number;
|
|
@@ -896,6 +914,7 @@ export interface RepoGraph {
|
|
|
896
914
|
scannedFiles: number;
|
|
897
915
|
files: number;
|
|
898
916
|
edges: number;
|
|
917
|
+
callEdges?: number;
|
|
899
918
|
unresolvedImports: number;
|
|
900
919
|
skipped: Array<{ path: string; reason: string }>;
|
|
901
920
|
redactions: Record<string, number>;
|
|
@@ -919,12 +938,14 @@ export interface RankWeights {
|
|
|
919
938
|
}
|
|
920
939
|
|
|
921
940
|
export interface RankOptions {
|
|
922
|
-
/** Files
|
|
941
|
+
/** Files, folders or file:symbol targets to personalise PageRank toward */
|
|
923
942
|
focus?: string[];
|
|
924
943
|
/** Blend of the normalised components (default 0.70 / 0.25 / 0.05) */
|
|
925
944
|
weights?: RankWeights;
|
|
926
945
|
/** PageRank damping (default 0.85) */
|
|
927
946
|
damping?: number;
|
|
947
|
+
/** Include cross-file AST symbol call edges in PageRank and focus expansion */
|
|
948
|
+
callGraph?: boolean;
|
|
928
949
|
}
|
|
929
950
|
|
|
930
951
|
export interface RankedFile {
|
|
@@ -953,6 +974,8 @@ export interface RepoMapOptions extends RepoGraphOptions, RankOptions {
|
|
|
953
974
|
style?: 'text' | 'markdown' | 'json' | 'dot';
|
|
954
975
|
/** Render the dependency edges instead of the map */
|
|
955
976
|
graph?: boolean;
|
|
977
|
+
/** Annotate methods with cross-file call targets and include call edges in graph/ranking */
|
|
978
|
+
callGraph?: boolean;
|
|
956
979
|
}
|
|
957
980
|
|
|
958
981
|
export interface RepoMapFile {
|
|
@@ -987,6 +1010,15 @@ export interface RepoMapResult {
|
|
|
987
1010
|
*/
|
|
988
1011
|
export function buildRepoGraph(root: string, options?: RepoGraphOptions): RepoGraph;
|
|
989
1012
|
|
|
1013
|
+
/**
|
|
1014
|
+
* Build cross-file AST symbol call edges across mapped nodes and import edges
|
|
1015
|
+
*/
|
|
1016
|
+
export function buildCallGraph(
|
|
1017
|
+
nodes: RepoGraphNode[],
|
|
1018
|
+
edges: RepoGraphEdge[],
|
|
1019
|
+
contentsByPath?: Map<string, string>
|
|
1020
|
+
): RepoGraphCallEdge[];
|
|
1021
|
+
|
|
990
1022
|
/**
|
|
991
1023
|
* Rank the files of a graph, best first: PageRank blended with git change frequency and
|
|
992
1024
|
* symbol references
|
|
@@ -1035,6 +1067,8 @@ export interface PrContextOptions {
|
|
|
1035
1067
|
maxFileBytes?: number;
|
|
1036
1068
|
/** Most related tests to list (default: 50) */
|
|
1037
1069
|
maxRelatedTests?: number;
|
|
1070
|
+
/** Additional repositories for multi-repo PR review context */
|
|
1071
|
+
repos?: WorkspaceRepoInput[];
|
|
1038
1072
|
}
|
|
1039
1073
|
|
|
1040
1074
|
export interface PrRevision {
|
|
@@ -1072,6 +1106,7 @@ export interface PrChangedMethod extends PrMethod {
|
|
|
1072
1106
|
}
|
|
1073
1107
|
|
|
1074
1108
|
export interface PrCommit {
|
|
1109
|
+
repo?: string;
|
|
1075
1110
|
sha: string;
|
|
1076
1111
|
short: string;
|
|
1077
1112
|
author: string;
|
|
@@ -1088,6 +1123,8 @@ export interface PrRelatedTest {
|
|
|
1088
1123
|
}
|
|
1089
1124
|
|
|
1090
1125
|
export interface PrContextResult {
|
|
1126
|
+
/** Participating repositories when `repos` was supplied */
|
|
1127
|
+
repos?: Array<{ alias: string; root: string }>;
|
|
1091
1128
|
/** The rendered context */
|
|
1092
1129
|
output: string;
|
|
1093
1130
|
/** Tokens of `output` */
|
|
@@ -1153,6 +1190,20 @@ export interface ExplainHistoryOptions {
|
|
|
1153
1190
|
rev?: string;
|
|
1154
1191
|
/** Include each commit's diff of the target */
|
|
1155
1192
|
patches?: boolean;
|
|
1193
|
+
/** Fetch referenced GitHub/GitLab issue, PR and MR discussions (default false) */
|
|
1194
|
+
discussions?: boolean;
|
|
1195
|
+
/** Maximum remote discussions fetched (default 10) */
|
|
1196
|
+
maxDiscussions?: number;
|
|
1197
|
+
/** Maximum comments fetched per discussion (default 5) */
|
|
1198
|
+
maxComments?: number;
|
|
1199
|
+
/** Per-request timeout in milliseconds (default 5000) */
|
|
1200
|
+
discussionTimeoutMs?: number;
|
|
1201
|
+
/** Explicit GitHub/GitLab API token override */
|
|
1202
|
+
token?: string;
|
|
1203
|
+
/** Custom fetch implementation */
|
|
1204
|
+
fetch?: typeof globalThis.fetch;
|
|
1205
|
+
/** Environment override for token lookup */
|
|
1206
|
+
env?: NodeJS.ProcessEnv;
|
|
1156
1207
|
/** Commits of the file examined for co-changes (default 500, 0 = off) */
|
|
1157
1208
|
couplingWindow?: number;
|
|
1158
1209
|
/** Co-changed files listed (default 10) */
|
|
@@ -1172,6 +1223,8 @@ export interface ExplainHistoryOptions {
|
|
|
1172
1223
|
redact?: boolean;
|
|
1173
1224
|
/** Directory relative target paths start from (default: root) */
|
|
1174
1225
|
cwd?: string;
|
|
1226
|
+
/** Additional repositories for multi-repo history & cross-repo ADR/doc/test lookup */
|
|
1227
|
+
repos?: WorkspaceRepoInput[];
|
|
1175
1228
|
}
|
|
1176
1229
|
|
|
1177
1230
|
export interface WhyCommit {
|
|
@@ -1204,6 +1257,7 @@ export interface WhyIssueReference {
|
|
|
1204
1257
|
}
|
|
1205
1258
|
|
|
1206
1259
|
export interface ExplainHistoryData {
|
|
1260
|
+
repos?: Array<{ alias: string; root: string }>;
|
|
1207
1261
|
target: {
|
|
1208
1262
|
path: string;
|
|
1209
1263
|
symbol: string | null;
|
|
@@ -1240,6 +1294,26 @@ export interface ExplainHistoryData {
|
|
|
1240
1294
|
coAuthors: Array<{ value: string; commits: string[] }>;
|
|
1241
1295
|
reviewers: Array<{ value: string; commits: string[] }>;
|
|
1242
1296
|
};
|
|
1297
|
+
discussions: Array<{
|
|
1298
|
+
id: string;
|
|
1299
|
+
number: number;
|
|
1300
|
+
repo: string;
|
|
1301
|
+
provider: 'github' | 'gitlab';
|
|
1302
|
+
kind: 'issue' | 'pr' | 'mr';
|
|
1303
|
+
title: string;
|
|
1304
|
+
state: string;
|
|
1305
|
+
author: string;
|
|
1306
|
+
createdAt: string | null;
|
|
1307
|
+
url: string | null;
|
|
1308
|
+
labels: string[];
|
|
1309
|
+
body: string;
|
|
1310
|
+
commits: string[];
|
|
1311
|
+
comments: Array<{
|
|
1312
|
+
author: string;
|
|
1313
|
+
createdAt: string | null;
|
|
1314
|
+
body: string;
|
|
1315
|
+
}>;
|
|
1316
|
+
}>;
|
|
1243
1317
|
ownership: {
|
|
1244
1318
|
startLine: number | null;
|
|
1245
1319
|
endLine: number | null;
|
|
@@ -1282,6 +1356,8 @@ export interface ExplainHistoryData {
|
|
|
1282
1356
|
}
|
|
1283
1357
|
|
|
1284
1358
|
export interface ExplainHistoryResult {
|
|
1359
|
+
/** Participating repositories when `repos` was supplied */
|
|
1360
|
+
repos?: Array<{ alias: string; root: string }>;
|
|
1285
1361
|
/** The rendered document */
|
|
1286
1362
|
text: string;
|
|
1287
1363
|
style: 'markdown' | 'xml' | 'json';
|
|
@@ -1420,3 +1496,866 @@ export interface PackResult {
|
|
|
1420
1496
|
* BUDGET_TOO_SMALL, SPLIT_TOO_SMALL).
|
|
1421
1497
|
*/
|
|
1422
1498
|
export function packContext(root: string, options?: PackOptions): Promise<PackResult>;
|
|
1499
|
+
|
|
1500
|
+
// ============================================
|
|
1501
|
+
// Core v3 Modular Pipeline & Cache
|
|
1502
|
+
// ============================================
|
|
1503
|
+
|
|
1504
|
+
export interface CacheManagerOptions {
|
|
1505
|
+
enabled?: boolean;
|
|
1506
|
+
strategy?: 'disk' | 'memory';
|
|
1507
|
+
ttl?: number;
|
|
1508
|
+
path?: string;
|
|
1509
|
+
maxEntries?: number;
|
|
1510
|
+
maxSize?: number;
|
|
1511
|
+
}
|
|
1512
|
+
|
|
1513
|
+
export interface CacheMeta {
|
|
1514
|
+
size?: number;
|
|
1515
|
+
namespace?: string;
|
|
1516
|
+
encoding?: string;
|
|
1517
|
+
methodLevel?: boolean;
|
|
1518
|
+
extraKey?: string;
|
|
1519
|
+
}
|
|
1520
|
+
|
|
1521
|
+
export class CacheManager {
|
|
1522
|
+
constructor(options?: CacheManagerOptions);
|
|
1523
|
+
options: Required<CacheManagerOptions>;
|
|
1524
|
+
stats: {
|
|
1525
|
+
hits: number;
|
|
1526
|
+
misses: number;
|
|
1527
|
+
writes: number;
|
|
1528
|
+
evictions: number;
|
|
1529
|
+
errors: number;
|
|
1530
|
+
};
|
|
1531
|
+
get(
|
|
1532
|
+
filePath: string,
|
|
1533
|
+
modifiedTime: number | Date | null,
|
|
1534
|
+
meta?: CacheMeta
|
|
1535
|
+
): Record<string, unknown> | null;
|
|
1536
|
+
set(
|
|
1537
|
+
filePath: string,
|
|
1538
|
+
analysis: Record<string, unknown>,
|
|
1539
|
+
modifiedTime: number | Date | null,
|
|
1540
|
+
meta?: CacheMeta
|
|
1541
|
+
): void;
|
|
1542
|
+
isExpired(
|
|
1543
|
+
cacheTimestamp: number,
|
|
1544
|
+
cacheModifiedTime: number | null,
|
|
1545
|
+
currentModifiedTime: number | Date | null,
|
|
1546
|
+
cachedSize?: number | null,
|
|
1547
|
+
currentSize?: number | null
|
|
1548
|
+
): boolean;
|
|
1549
|
+
getCacheKey(filePath: string, meta?: CacheMeta): string;
|
|
1550
|
+
clear(): void;
|
|
1551
|
+
prune(): void;
|
|
1552
|
+
getStats(): {
|
|
1553
|
+
hits: number;
|
|
1554
|
+
misses: number;
|
|
1555
|
+
writes: number;
|
|
1556
|
+
evictions: number;
|
|
1557
|
+
errors: number;
|
|
1558
|
+
totalRequests: number;
|
|
1559
|
+
hitRate: number;
|
|
1560
|
+
cacheSize: number;
|
|
1561
|
+
};
|
|
1562
|
+
}
|
|
1563
|
+
|
|
1564
|
+
export function resolveCacheManager(
|
|
1565
|
+
cacheOption: boolean | 'memory' | 'disk' | CacheManagerOptions | CacheManager | null | undefined,
|
|
1566
|
+
defaults?: CacheManagerOptions
|
|
1567
|
+
): CacheManager | null;
|
|
1568
|
+
|
|
1569
|
+
export interface ScannedFile {
|
|
1570
|
+
path: string;
|
|
1571
|
+
relativePath: string;
|
|
1572
|
+
name: string;
|
|
1573
|
+
extension: string;
|
|
1574
|
+
size: number;
|
|
1575
|
+
modified: Date;
|
|
1576
|
+
created: Date;
|
|
1577
|
+
}
|
|
1578
|
+
|
|
1579
|
+
export interface ScannerOptions {
|
|
1580
|
+
respectGitignore?: boolean;
|
|
1581
|
+
followSymlinks?: boolean;
|
|
1582
|
+
maxDepth?: number;
|
|
1583
|
+
policy?: Policy | false | null;
|
|
1584
|
+
respectIgnoreFiles?: string | string[];
|
|
1585
|
+
env?: NodeJS.ProcessEnv;
|
|
1586
|
+
}
|
|
1587
|
+
|
|
1588
|
+
export class Scanner {
|
|
1589
|
+
constructor(rootPath: string, options?: ScannerOptions);
|
|
1590
|
+
rootPath: string;
|
|
1591
|
+
scan(): ScannedFile[];
|
|
1592
|
+
isDenied(relativePath: string): boolean;
|
|
1593
|
+
shouldIgnore(relativePath: string, fullPath?: string): boolean;
|
|
1594
|
+
getPolicy(): Policy | null;
|
|
1595
|
+
getStats(): {
|
|
1596
|
+
filesScanned: number;
|
|
1597
|
+
directoriesTraversed: number;
|
|
1598
|
+
filesIgnored: number;
|
|
1599
|
+
filesDenied: number;
|
|
1600
|
+
errors: number;
|
|
1601
|
+
};
|
|
1602
|
+
reset(): void;
|
|
1603
|
+
}
|
|
1604
|
+
|
|
1605
|
+
export interface AnalyzerOptions {
|
|
1606
|
+
methodLevel?: boolean;
|
|
1607
|
+
parallel?: boolean;
|
|
1608
|
+
maxWorkers?: number;
|
|
1609
|
+
targetModel?: string | null;
|
|
1610
|
+
encoding?: string;
|
|
1611
|
+
cache?: boolean | 'memory' | 'disk' | CacheManagerOptions | CacheManager;
|
|
1612
|
+
cachePath?: string;
|
|
1613
|
+
}
|
|
1614
|
+
|
|
1615
|
+
export interface AnalyzedFile {
|
|
1616
|
+
path: string;
|
|
1617
|
+
relativePath: string;
|
|
1618
|
+
name: string;
|
|
1619
|
+
extension: string;
|
|
1620
|
+
size: number;
|
|
1621
|
+
modified: Date | number;
|
|
1622
|
+
tokens: number;
|
|
1623
|
+
lines: number;
|
|
1624
|
+
language: string;
|
|
1625
|
+
methods?: MethodInfo[];
|
|
1626
|
+
methodCount?: number;
|
|
1627
|
+
}
|
|
1628
|
+
|
|
1629
|
+
export interface AnalyzerStats {
|
|
1630
|
+
totalFiles: number;
|
|
1631
|
+
totalTokens: number;
|
|
1632
|
+
totalSize: number;
|
|
1633
|
+
totalMethods: number;
|
|
1634
|
+
totalLines: number;
|
|
1635
|
+
byLanguage: Record<string, { files: number; tokens: number; size: number }>;
|
|
1636
|
+
largestFiles: Array<{ path: string; tokens: number; size: number }>;
|
|
1637
|
+
analysisTime: number;
|
|
1638
|
+
cacheHits?: number;
|
|
1639
|
+
cacheMisses?: number;
|
|
1640
|
+
}
|
|
1641
|
+
|
|
1642
|
+
export class Analyzer {
|
|
1643
|
+
constructor(options?: AnalyzerOptions);
|
|
1644
|
+
analyze(files: ScannedFile[]): Promise<{ files: AnalyzedFile[]; stats: AnalyzerStats }>;
|
|
1645
|
+
analyzeFile(fileInfo: ScannedFile): Promise<AnalyzedFile | null>;
|
|
1646
|
+
getStats(): AnalyzerStats;
|
|
1647
|
+
reset(): void;
|
|
1648
|
+
getLanguageDistribution(): Array<{
|
|
1649
|
+
language: string;
|
|
1650
|
+
files: number;
|
|
1651
|
+
tokens: number;
|
|
1652
|
+
size: number;
|
|
1653
|
+
percentage: number;
|
|
1654
|
+
}>;
|
|
1655
|
+
}
|
|
1656
|
+
|
|
1657
|
+
export interface ContextBuilderOptions {
|
|
1658
|
+
targetModel?: string | null;
|
|
1659
|
+
targetTokens?: number | null;
|
|
1660
|
+
useCase?: string;
|
|
1661
|
+
includeTests?: boolean;
|
|
1662
|
+
includeDocumentation?: boolean;
|
|
1663
|
+
methodLevel?: boolean;
|
|
1664
|
+
priorityStrategy?: 'balanced' | 'changed-first' | 'core-first';
|
|
1665
|
+
}
|
|
1666
|
+
|
|
1667
|
+
export class ContextBuilder {
|
|
1668
|
+
constructor(options?: ContextBuilderOptions);
|
|
1669
|
+
build(analysisResult: { files: AnalyzedFile[]; stats: AnalyzerStats }): Record<string, unknown>;
|
|
1670
|
+
getSummary(context: Record<string, unknown>): string;
|
|
1671
|
+
}
|
|
1672
|
+
|
|
1673
|
+
export interface ReporterOptions {
|
|
1674
|
+
format?: string;
|
|
1675
|
+
outputPath?: string | null;
|
|
1676
|
+
clipboard?: boolean;
|
|
1677
|
+
verbose?: boolean;
|
|
1678
|
+
}
|
|
1679
|
+
|
|
1680
|
+
export class Reporter {
|
|
1681
|
+
constructor(options?: ReporterOptions);
|
|
1682
|
+
report(context: Record<string, unknown>, stats: AnalyzerStats): Promise<void>;
|
|
1683
|
+
exportToFile(context: Record<string, unknown>, outputPath: string): Promise<void>;
|
|
1684
|
+
exportToClipboard(context: Record<string, unknown>): Promise<void>;
|
|
1685
|
+
generateSummary(context: Record<string, unknown>): string;
|
|
1686
|
+
}
|
|
1687
|
+
|
|
1688
|
+
// ============================================
|
|
1689
|
+
// Search, Symbol Lookup, Token Counting, RAG & Policy
|
|
1690
|
+
// ============================================
|
|
1691
|
+
|
|
1692
|
+
export interface SearchProjectOptions {
|
|
1693
|
+
limit?: number;
|
|
1694
|
+
maxTokens?: number;
|
|
1695
|
+
redact?: boolean;
|
|
1696
|
+
windowLines?: number;
|
|
1697
|
+
}
|
|
1698
|
+
|
|
1699
|
+
export interface SearchHit {
|
|
1700
|
+
file: string;
|
|
1701
|
+
name: string | null;
|
|
1702
|
+
kind: string;
|
|
1703
|
+
parent?: string;
|
|
1704
|
+
startLine: number;
|
|
1705
|
+
endLine: number;
|
|
1706
|
+
score: number;
|
|
1707
|
+
tokens: number;
|
|
1708
|
+
text: string | null;
|
|
1709
|
+
truncated?: boolean;
|
|
1710
|
+
}
|
|
1711
|
+
|
|
1712
|
+
export interface SearchProjectResult {
|
|
1713
|
+
query: string;
|
|
1714
|
+
root: string;
|
|
1715
|
+
files: number;
|
|
1716
|
+
chunks: number;
|
|
1717
|
+
tokens: number;
|
|
1718
|
+
results: SearchHit[];
|
|
1719
|
+
}
|
|
1720
|
+
|
|
1721
|
+
export function searchProject(
|
|
1722
|
+
root: string,
|
|
1723
|
+
query: string,
|
|
1724
|
+
options?: SearchProjectOptions
|
|
1725
|
+
): SearchProjectResult;
|
|
1726
|
+
|
|
1727
|
+
export interface GetSymbolOptions {
|
|
1728
|
+
file?: string;
|
|
1729
|
+
limit?: number;
|
|
1730
|
+
maxTokens?: number;
|
|
1731
|
+
redact?: boolean;
|
|
1732
|
+
repos?: WorkspaceRepoInput[];
|
|
1733
|
+
}
|
|
1734
|
+
|
|
1735
|
+
export interface SymbolMatch {
|
|
1736
|
+
name: string;
|
|
1737
|
+
kind: string;
|
|
1738
|
+
parent?: string;
|
|
1739
|
+
repo?: string;
|
|
1740
|
+
file: string;
|
|
1741
|
+
startLine: number;
|
|
1742
|
+
endLine: number;
|
|
1743
|
+
tokens: number;
|
|
1744
|
+
source: string;
|
|
1745
|
+
truncated?: boolean;
|
|
1746
|
+
}
|
|
1747
|
+
|
|
1748
|
+
export interface GetSymbolResult {
|
|
1749
|
+
query: string;
|
|
1750
|
+
match: 'exact' | 'case-insensitive' | 'none';
|
|
1751
|
+
total: number;
|
|
1752
|
+
repos?: Array<{ alias: string; root: string }>;
|
|
1753
|
+
symbols: SymbolMatch[];
|
|
1754
|
+
suggestions?: Array<{
|
|
1755
|
+
name: string;
|
|
1756
|
+
kind: string;
|
|
1757
|
+
parent?: string;
|
|
1758
|
+
file: string;
|
|
1759
|
+
startLine: number;
|
|
1760
|
+
}>;
|
|
1761
|
+
}
|
|
1762
|
+
|
|
1763
|
+
export function getSymbol(root: string, query: string, options?: GetSymbolOptions): GetSymbolResult;
|
|
1764
|
+
|
|
1765
|
+
export interface CountForModelOptions {
|
|
1766
|
+
model?: string;
|
|
1767
|
+
text?: string;
|
|
1768
|
+
repos?: WorkspaceRepoInput[];
|
|
1769
|
+
api?: boolean;
|
|
1770
|
+
client?: unknown;
|
|
1771
|
+
onProgress?: (done: number, total: number) => void;
|
|
1772
|
+
}
|
|
1773
|
+
|
|
1774
|
+
export interface CountForModelResult {
|
|
1775
|
+
model: string;
|
|
1776
|
+
modelName: string;
|
|
1777
|
+
vendor: string;
|
|
1778
|
+
files: number;
|
|
1779
|
+
encoding: string;
|
|
1780
|
+
localTokens: number;
|
|
1781
|
+
tokens: number;
|
|
1782
|
+
method: 'local' | 'anthropic-api';
|
|
1783
|
+
exact: boolean;
|
|
1784
|
+
contextWindow: number;
|
|
1785
|
+
fits: boolean;
|
|
1786
|
+
percentOfWindow: number;
|
|
1787
|
+
requests?: number;
|
|
1788
|
+
ratio?: number | null;
|
|
1789
|
+
repos?: Array<{
|
|
1790
|
+
alias: string;
|
|
1791
|
+
root: string;
|
|
1792
|
+
files: number;
|
|
1793
|
+
localTokens: number;
|
|
1794
|
+
tokens: number;
|
|
1795
|
+
percentOfWindow: number;
|
|
1796
|
+
}>;
|
|
1797
|
+
largestFiles: Array<{ path: string; tokens: number }>;
|
|
1798
|
+
}
|
|
1799
|
+
|
|
1800
|
+
export function countForModel(
|
|
1801
|
+
root: string,
|
|
1802
|
+
options?: CountForModelOptions
|
|
1803
|
+
): Promise<CountForModelResult>;
|
|
1804
|
+
|
|
1805
|
+
export interface AskCodebaseOptions {
|
|
1806
|
+
limit?: number;
|
|
1807
|
+
redact?: boolean;
|
|
1808
|
+
maxChars?: number;
|
|
1809
|
+
repos?: WorkspaceRepoInput[];
|
|
1810
|
+
onProgress?: (event: 'indexing' | 'indexed') => void;
|
|
1811
|
+
createStore?: (storePath: string, repo?: ResolvedWorkspaceRepo) => unknown;
|
|
1812
|
+
}
|
|
1813
|
+
|
|
1814
|
+
export interface AskCodebaseResult {
|
|
1815
|
+
query: string;
|
|
1816
|
+
indexed: boolean;
|
|
1817
|
+
repos?: Array<{ alias: string; root: string }>;
|
|
1818
|
+
results: Array<{
|
|
1819
|
+
repo?: string;
|
|
1820
|
+
file: string;
|
|
1821
|
+
score: number | null;
|
|
1822
|
+
text: string;
|
|
1823
|
+
truncated: boolean;
|
|
1824
|
+
}>;
|
|
1825
|
+
removedByPolicy: number;
|
|
1826
|
+
redactions: number;
|
|
1827
|
+
}
|
|
1828
|
+
|
|
1829
|
+
export function askCodebase(
|
|
1830
|
+
root: string,
|
|
1831
|
+
query: string,
|
|
1832
|
+
options?: AskCodebaseOptions
|
|
1833
|
+
): Promise<AskCodebaseResult>;
|
|
1834
|
+
|
|
1835
|
+
export class Policy {
|
|
1836
|
+
active: boolean;
|
|
1837
|
+
requireRedaction: boolean;
|
|
1838
|
+
maxExportTokens: number | null;
|
|
1839
|
+
allowedModels: string[] | null;
|
|
1840
|
+
ignoreFiles: string[];
|
|
1841
|
+
audit: { enabled: boolean; path: string };
|
|
1842
|
+
sources: Array<{ scope: string; file: string }>;
|
|
1843
|
+
isDenied(relativePath: string): boolean;
|
|
1844
|
+
isAuditLog(relativePath: string): boolean;
|
|
1845
|
+
toJSON(): Record<string, unknown>;
|
|
1846
|
+
}
|
|
1847
|
+
|
|
1848
|
+
export class PolicyConfigError extends Error {
|
|
1849
|
+
file: string;
|
|
1850
|
+
errors: string[];
|
|
1851
|
+
exitCode: number;
|
|
1852
|
+
}
|
|
1853
|
+
|
|
1854
|
+
export class PolicyViolationError extends Error {
|
|
1855
|
+
violations: Array<Record<string, unknown>>;
|
|
1856
|
+
exitCode: number;
|
|
1857
|
+
}
|
|
1858
|
+
|
|
1859
|
+
export function loadPolicy(rootPath: string, options?: { env?: NodeJS.ProcessEnv }): Policy;
|
|
1860
|
+
|
|
1861
|
+
export interface WorkspacePolicySummary {
|
|
1862
|
+
valid: boolean;
|
|
1863
|
+
active: boolean;
|
|
1864
|
+
requireRedaction: boolean;
|
|
1865
|
+
maxExportTokens: number | null;
|
|
1866
|
+
allowedTargetModels: Array<{
|
|
1867
|
+
repo: string;
|
|
1868
|
+
scope: string;
|
|
1869
|
+
file: string;
|
|
1870
|
+
patterns: string[];
|
|
1871
|
+
}> | null;
|
|
1872
|
+
ignoreFiles: string[];
|
|
1873
|
+
repos: Array<Record<string, unknown>>;
|
|
1874
|
+
}
|
|
1875
|
+
|
|
1876
|
+
export function checkWorkspacePolicies(
|
|
1877
|
+
primaryRoot: string,
|
|
1878
|
+
extraRepos?: WorkspaceRepoInput[],
|
|
1879
|
+
options?: { env?: NodeJS.ProcessEnv }
|
|
1880
|
+
): WorkspacePolicySummary;
|
|
1881
|
+
|
|
1882
|
+
export interface WorkspaceAuditResult {
|
|
1883
|
+
repos: Array<{ alias: string; root: string }>;
|
|
1884
|
+
files: string[];
|
|
1885
|
+
allFiles: string[];
|
|
1886
|
+
missing: string[];
|
|
1887
|
+
total: number;
|
|
1888
|
+
events: Array<Record<string, unknown>>;
|
|
1889
|
+
skippedLines: number;
|
|
1890
|
+
policyErrors: Array<{ repo: string; root: string; message: string }>;
|
|
1891
|
+
}
|
|
1892
|
+
|
|
1893
|
+
export function readWorkspaceAuditLogs(
|
|
1894
|
+
primaryRoot: string,
|
|
1895
|
+
extraRepos?: WorkspaceRepoInput[],
|
|
1896
|
+
options?: { since?: Date | null; limit?: number | null; env?: NodeJS.ProcessEnv }
|
|
1897
|
+
): WorkspaceAuditResult;
|
|
1898
|
+
|
|
1899
|
+
// ============================================
|
|
1900
|
+
// Focused Neighborhood Context (`ctxman focus`)
|
|
1901
|
+
// ============================================
|
|
1902
|
+
|
|
1903
|
+
export type FocusDirection = 'both' | 'imports' | 'importers' | 'calls' | 'callers';
|
|
1904
|
+
|
|
1905
|
+
export interface FocusOptions extends Omit<PackOptions, 'files'> {
|
|
1906
|
+
/** Target function or method name for symbol-level call graph traversal */
|
|
1907
|
+
symbol?: string;
|
|
1908
|
+
/** Graph traversal hops (default: 1; 0 = target file only) */
|
|
1909
|
+
depth?: number;
|
|
1910
|
+
/** Traversal direction (default: 'both') */
|
|
1911
|
+
direction?: FocusDirection;
|
|
1912
|
+
/** Include outgoing imports (default: true) */
|
|
1913
|
+
imports?: boolean;
|
|
1914
|
+
/** Include incoming importers (default: true) */
|
|
1915
|
+
importers?: boolean;
|
|
1916
|
+
/** Include cross-file AST symbol call graph edges (default: true) */
|
|
1917
|
+
callGraph?: boolean;
|
|
1918
|
+
/** Include outgoing cross-file calls (default: true) */
|
|
1919
|
+
calls?: boolean;
|
|
1920
|
+
/** Include incoming cross-file callers (default: true) */
|
|
1921
|
+
callers?: boolean;
|
|
1922
|
+
/** Include test files in neighborhood (default: true) */
|
|
1923
|
+
includeTests?: boolean;
|
|
1924
|
+
/** Git commits mined for tie-breaking PageRank (default: 0) */
|
|
1925
|
+
history?: number;
|
|
1926
|
+
/** Explicit rank order override */
|
|
1927
|
+
rankOrder?: string[];
|
|
1928
|
+
/** Additional repositories for multi-repo workspace focus */
|
|
1929
|
+
repos?: WorkspaceRepoInput[];
|
|
1930
|
+
}
|
|
1931
|
+
|
|
1932
|
+
export interface FocusNeighbor {
|
|
1933
|
+
path: string;
|
|
1934
|
+
distance: number;
|
|
1935
|
+
relation: 'import' | 'importer' | 'call' | 'caller' | 'both';
|
|
1936
|
+
score: number;
|
|
1937
|
+
}
|
|
1938
|
+
|
|
1939
|
+
export interface FocusMetadata {
|
|
1940
|
+
target: string;
|
|
1941
|
+
symbol?: string | null;
|
|
1942
|
+
depth: number;
|
|
1943
|
+
direction: FocusDirection;
|
|
1944
|
+
callGraph?: boolean;
|
|
1945
|
+
inGraph: boolean;
|
|
1946
|
+
neighbors: FocusNeighbor[];
|
|
1947
|
+
callEdges?: RepoGraphCallEdge[];
|
|
1948
|
+
repos?: Array<{ alias: string; root: string }>;
|
|
1949
|
+
}
|
|
1950
|
+
|
|
1951
|
+
export interface FocusResult extends PackResult {
|
|
1952
|
+
focus: FocusMetadata;
|
|
1953
|
+
repos?: Array<{ alias: string; root: string }>;
|
|
1954
|
+
}
|
|
1955
|
+
|
|
1956
|
+
export class FocusError extends Error {
|
|
1957
|
+
code: string;
|
|
1958
|
+
constructor(code: string, message: string);
|
|
1959
|
+
}
|
|
1960
|
+
|
|
1961
|
+
export function focusContext(
|
|
1962
|
+
root: string,
|
|
1963
|
+
target: string,
|
|
1964
|
+
options?: FocusOptions
|
|
1965
|
+
): Promise<FocusResult>;
|
|
1966
|
+
|
|
1967
|
+
export function describeFocus(result: FocusResult): string;
|
|
1968
|
+
|
|
1969
|
+
// ============================================
|
|
1970
|
+
// Hybrid Search (BM25 + Semantic RRF)
|
|
1971
|
+
// ============================================
|
|
1972
|
+
|
|
1973
|
+
export type HybridSearchMode = 'bm25' | 'semantic' | 'hybrid';
|
|
1974
|
+
|
|
1975
|
+
export interface HybridSearchOptions extends SearchProjectOptions {
|
|
1976
|
+
mode?: HybridSearchMode;
|
|
1977
|
+
rrfK?: number;
|
|
1978
|
+
bm25Weight?: number;
|
|
1979
|
+
semanticWeight?: number;
|
|
1980
|
+
fallbackToBm25?: boolean;
|
|
1981
|
+
onProgress?: (event: 'indexing' | 'indexed') => void;
|
|
1982
|
+
createStore?: (storePath: string) => unknown;
|
|
1983
|
+
}
|
|
1984
|
+
|
|
1985
|
+
export interface HybridSearchHit extends SearchHit {
|
|
1986
|
+
bm25Rank: number | null;
|
|
1987
|
+
semanticRank: number | null;
|
|
1988
|
+
bm25Score: number | null;
|
|
1989
|
+
semanticScore: number | null;
|
|
1990
|
+
}
|
|
1991
|
+
|
|
1992
|
+
export interface HybridSearchResult {
|
|
1993
|
+
query: string;
|
|
1994
|
+
mode: HybridSearchMode;
|
|
1995
|
+
effectiveMode: HybridSearchMode;
|
|
1996
|
+
semanticAvailable: boolean;
|
|
1997
|
+
indexed: boolean;
|
|
1998
|
+
root: string;
|
|
1999
|
+
files: number;
|
|
2000
|
+
chunks: number;
|
|
2001
|
+
tokens: number;
|
|
2002
|
+
warnings: string[];
|
|
2003
|
+
results: HybridSearchHit[];
|
|
2004
|
+
}
|
|
2005
|
+
|
|
2006
|
+
export function hybridSearch(
|
|
2007
|
+
root: string,
|
|
2008
|
+
query: string,
|
|
2009
|
+
options?: HybridSearchOptions
|
|
2010
|
+
): Promise<HybridSearchResult>;
|
|
2011
|
+
|
|
2012
|
+
// ============================================
|
|
2013
|
+
// Multi-Repository Workspace (`--repo`)
|
|
2014
|
+
// ============================================
|
|
2015
|
+
|
|
2016
|
+
export type WorkspaceRepoInput = string | { path: string; alias?: string };
|
|
2017
|
+
|
|
2018
|
+
export interface ResolvedWorkspaceRepo {
|
|
2019
|
+
alias: string;
|
|
2020
|
+
root: string;
|
|
2021
|
+
realRoot?: string;
|
|
2022
|
+
policy?: Policy;
|
|
2023
|
+
}
|
|
2024
|
+
|
|
2025
|
+
export function resolveWorkspaceRepos(repos: WorkspaceRepoInput[]): ResolvedWorkspaceRepo[];
|
|
2026
|
+
|
|
2027
|
+
export interface WorkspaceGraph extends RepoGraph {
|
|
2028
|
+
repos: Array<{ alias: string; root: string }>;
|
|
2029
|
+
}
|
|
2030
|
+
|
|
2031
|
+
export function buildWorkspaceGraph(
|
|
2032
|
+
repos: WorkspaceRepoInput[],
|
|
2033
|
+
options?: RepoGraphOptions & { callGraph?: boolean }
|
|
2034
|
+
): WorkspaceGraph;
|
|
2035
|
+
|
|
2036
|
+
export interface WorkspaceMapResult extends RepoMapResult {
|
|
2037
|
+
repos: Array<{ alias: string; root: string }>;
|
|
2038
|
+
}
|
|
2039
|
+
|
|
2040
|
+
export function mapWorkspace(
|
|
2041
|
+
repos: WorkspaceRepoInput[],
|
|
2042
|
+
options?: RepoMapOptions
|
|
2043
|
+
): WorkspaceMapResult;
|
|
2044
|
+
|
|
2045
|
+
export interface WorkspaceSearchHit extends SearchHit {
|
|
2046
|
+
repo: string;
|
|
2047
|
+
}
|
|
2048
|
+
|
|
2049
|
+
export interface WorkspaceSearchResult extends Omit<SearchProjectResult, 'results'> {
|
|
2050
|
+
repos: Array<{ alias: string; root: string }>;
|
|
2051
|
+
results: WorkspaceSearchHit[];
|
|
2052
|
+
}
|
|
2053
|
+
|
|
2054
|
+
export function searchWorkspace(
|
|
2055
|
+
repos: WorkspaceRepoInput[],
|
|
2056
|
+
query: string,
|
|
2057
|
+
options?: SearchProjectOptions
|
|
2058
|
+
): WorkspaceSearchResult;
|
|
2059
|
+
|
|
2060
|
+
export interface WorkspacePackResult extends PackResult {
|
|
2061
|
+
repos: Array<{ alias: string; root: string }>;
|
|
2062
|
+
}
|
|
2063
|
+
|
|
2064
|
+
export function packWorkspace(
|
|
2065
|
+
repos: WorkspaceRepoInput[],
|
|
2066
|
+
options?: Omit<PackOptions, 'files' | 'cwd'>
|
|
2067
|
+
): Promise<WorkspacePackResult>;
|
|
2068
|
+
|
|
2069
|
+
// ============================================
|
|
2070
|
+
// RAG Vector Stores & Embedding Providers (v3.2.0)
|
|
2071
|
+
// ============================================
|
|
2072
|
+
|
|
2073
|
+
export class LocalHashEmbeddingProvider {
|
|
2074
|
+
dimension: number;
|
|
2075
|
+
constructor(dimension?: number);
|
|
2076
|
+
embed(text: string): Promise<number[]>;
|
|
2077
|
+
}
|
|
2078
|
+
|
|
2079
|
+
export class AutoEmbeddingProvider {
|
|
2080
|
+
modelName?: string;
|
|
2081
|
+
constructor(options?: { modelName?: string });
|
|
2082
|
+
init(): Promise<void>;
|
|
2083
|
+
embed(text: string): Promise<number[]>;
|
|
2084
|
+
}
|
|
2085
|
+
|
|
2086
|
+
export class SqliteVectorStore {
|
|
2087
|
+
storagePath: string;
|
|
2088
|
+
dbPath: string;
|
|
2089
|
+
constructor(embeddingProvider: any, storagePath?: string);
|
|
2090
|
+
init(): Promise<void>;
|
|
2091
|
+
addDocument(
|
|
2092
|
+
text: string,
|
|
2093
|
+
metadata?: Record<string, any>
|
|
2094
|
+
): Promise<{ upserted: number; skipped: number }>;
|
|
2095
|
+
addDocuments(
|
|
2096
|
+
docs: Array<{ text: string; id?: string; metadata?: Record<string, any> }>
|
|
2097
|
+
): Promise<{ upserted: number; skipped: number }>;
|
|
2098
|
+
removeDocument(idOrFilePath: string): Promise<number>;
|
|
2099
|
+
upsertGraphNode(node: Record<string, any>): Promise<void>;
|
|
2100
|
+
replaceGraphEdges(
|
|
2101
|
+
fromPath: string,
|
|
2102
|
+
edges?: Array<{ to: string; weight?: number }>
|
|
2103
|
+
): Promise<void>;
|
|
2104
|
+
removeGraphNode(filePath: string): Promise<{ removedNode: number; removedEdges: number }>;
|
|
2105
|
+
syncGraph(graph: {
|
|
2106
|
+
nodes?: Array<Record<string, any>>;
|
|
2107
|
+
edges?: Array<{ from: string; to: string; weight?: number }>;
|
|
2108
|
+
replaceAll?: boolean;
|
|
2109
|
+
}): Promise<void>;
|
|
2110
|
+
getGraph(): Promise<{
|
|
2111
|
+
nodes: Array<Record<string, any>>;
|
|
2112
|
+
edges: Array<{ from: string; to: string; weight: number }>;
|
|
2113
|
+
}>;
|
|
2114
|
+
graphCounts(): { nodes: number; edges: number };
|
|
2115
|
+
search(
|
|
2116
|
+
queryText: string,
|
|
2117
|
+
limit?: number
|
|
2118
|
+
): Promise<Array<{ id?: string; text: string; score: number; metadata: Record<string, any> }>>;
|
|
2119
|
+
deleteTable(): Promise<void>;
|
|
2120
|
+
count(): number;
|
|
2121
|
+
close(): void;
|
|
2122
|
+
}
|
|
2123
|
+
|
|
2124
|
+
export interface FileWatcherOptions {
|
|
2125
|
+
debounce?: number;
|
|
2126
|
+
recursive?: boolean;
|
|
2127
|
+
ignorePatterns?: Array<string | RegExp>;
|
|
2128
|
+
repos?: string[];
|
|
2129
|
+
}
|
|
2130
|
+
|
|
2131
|
+
export class FileWatcher {
|
|
2132
|
+
rootPath: string;
|
|
2133
|
+
options: FileWatcherOptions;
|
|
2134
|
+
isWatching: boolean;
|
|
2135
|
+
isMultiRepo: boolean;
|
|
2136
|
+
repos: Array<{ root: string; alias: string | null }>;
|
|
2137
|
+
constructor(rootPath: string, options?: FileWatcherOptions);
|
|
2138
|
+
start(): void;
|
|
2139
|
+
stop(): void;
|
|
2140
|
+
shouldIgnore(relativePath: string, repoRoot?: string): boolean;
|
|
2141
|
+
getStats(): {
|
|
2142
|
+
totalChanges: number;
|
|
2143
|
+
ignoredChanges: number;
|
|
2144
|
+
errors: number;
|
|
2145
|
+
isWatching: boolean;
|
|
2146
|
+
activeWatchers: number;
|
|
2147
|
+
pendingDebounce: number;
|
|
2148
|
+
};
|
|
2149
|
+
resetStats(): void;
|
|
2150
|
+
on(event: string, listener: (...args: any[]) => void): this;
|
|
2151
|
+
}
|
|
2152
|
+
|
|
2153
|
+
export interface IncrementalAnalyzerOptions extends AnalyzerOptions {
|
|
2154
|
+
projectRoot?: string;
|
|
2155
|
+
repos?: string[];
|
|
2156
|
+
sync?: boolean;
|
|
2157
|
+
syncRag?: boolean;
|
|
2158
|
+
syncGraph?: boolean;
|
|
2159
|
+
storePath?: string;
|
|
2160
|
+
vectorStore?: SqliteVectorStore;
|
|
2161
|
+
embeddingProvider?: any;
|
|
2162
|
+
redactSecrets?: boolean;
|
|
2163
|
+
maxFileBytes?: number;
|
|
2164
|
+
hydrateGraphOnStart?: boolean;
|
|
2165
|
+
}
|
|
2166
|
+
|
|
2167
|
+
export class IncrementalAnalyzer {
|
|
2168
|
+
projectRoot: string | null;
|
|
2169
|
+
vectorStore: SqliteVectorStore | null;
|
|
2170
|
+
constructor(options?: IncrementalAnalyzerOptions);
|
|
2171
|
+
isMultiRepo: boolean;
|
|
2172
|
+
repos: Array<{ root: string; alias: string | null }>;
|
|
2173
|
+
isPathDenied(graphPath: string): boolean;
|
|
2174
|
+
ensureSyncReady(rootOverride?: string | null): Promise<boolean>;
|
|
2175
|
+
bootstrapSync(
|
|
2176
|
+
root?: string,
|
|
2177
|
+
options?: { repos?: string[] }
|
|
2178
|
+
): Promise<{
|
|
2179
|
+
files: number;
|
|
2180
|
+
ragUpserted: number;
|
|
2181
|
+
ragSkipped: number;
|
|
2182
|
+
graphNodes: number;
|
|
2183
|
+
graphEdges: number;
|
|
2184
|
+
repos?: string[];
|
|
2185
|
+
}>;
|
|
2186
|
+
syncFileChange(changeEvent: Record<string, any>): Promise<{
|
|
2187
|
+
rag: Record<string, any> | null;
|
|
2188
|
+
graph: Record<string, any> | null;
|
|
2189
|
+
}>;
|
|
2190
|
+
analyzeChange(changeEvent: Record<string, any>): Promise<void>;
|
|
2191
|
+
handleFileDeleted(changeEvent: Record<string, any>): Promise<void>;
|
|
2192
|
+
getGraph(): Promise<{
|
|
2193
|
+
nodes: Array<Record<string, any>>;
|
|
2194
|
+
edges: Array<{ from: string; to: string; weight: number }>;
|
|
2195
|
+
}>;
|
|
2196
|
+
getStats(): AnalyzerStats;
|
|
2197
|
+
getCachedAnalysis(filePath: string): AnalyzedFile | null;
|
|
2198
|
+
clearCache(): void;
|
|
2199
|
+
close(): void;
|
|
2200
|
+
getCacheStats(): {
|
|
2201
|
+
cachedFiles: number;
|
|
2202
|
+
cacheSize: number;
|
|
2203
|
+
graphNodes: number;
|
|
2204
|
+
graphEdges: number;
|
|
2205
|
+
vectorDocuments: number;
|
|
2206
|
+
};
|
|
2207
|
+
on(event: string, listener: (...args: any[]) => void): this;
|
|
2208
|
+
}
|
|
2209
|
+
|
|
2210
|
+
// ============================================
|
|
2211
|
+
// Task-Driven Auto Context (v3.2.0)
|
|
2212
|
+
// ============================================
|
|
2213
|
+
|
|
2214
|
+
export interface TaskContextOptions {
|
|
2215
|
+
budget?: number | string;
|
|
2216
|
+
format?: 'markdown' | 'json' | 'xml';
|
|
2217
|
+
searchMode?: 'hybrid' | 'bm25' | 'semantic';
|
|
2218
|
+
callGraph?: boolean;
|
|
2219
|
+
redact?: boolean;
|
|
2220
|
+
output?: string;
|
|
2221
|
+
model?: string;
|
|
2222
|
+
limit?: number;
|
|
2223
|
+
repos?: WorkspaceRepoInput[];
|
|
2224
|
+
}
|
|
2225
|
+
|
|
2226
|
+
export interface TaskContextResult {
|
|
2227
|
+
query: string;
|
|
2228
|
+
format: string;
|
|
2229
|
+
budget: number;
|
|
2230
|
+
totalTokens: number;
|
|
2231
|
+
text: string;
|
|
2232
|
+
seeds: Array<{ file: string; score: number; kind?: string; name?: string }>;
|
|
2233
|
+
files: Array<{ path: string; hop: number; compressed: boolean; tokens: number; lines: number }>;
|
|
2234
|
+
callEdges?: RepoGraphCallEdge[];
|
|
2235
|
+
omitted: Array<{ path: string; reason: string }>;
|
|
2236
|
+
redactions: { total: number };
|
|
2237
|
+
repos?: Array<{ alias: string; root: string }>;
|
|
2238
|
+
}
|
|
2239
|
+
|
|
2240
|
+
export function buildTaskContext(
|
|
2241
|
+
root: string,
|
|
2242
|
+
taskQuery: string,
|
|
2243
|
+
options?: TaskContextOptions
|
|
2244
|
+
): Promise<TaskContextResult>;
|
|
2245
|
+
|
|
2246
|
+
// ============================================
|
|
2247
|
+
// Failure Diagnosis (v3.2.0)
|
|
2248
|
+
// ============================================
|
|
2249
|
+
|
|
2250
|
+
export interface DiagnoseFailureOptions {
|
|
2251
|
+
budget?: number | string;
|
|
2252
|
+
format?: 'markdown' | 'json' | 'xml';
|
|
2253
|
+
callGraph?: boolean;
|
|
2254
|
+
redact?: boolean;
|
|
2255
|
+
windowLines?: number;
|
|
2256
|
+
output?: string;
|
|
2257
|
+
repos?: WorkspaceRepoInput[];
|
|
2258
|
+
}
|
|
2259
|
+
|
|
2260
|
+
export interface DiagnoseFailureResult {
|
|
2261
|
+
frames: Array<any>;
|
|
2262
|
+
implicatedFiles: string[];
|
|
2263
|
+
totalTokens: number;
|
|
2264
|
+
budget: number;
|
|
2265
|
+
text: string;
|
|
2266
|
+
history: Array<{ file: string; text: string; tokens: number }>;
|
|
2267
|
+
neighbors: string[];
|
|
2268
|
+
callEdges?: RepoGraphCallEdge[];
|
|
2269
|
+
redactions: { total: number };
|
|
2270
|
+
repos?: Array<{ alias: string; root: string }>;
|
|
2271
|
+
}
|
|
2272
|
+
|
|
2273
|
+
export function diagnoseFailure(
|
|
2274
|
+
root: string,
|
|
2275
|
+
traceOrLog: string,
|
|
2276
|
+
options?: DiagnoseFailureOptions
|
|
2277
|
+
): Promise<DiagnoseFailureResult>;
|
|
2278
|
+
|
|
2279
|
+
// ============================================
|
|
2280
|
+
// Institutional Memory Bridge (v3.2.0)
|
|
2281
|
+
// ============================================
|
|
2282
|
+
|
|
2283
|
+
export interface AnalyzerCitation {
|
|
2284
|
+
id: string;
|
|
2285
|
+
kind: string;
|
|
2286
|
+
title: string;
|
|
2287
|
+
snippet: string;
|
|
2288
|
+
url: string | null;
|
|
2289
|
+
author: string | null;
|
|
2290
|
+
timestamp: string | null;
|
|
2291
|
+
refs: string[];
|
|
2292
|
+
score: number;
|
|
2293
|
+
}
|
|
2294
|
+
|
|
2295
|
+
export interface QueryAnalyzerOptions {
|
|
2296
|
+
file?: string;
|
|
2297
|
+
symbol?: string;
|
|
2298
|
+
commits?: string[];
|
|
2299
|
+
limit?: number;
|
|
2300
|
+
redact?: boolean;
|
|
2301
|
+
}
|
|
2302
|
+
|
|
2303
|
+
export function queryAnalyzerCitations(
|
|
2304
|
+
rootOrDbPath: string,
|
|
2305
|
+
options?: QueryAnalyzerOptions
|
|
2306
|
+
): AnalyzerCitation[];
|
|
2307
|
+
|
|
2308
|
+
// ============================================
|
|
2309
|
+
// Expert Finder ("Who knows about this?")
|
|
2310
|
+
// ============================================
|
|
2311
|
+
|
|
2312
|
+
export class WhoError extends Error {
|
|
2313
|
+
constructor(message: string);
|
|
2314
|
+
}
|
|
2315
|
+
|
|
2316
|
+
export interface FindExpertsOptions {
|
|
2317
|
+
limit?: number;
|
|
2318
|
+
commitWindow?: number;
|
|
2319
|
+
halfLifeDays?: number;
|
|
2320
|
+
since?: string;
|
|
2321
|
+
style?: 'markdown' | 'xml' | 'json';
|
|
2322
|
+
nowMs?: number;
|
|
2323
|
+
repos?: WorkspaceRepoInput[];
|
|
2324
|
+
}
|
|
2325
|
+
|
|
2326
|
+
export interface ExpertEntry {
|
|
2327
|
+
name: string;
|
|
2328
|
+
email: string | null;
|
|
2329
|
+
score: number;
|
|
2330
|
+
blameLines: number;
|
|
2331
|
+
blameShare: number;
|
|
2332
|
+
commits: number;
|
|
2333
|
+
commitShare: number;
|
|
2334
|
+
recencyShare: number;
|
|
2335
|
+
additions: number;
|
|
2336
|
+
deletions: number;
|
|
2337
|
+
lastActive: string | null;
|
|
2338
|
+
isCodeOwner: boolean;
|
|
2339
|
+
codeOwnerHandles: string[];
|
|
2340
|
+
filesTouched: number;
|
|
2341
|
+
recentCommits: Array<{ sha: string; date: string | null; subject: string }>;
|
|
2342
|
+
}
|
|
2343
|
+
|
|
2344
|
+
export interface FindExpertsResult {
|
|
2345
|
+
repos?: Array<{ alias: string; root: string }>;
|
|
2346
|
+
data: {
|
|
2347
|
+
repos?: Array<{ alias: string; root: string }>;
|
|
2348
|
+
target: { query: string; mode: string; label: string; files: string[] };
|
|
2349
|
+
codeOwners: { file: string | null; owners: string[] };
|
|
2350
|
+
totalAuthors: number;
|
|
2351
|
+
experts: ExpertEntry[];
|
|
2352
|
+
};
|
|
2353
|
+
experts: ExpertEntry[];
|
|
2354
|
+
text: string;
|
|
2355
|
+
}
|
|
2356
|
+
|
|
2357
|
+
export function findExperts(
|
|
2358
|
+
projectDir: string,
|
|
2359
|
+
target: string,
|
|
2360
|
+
options?: FindExpertsOptions
|
|
2361
|
+
): Promise<FindExpertsResult>;
|