ultracode 5.4.0 → 5.6.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/dist/chunks/analysis-tool-handlers-GH5FDEWW.js +817 -0
- package/dist/chunks/analysis-tool-handlers-IXP4MWZX.js +817 -0
- package/dist/chunks/analysis-tool-handlers-LC2BTQYK.js +13 -0
- package/dist/chunks/analysis-tool-handlers-QYFKQPFL.js +817 -0
- package/dist/chunks/autodoc-tool-handlers-2HF6ERYN.js +1112 -0
- package/dist/chunks/autodoc-tool-handlers-4OGQJ7C3.js +1112 -0
- package/dist/chunks/autodoc-tool-handlers-N736CB56.js +138 -0
- package/dist/chunks/autodoc-tool-handlers-NQYBY6U4.js +1112 -0
- package/dist/chunks/branch-tool-handlers-KW3H4FJK.js +276 -0
- package/dist/chunks/branch-tool-handlers-QOUDZKJ2.js +276 -0
- package/dist/chunks/branch-tool-handlers-RB2U36KI.js +2 -0
- package/dist/chunks/branch-tool-handlers-ZHJM6PDK.js +276 -0
- package/dist/chunks/chunk-2Z6OQPYC.js +656 -0
- package/dist/chunks/chunk-3MQ7LRPN.js +322 -0
- package/dist/chunks/chunk-4W6QYGXZ.js +10 -0
- package/dist/chunks/chunk-533NFGUG.js +1 -0
- package/dist/chunks/chunk-5NUPOPWM.js +1 -0
- package/dist/chunks/chunk-AK4HIPA2.js +322 -0
- package/dist/chunks/chunk-B3H5NS3I.js +656 -0
- package/dist/chunks/chunk-DPTZHDST.js +4 -0
- package/dist/chunks/chunk-E5HQWLU5.js +322 -0
- package/dist/chunks/chunk-EOH25B5P.js +572 -0
- package/dist/chunks/chunk-ESV6F6E3.js +3179 -0
- package/dist/chunks/chunk-FPELPFER.js +924 -0
- package/dist/chunks/chunk-G6J42I55.js +161 -0
- package/dist/chunks/chunk-GCQE7ZYW.js +1 -0
- package/dist/chunks/chunk-GTIF6MOX.js +1 -0
- package/dist/chunks/chunk-I6STSSAK.js +2 -0
- package/dist/chunks/chunk-J2WBGTK2.js +4697 -0
- package/dist/chunks/chunk-KAYOX5EB.js +4697 -0
- package/dist/chunks/chunk-KPMTACOT.js +656 -0
- package/dist/chunks/chunk-L376GZ44.js +3179 -0
- package/dist/chunks/chunk-LCTOTHDA.js +15 -0
- package/dist/chunks/chunk-LEDJ7GVQ.js +316 -0
- package/dist/chunks/chunk-LH4OUKNZ.js +277 -0
- package/dist/chunks/chunk-O6IE2MEZ.js +161 -0
- package/dist/chunks/chunk-OEXPCY3F.js +316 -0
- package/dist/chunks/chunk-OMXOLFDN.js +924 -0
- package/dist/chunks/chunk-PLPBXWOU.js +3179 -0
- package/dist/chunks/chunk-PWLE5DN2.js +572 -0
- package/dist/chunks/chunk-PY43JPWL.js +447 -0
- package/dist/chunks/chunk-Q3B4EB7A.js +15 -0
- package/dist/chunks/chunk-Q5LPVLXA.js +337 -0
- package/dist/chunks/chunk-QIRZHZK2.js +5 -0
- package/dist/chunks/chunk-ROQ27LSL.js +924 -0
- package/dist/chunks/chunk-S5Q7BD6J.js +572 -0
- package/dist/chunks/chunk-SAMX3HJQ.js +337 -0
- package/dist/chunks/chunk-SV3WKUNV.js +1 -0
- package/dist/chunks/chunk-TCHCDCDO.js +167 -0
- package/dist/chunks/chunk-TR3HS7U6.js +316 -0
- package/dist/chunks/chunk-TUWE6FCW.js +167 -0
- package/dist/chunks/chunk-TVOTA7EE.js +277 -0
- package/dist/chunks/chunk-VS44D772.js +337 -0
- package/dist/chunks/chunk-WIE3G5ES.js +167 -0
- package/dist/chunks/chunk-XG3ACLWR.js +5 -0
- package/dist/chunks/chunk-XJ2Z5QQO.js +1 -0
- package/dist/chunks/chunk-XK2NY7RB.js +277 -0
- package/dist/chunks/chunk-Y4F7NZFZ.js +4700 -0
- package/dist/chunks/chunk-YS75L3ZS.js +161 -0
- package/dist/chunks/chunk-ZVG5HHI3.js +15 -0
- package/dist/chunks/dev-agent-DDDIVWOF.js +1 -0
- package/dist/chunks/dev-agent-E2VCFKXN.js +1624 -0
- package/dist/chunks/dev-agent-KJNSU5KQ.js +1624 -0
- package/dist/chunks/dev-agent-NDERYIPV.js +1624 -0
- package/dist/chunks/faiss-provider-7R4BQDIV.js +12 -0
- package/dist/chunks/faiss-provider-7ZFRSDN5.js +12 -0
- package/dist/chunks/faiss-provider-SXB7FTLB.js +1 -0
- package/dist/chunks/faiss-provider-TKLBEUSH.js +12 -0
- package/dist/chunks/file-tool-handlers-5DODQXGF.js +1027 -0
- package/dist/chunks/file-tool-handlers-KGHLE4KR.js +1027 -0
- package/dist/chunks/file-tool-handlers-KTOQ4NFS.js +12 -0
- package/dist/chunks/file-tool-handlers-V4SFUDQB.js +1027 -0
- package/dist/chunks/graph-metrics-tool-handlers-3AV4X4ZY.js +65 -0
- package/dist/chunks/graph-metrics-tool-handlers-3VMDQHJ6.js +65 -0
- package/dist/chunks/graph-metrics-tool-handlers-BZ6E6YHF.js +1 -0
- package/dist/chunks/graph-metrics-tool-handlers-IYBGSXL7.js +65 -0
- package/dist/chunks/graph-storage-factory-2CQ2RPDV.js +13 -0
- package/dist/chunks/graph-storage-factory-C5SMMYL6.js +13 -0
- package/dist/chunks/graph-storage-factory-EEO2V3GJ.js +1 -0
- package/dist/chunks/graph-storage-factory-WBCTXP34.js +13 -0
- package/dist/chunks/history-tool-handlers-AS7OQFZI.js +1 -0
- package/dist/chunks/history-tool-handlers-FSNJYXV2.js +208 -0
- package/dist/chunks/history-tool-handlers-JZAH4EIQ.js +208 -0
- package/dist/chunks/history-tool-handlers-KCSCXZ7T.js +208 -0
- package/dist/chunks/incremental-updater-A2EL4QXU.js +14 -0
- package/dist/chunks/incremental-updater-EQIKBVY2.js +14 -0
- package/dist/chunks/incremental-updater-JFGRPH3B.js +14 -0
- package/dist/chunks/incremental-updater-S5BAAGHP.js +1 -0
- package/dist/chunks/indexer-agent-ASKY7JPG.js +1 -0
- package/dist/chunks/indexer-agent-NKAOF323.js +21 -0
- package/dist/chunks/indexer-agent-PJN5IOKQ.js +21 -0
- package/dist/chunks/indexer-agent-WRJFWKZX.js +21 -0
- package/dist/chunks/indexing-pipeline-D4P2O72Z.js +249 -0
- package/dist/chunks/indexing-pipeline-L7C543N4.js +1 -0
- package/dist/chunks/indexing-pipeline-NHPRN3AB.js +249 -0
- package/dist/chunks/indexing-pipeline-ZAXCZU22.js +249 -0
- package/dist/chunks/layered-faiss-provider-62CNW54X.js +1 -0
- package/dist/chunks/layered-faiss-provider-O7L77GFX.js +12 -0
- package/dist/chunks/layered-faiss-provider-RVHLHLPK.js +12 -0
- package/dist/chunks/layered-faiss-provider-YT7EDIJI.js +12 -0
- package/dist/chunks/merge-agent-3RF7VFF5.js +2481 -0
- package/dist/chunks/merge-agent-JCKTCBCE.js +2481 -0
- package/dist/chunks/merge-agent-VCL7OXPN.js +2481 -0
- package/dist/chunks/merge-agent-ZGK24WVF.js +11 -0
- package/dist/chunks/merge-tool-handlers-GV2LOIKU.js +277 -0
- package/dist/chunks/merge-tool-handlers-TYDWU5X2.js +277 -0
- package/dist/chunks/merge-tool-handlers-U7X2ZO2M.js +1 -0
- package/dist/chunks/merge-tool-handlers-YH62ZLPJ.js +277 -0
- package/dist/chunks/pattern-tool-handlers-76NF5JDS.js +13 -0
- package/dist/chunks/pattern-tool-handlers-IJAGEIVD.js +1549 -0
- package/dist/chunks/pattern-tool-handlers-VA5WYA62.js +1549 -0
- package/dist/chunks/pattern-tool-handlers-WQ6UBMJS.js +1549 -0
- package/dist/chunks/query-agent-36ADGCFZ.js +1 -0
- package/dist/chunks/query-agent-H22CR5N5.js +191 -0
- package/dist/chunks/query-agent-K2UGZS4M.js +191 -0
- package/dist/chunks/query-agent-YJCEHOXD.js +191 -0
- package/dist/chunks/semantic-agent-AC7CBEDE.js +6381 -0
- package/dist/chunks/semantic-agent-HK5X6CKU.js +6381 -0
- package/dist/chunks/semantic-agent-KONIKEGW.js +6381 -0
- package/dist/chunks/semantic-agent-LH6IZ2L7.js +137 -0
- package/dist/chunks/semantic-tool-handlers-5LMSH2U7.js +3 -0
- package/dist/chunks/semantic-tool-handlers-735UMO7Y.js +817 -0
- package/dist/chunks/semantic-tool-handlers-BNUYPP7X.js +817 -0
- package/dist/chunks/semantic-tool-handlers-MYZPEUD2.js +817 -0
- package/dist/chunks/snapshot-tool-handlers-6SIHZT2F.js +201 -0
- package/dist/chunks/snapshot-tool-handlers-DS4P3KOT.js +201 -0
- package/dist/chunks/snapshot-tool-handlers-JYHRFPC7.js +201 -0
- package/dist/chunks/snapshot-tool-handlers-YEHMAT3L.js +1 -0
- package/dist/chunks/storage-paths-A3C7WHHG.js +8 -0
- package/dist/chunks/storage-paths-HDYH7WPM.js +1 -0
- package/dist/chunks/storage-paths-IMFRHBWF.js +8 -0
- package/dist/chunks/storage-paths-P3PUSMUD.js +8 -0
- package/dist/chunks/taint-tool-handlers-CWESOOMQ.js +68 -0
- package/dist/chunks/taint-tool-handlers-OG3NVVP3.js +1 -0
- package/dist/chunks/taint-tool-handlers-ON3G3FA7.js +68 -0
- package/dist/chunks/taint-tool-handlers-P4P5J6DB.js +68 -0
- package/dist/chunks/tracing-tool-handlers-4BDCXTZZ.js +3935 -0
- package/dist/chunks/tracing-tool-handlers-6FPNM7HX.js +3935 -0
- package/dist/chunks/tracing-tool-handlers-LQTQ5SKK.js +89 -0
- package/dist/chunks/tracing-tool-handlers-XRQX2DTS.js +3935 -0
- package/dist/chunks/validation-tool-handlers-DZUG7KYY.js +2 -0
- package/dist/chunks/validation-tool-handlers-O6TGFSH5.js +555 -0
- package/dist/chunks/validation-tool-handlers-RREUYKIR.js +555 -0
- package/dist/chunks/validation-tool-handlers-XPWSMS37.js +555 -0
- package/dist/index.js +13 -13
- package/dist/roslyn-addon/.build-hash +1 -1
- package/dist/roslyn-addon/ILGPU.Algorithms.dll +0 -0
- package/dist/roslyn-addon/ILGPU.dll +0 -0
- package/dist/roslyn-addon/UltraCode.CSharp.deps.json +35 -0
- package/dist/roslyn-addon/UltraCode.CSharp.dll +0 -0
- package/package.json +1 -1
|
@@ -0,0 +1,337 @@
|
|
|
1
|
+
import { getProjectContext } from './chunk-WIE3G5ES.js';
|
|
2
|
+
import { init_logging, log } from './chunk-VCCBEJQ5.js';
|
|
3
|
+
|
|
4
|
+
// src/tools/response-limits.ts
|
|
5
|
+
var MAX_RESPONSE_SIZE_BYTES = 5e4;
|
|
6
|
+
var DEFAULT_PAGE_SIZE = 50;
|
|
7
|
+
var MAX_PAGE_SIZE = 200;
|
|
8
|
+
var SAFE_LIMITS = {
|
|
9
|
+
entities: 100,
|
|
10
|
+
relationships: 100,
|
|
11
|
+
clones: 30,
|
|
12
|
+
searchResults: 20,
|
|
13
|
+
hotspots: 20,
|
|
14
|
+
graphNodes: 200,
|
|
15
|
+
taintVulnerabilities: 20
|
|
16
|
+
};
|
|
17
|
+
function paginate(items, offset = 0, limit = DEFAULT_PAGE_SIZE) {
|
|
18
|
+
const safeLimit = Math.min(limit, MAX_PAGE_SIZE);
|
|
19
|
+
const safeOffset = Math.max(0, offset);
|
|
20
|
+
const total = items.length;
|
|
21
|
+
const data = items.slice(safeOffset, safeOffset + safeLimit);
|
|
22
|
+
const hasMore = safeOffset + safeLimit < total;
|
|
23
|
+
return {
|
|
24
|
+
data,
|
|
25
|
+
pagination: {
|
|
26
|
+
offset: safeOffset,
|
|
27
|
+
limit: safeLimit,
|
|
28
|
+
total,
|
|
29
|
+
hasMore,
|
|
30
|
+
...hasMore && { nextOffset: safeOffset + safeLimit }
|
|
31
|
+
}
|
|
32
|
+
};
|
|
33
|
+
}
|
|
34
|
+
function truncateResponse(data, maxSize = MAX_RESPONSE_SIZE_BYTES) {
|
|
35
|
+
const jsonText = JSON.stringify(data, null, 2);
|
|
36
|
+
const originalSize = Buffer.byteLength(jsonText, "utf8");
|
|
37
|
+
if (originalSize <= maxSize) {
|
|
38
|
+
return {
|
|
39
|
+
text: jsonText,
|
|
40
|
+
wasTruncated: false,
|
|
41
|
+
originalSize,
|
|
42
|
+
truncatedSize: originalSize
|
|
43
|
+
};
|
|
44
|
+
}
|
|
45
|
+
const truncatedData = truncateData(data, maxSize);
|
|
46
|
+
const truncatedJson = JSON.stringify(truncatedData, null, 2);
|
|
47
|
+
return {
|
|
48
|
+
text: truncatedJson,
|
|
49
|
+
wasTruncated: true,
|
|
50
|
+
originalSize,
|
|
51
|
+
truncatedSize: Buffer.byteLength(truncatedJson, "utf8")
|
|
52
|
+
};
|
|
53
|
+
}
|
|
54
|
+
function truncateData(data, maxSize, depth = 0) {
|
|
55
|
+
if (depth > 5) return "[nested data omitted]";
|
|
56
|
+
if (data === null || data === void 0) return data;
|
|
57
|
+
if (typeof data !== "object") return data;
|
|
58
|
+
if (Array.isArray(data)) {
|
|
59
|
+
return truncateArray(data, maxSize);
|
|
60
|
+
}
|
|
61
|
+
return truncateObject(data, maxSize, depth);
|
|
62
|
+
}
|
|
63
|
+
function truncateArray(arr, maxSize) {
|
|
64
|
+
let items = arr;
|
|
65
|
+
let estimatedSize = JSON.stringify(items).length;
|
|
66
|
+
while (estimatedSize > maxSize * 0.8 && items.length > 1) {
|
|
67
|
+
const newLength = Math.max(1, Math.floor(items.length / 2));
|
|
68
|
+
items = arr.slice(0, newLength);
|
|
69
|
+
estimatedSize = JSON.stringify(items).length;
|
|
70
|
+
}
|
|
71
|
+
const truncated = items.length < arr.length;
|
|
72
|
+
if (truncated) {
|
|
73
|
+
return {
|
|
74
|
+
_truncated: true,
|
|
75
|
+
_message: `Response truncated. Showing ${items.length} of ${arr.length} items. Use 'offset' parameter to paginate.`,
|
|
76
|
+
_total: arr.length,
|
|
77
|
+
_showing: items.length,
|
|
78
|
+
items
|
|
79
|
+
};
|
|
80
|
+
}
|
|
81
|
+
return items;
|
|
82
|
+
}
|
|
83
|
+
function truncateObject(obj, maxSize, depth = 0) {
|
|
84
|
+
const result = {};
|
|
85
|
+
const priorityFields = ["id", "name", "type", "count", "total", "pagination", "error", "success"];
|
|
86
|
+
const arrayFields = [];
|
|
87
|
+
for (const key of Object.keys(obj)) {
|
|
88
|
+
if (priorityFields.includes(key)) {
|
|
89
|
+
result[key] = obj[key];
|
|
90
|
+
} else if (Array.isArray(obj[key])) {
|
|
91
|
+
arrayFields.push(key);
|
|
92
|
+
}
|
|
93
|
+
}
|
|
94
|
+
for (const key of Object.keys(obj)) {
|
|
95
|
+
if (!priorityFields.includes(key) && !Array.isArray(obj[key])) {
|
|
96
|
+
const value = obj[key];
|
|
97
|
+
if (typeof value === "string" && value.length > maxSize * 0.2) {
|
|
98
|
+
result[key] = value.slice(0, Math.floor(maxSize * 0.2)) + "... [truncated]";
|
|
99
|
+
} else if (typeof value === "object" && value !== null) {
|
|
100
|
+
const remainingSize = maxSize - JSON.stringify(result).length;
|
|
101
|
+
if (remainingSize > 100) {
|
|
102
|
+
result[key] = truncateData(value, remainingSize * 0.8, depth + 1);
|
|
103
|
+
} else {
|
|
104
|
+
result[key] = "[object omitted \u2014 response too large]";
|
|
105
|
+
}
|
|
106
|
+
} else {
|
|
107
|
+
result[key] = value;
|
|
108
|
+
}
|
|
109
|
+
}
|
|
110
|
+
}
|
|
111
|
+
for (const key of arrayFields) {
|
|
112
|
+
const arr = obj[key];
|
|
113
|
+
const remainingSize = maxSize - JSON.stringify(result).length;
|
|
114
|
+
result[key] = truncateArray(arr, remainingSize * 0.8);
|
|
115
|
+
}
|
|
116
|
+
return result;
|
|
117
|
+
}
|
|
118
|
+
|
|
119
|
+
// src/tools/base-tool-handler.ts
|
|
120
|
+
init_logging();
|
|
121
|
+
var BaseToolHandler = class {
|
|
122
|
+
constructor(context) {
|
|
123
|
+
this.context = context;
|
|
124
|
+
}
|
|
125
|
+
/** Maximum response size in bytes. Override in subclass if needed. */
|
|
126
|
+
maxResponseSize = MAX_RESPONSE_SIZE_BYTES;
|
|
127
|
+
// ==========================================================================
|
|
128
|
+
// PROJECT CONTEXT HELPERS (v5: session-aware)
|
|
129
|
+
// ==========================================================================
|
|
130
|
+
/**
|
|
131
|
+
* Get the ProjectContextManager singleton.
|
|
132
|
+
* @deprecated Use context.session or context.projectPath instead for isolation.
|
|
133
|
+
*/
|
|
134
|
+
getProjectContext() {
|
|
135
|
+
return getProjectContext();
|
|
136
|
+
}
|
|
137
|
+
/**
|
|
138
|
+
* v5: Resolve project path using session-aware logic.
|
|
139
|
+
*
|
|
140
|
+
* Priority:
|
|
141
|
+
* 1. Explicit path from args (if provided)
|
|
142
|
+
* 2. context.projectPath (set from session or startup)
|
|
143
|
+
* 3. Fallback to global singleton (legacy mode)
|
|
144
|
+
*/
|
|
145
|
+
resolveProjectPath(args) {
|
|
146
|
+
if (args.projectPath) {
|
|
147
|
+
return this.context.session?.resolvePath(args.projectPath) ?? args.projectPath;
|
|
148
|
+
}
|
|
149
|
+
if (args.directory) {
|
|
150
|
+
return this.context.session?.resolvePath(args.directory) ?? args.directory;
|
|
151
|
+
}
|
|
152
|
+
if (this.context.session) {
|
|
153
|
+
return this.context.session.projectPath;
|
|
154
|
+
}
|
|
155
|
+
if (this.context.projectPath) {
|
|
156
|
+
return this.context.projectPath;
|
|
157
|
+
}
|
|
158
|
+
const current = getProjectContext().getCurrentProject();
|
|
159
|
+
if (current) {
|
|
160
|
+
return current;
|
|
161
|
+
}
|
|
162
|
+
return process.cwd();
|
|
163
|
+
}
|
|
164
|
+
/**
|
|
165
|
+
* Get storage paths for a project
|
|
166
|
+
*/
|
|
167
|
+
getProjectStoragePaths(projectPath) {
|
|
168
|
+
const resolved = this.resolveProjectPath({ projectPath });
|
|
169
|
+
return getProjectContext().getStoragePaths(resolved);
|
|
170
|
+
}
|
|
171
|
+
/**
|
|
172
|
+
* Check if project is indexed
|
|
173
|
+
*/
|
|
174
|
+
isProjectIndexed(projectPath) {
|
|
175
|
+
const resolved = this.resolveProjectPath({ projectPath });
|
|
176
|
+
return getProjectContext().isProjectIndexed(resolved);
|
|
177
|
+
}
|
|
178
|
+
/**
|
|
179
|
+
* v5: Get GraphStorage with project context automatically set.
|
|
180
|
+
* Uses session-aware project resolution.
|
|
181
|
+
*/
|
|
182
|
+
async ensureGraphStorageForProject(projectPath) {
|
|
183
|
+
const resolved = this.resolveProjectPath({ projectPath });
|
|
184
|
+
log.d("BASETOOL", "ensure_storage", { resolved, hasSession: !!this.context.session });
|
|
185
|
+
const storage = await this.context.getGraphStorage();
|
|
186
|
+
storage.setProject(resolved);
|
|
187
|
+
log.d("BASETOOL", "storage_set", { resolved });
|
|
188
|
+
return storage;
|
|
189
|
+
}
|
|
190
|
+
/**
|
|
191
|
+
* v5: Ensure SemanticAgent is initialized for the correct project.
|
|
192
|
+
* Uses session-aware project resolution.
|
|
193
|
+
*/
|
|
194
|
+
async ensureSemanticAgentForProject(projectPath) {
|
|
195
|
+
const resolved = this.resolveProjectPath({ projectPath });
|
|
196
|
+
const semanticAgent = await this.context.getSemanticAgent();
|
|
197
|
+
const vectorStore = semanticAgent?.getVectorStore?.();
|
|
198
|
+
const currentContext = vectorStore?.getProjectContext?.();
|
|
199
|
+
log.d("BASETOOL", "semantic_ctx", {
|
|
200
|
+
resolved,
|
|
201
|
+
hasSession: !!this.context.session,
|
|
202
|
+
ctx: JSON.stringify(currentContext)
|
|
203
|
+
});
|
|
204
|
+
if (semanticAgent && typeof semanticAgent.reinitializeForProject === "function") {
|
|
205
|
+
log.d("BASETOOL", "reinit_proj", { resolved });
|
|
206
|
+
await semanticAgent.reinitializeForProject(resolved);
|
|
207
|
+
const newContext = semanticAgent.getVectorStore?.()?.getProjectContext?.();
|
|
208
|
+
log.d("BASETOOL", "ctx_switched", { ctx: JSON.stringify(newContext) });
|
|
209
|
+
}
|
|
210
|
+
return semanticAgent;
|
|
211
|
+
}
|
|
212
|
+
/**
|
|
213
|
+
* Apply response size limits and truncation if needed
|
|
214
|
+
*/
|
|
215
|
+
applyResponseLimits(result) {
|
|
216
|
+
if (!result.content || result.content.length === 0) {
|
|
217
|
+
return result;
|
|
218
|
+
}
|
|
219
|
+
const newContent = result.content.map((item) => {
|
|
220
|
+
if (item.type !== "text") return item;
|
|
221
|
+
const size = Buffer.byteLength(item.text, "utf8");
|
|
222
|
+
if (size <= this.maxResponseSize) {
|
|
223
|
+
return item;
|
|
224
|
+
}
|
|
225
|
+
let newItem;
|
|
226
|
+
try {
|
|
227
|
+
const data = JSON.parse(item.text);
|
|
228
|
+
const truncated = truncateResponse(data, this.maxResponseSize);
|
|
229
|
+
if (truncated.wasTruncated) {
|
|
230
|
+
const parsed = JSON.parse(truncated.text);
|
|
231
|
+
parsed._responseMeta = {
|
|
232
|
+
truncated: true,
|
|
233
|
+
originalSizeBytes: truncated.originalSize,
|
|
234
|
+
truncatedSizeBytes: truncated.truncatedSize,
|
|
235
|
+
hint: "Response was truncated. Use 'offset' and 'limit' parameters for pagination."
|
|
236
|
+
};
|
|
237
|
+
newItem = {
|
|
238
|
+
type: "text",
|
|
239
|
+
text: JSON.stringify(parsed, null, 2)
|
|
240
|
+
};
|
|
241
|
+
} else {
|
|
242
|
+
newItem = { type: "text", text: truncated.text };
|
|
243
|
+
}
|
|
244
|
+
} catch {
|
|
245
|
+
const truncatedText = item.text.slice(0, this.maxResponseSize);
|
|
246
|
+
newItem = {
|
|
247
|
+
type: "text",
|
|
248
|
+
text: truncatedText + "\n\n[RESPONSE TRUNCATED - original size: " + size + " bytes]"
|
|
249
|
+
};
|
|
250
|
+
}
|
|
251
|
+
const finalSize = Buffer.byteLength(newItem.text, "utf8");
|
|
252
|
+
if (finalSize > this.maxResponseSize) {
|
|
253
|
+
const sliced = newItem.text.slice(0, this.maxResponseSize - 200);
|
|
254
|
+
return {
|
|
255
|
+
type: "text",
|
|
256
|
+
text: sliced + "\n\n[RESPONSE TRUNCATED \u2014 hard cap at " + this.maxResponseSize + " bytes. Original: " + finalSize + " bytes. Use 'offset'/'limit' for pagination.]"
|
|
257
|
+
};
|
|
258
|
+
}
|
|
259
|
+
return newItem;
|
|
260
|
+
});
|
|
261
|
+
return { content: newContent };
|
|
262
|
+
}
|
|
263
|
+
/**
|
|
264
|
+
* Summarize tool args for logging (truncate large values)
|
|
265
|
+
*/
|
|
266
|
+
summarizeArgs(args) {
|
|
267
|
+
if (!args || typeof args !== "object") return {};
|
|
268
|
+
const summary = {};
|
|
269
|
+
for (const [key, value] of Object.entries(args)) {
|
|
270
|
+
if (value === void 0 || value === null) continue;
|
|
271
|
+
if (typeof value === "string") {
|
|
272
|
+
summary[key] = value.length > 80 ? value.slice(0, 80) + "..." : value;
|
|
273
|
+
} else if (Array.isArray(value)) {
|
|
274
|
+
summary[key] = `[${value.length}]`;
|
|
275
|
+
} else {
|
|
276
|
+
summary[key] = value;
|
|
277
|
+
}
|
|
278
|
+
}
|
|
279
|
+
return summary;
|
|
280
|
+
}
|
|
281
|
+
/**
|
|
282
|
+
* Calculate response size in bytes
|
|
283
|
+
*/
|
|
284
|
+
responseSize(result) {
|
|
285
|
+
let size = 0;
|
|
286
|
+
for (const item of result.content) {
|
|
287
|
+
size += item.text.length;
|
|
288
|
+
}
|
|
289
|
+
return size;
|
|
290
|
+
}
|
|
291
|
+
/**
|
|
292
|
+
* Main entry point for tool execution
|
|
293
|
+
*/
|
|
294
|
+
async handle(args) {
|
|
295
|
+
const startTime = Date.now();
|
|
296
|
+
const toolName = this.constructor.name.replace("ToolHandler", "").toLowerCase();
|
|
297
|
+
try {
|
|
298
|
+
const parsedArgs = this.parseArgs(args);
|
|
299
|
+
const result = await this.execute(parsedArgs);
|
|
300
|
+
const limitedResult = this.applyResponseLimits(result);
|
|
301
|
+
const duration = Date.now() - startTime;
|
|
302
|
+
const respSize = this.responseSize(limitedResult);
|
|
303
|
+
log.i("BASETOOL", "mcp_response", {
|
|
304
|
+
tool: toolName,
|
|
305
|
+
durationMs: duration,
|
|
306
|
+
respBytes: respSize,
|
|
307
|
+
args: this.summarizeArgs(args),
|
|
308
|
+
reqId: this.context.requestId
|
|
309
|
+
});
|
|
310
|
+
return limitedResult;
|
|
311
|
+
} catch (error) {
|
|
312
|
+
const duration = Date.now() - startTime;
|
|
313
|
+
log.e("BASETOOL", "exec_failed", {
|
|
314
|
+
tool: toolName,
|
|
315
|
+
durationMs: duration,
|
|
316
|
+
err: error.message,
|
|
317
|
+
args: this.summarizeArgs(args),
|
|
318
|
+
reqId: this.context.requestId
|
|
319
|
+
});
|
|
320
|
+
return {
|
|
321
|
+
content: [
|
|
322
|
+
{
|
|
323
|
+
type: "text",
|
|
324
|
+
text: JSON.stringify({
|
|
325
|
+
success: false,
|
|
326
|
+
error: error.message
|
|
327
|
+
})
|
|
328
|
+
}
|
|
329
|
+
]
|
|
330
|
+
};
|
|
331
|
+
}
|
|
332
|
+
}
|
|
333
|
+
};
|
|
334
|
+
|
|
335
|
+
export { BaseToolHandler, DEFAULT_PAGE_SIZE, MAX_PAGE_SIZE, MAX_RESPONSE_SIZE_BYTES, SAFE_LIMITS, paginate, truncateResponse };
|
|
336
|
+
//# sourceMappingURL=chunk-SAMX3HJQ.js.map
|
|
337
|
+
//# sourceMappingURL=chunk-SAMX3HJQ.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
import {b,c}from'./chunk-PZF7YC35.js';import {d,b as b$1}from'./chunk-DXB73IDG.js';import {execSync}from'child_process';import {existsSync,mkdirSync}from'fs';import {homedir}from'os';import {join}from'path';var K={};d(K,{DEFAULT_BRANCH:()=>C,ensureDataDir:()=>H,ensureGlobalDbDir:()=>N,ensureProjectDir:()=>I,getASTCacheDir:()=>X,getBranchPaths:()=>z,getCacheDir:()=>p,getConfigDir:()=>l,getConfigPath:()=>y,getCoreLockPath:()=>k,getCorePidPath:()=>L,getCurrentGitBranch:()=>A,getCurrentGitBranchOrDefault:()=>G,getDataDir:()=>i,getFaissHotBufferPath:()=>U,getFaissIdMapPath:()=>R,getFaissIndexPath:()=>M,getFaissIndexPathByHash:()=>O,getGlobalDbPaths:()=>v,getIPCSocketPath:()=>S,getLogsDir:()=>x,getModelsDir:()=>P,getMultiDbPaths:()=>T,getProjectDir:()=>u,getProjectHash:()=>_,getProjectPaths:()=>m,getProjectsDir:()=>a,getSemanticConfigPath:()=>E,getTreeSitterCacheDir:()=>J,hashProjectPath:()=>D,initializeStorageDirs:()=>q,isBaseBranch:()=>F,normalizeBranchName:()=>g});function i(){let r;switch(process.platform){case "win32":r=process.env.LOCALAPPDATA||join(homedir(),"AppData","Local");break;case "darwin":r=join(homedir(),"Library","Application Support");break;default:r=process.env.XDG_DATA_HOME||join(homedir(),".local","share");}return join(r,"UltraCode")}function H(){let r=i();return existsSync(r)||mkdirSync(r,{recursive:true}),r}function S(){return process.platform==="win32"?"\\\\.\\pipe\\ultracode-core":"/tmp/ultracode-core.sock"}function x(){return join(i(),"logs")}function p(){return join(i(),"cache")}function a(){return join(i(),"projects")}function P(){return join(i(),"models")}function l(){return join(i(),"config")}function y(){return join(i(),"config.yaml")}function E(){return join(l(),"semantic-config.json")}function L(){return join(i(),"core.pid")}function k(){return join(i(),"core.lock")}function D(r){if(!r)throw new Error(`hashProjectPath: projectPath must not be empty (got ${JSON.stringify(r)}). Ensure projectPath is provided in tool args or resolved from session/context.`);let t=r.toLowerCase().replace(/\\/g,"/").replace(/\/$/,"");return b(t)}function u(r){let t=D(r);return join(a(),t)}function m(r){let t=u(r);return {dir:t,metaPath:join(t,"meta.json"),graphDbPath:join(t,"graph.db"),vectorsDbPath:join(t,"vectors.db"),branchesDir:join(t,"branches"),parserCachePath:join(t,"parser-cache.json"),semanticCachePath:join(t,"semantic-cache.json")}}function v(){let r=i();return {dir:r,graphDbPath:join(r,"graph.db"),vectorsDbPath:join(r,"graph.db"),unifiedDbPath:join(r,"graph.db"),metaPath:join(r,"global-meta.json"),cacheDir:p(),projectsDir:a()}}function T(r){let t=r??i();return {graph:join(t,"graph.db"),semantic:join(t,"semantic.db"),versioning:join(t,"versioning.db"),cache:join(t,"cache.db")}}function _(r){return D(r)}function g(r){return r.toLowerCase().replace(/[<>:"/\\|?*]/g,"_")}function F(r){if(!r)return false;let t=r.toLowerCase();return $.includes(t)}function A(r){if(!r)return null;try{let t=join(r,".git");return existsSync(t)&&execSync("git symbolic-ref --short HEAD",{cwd:r,encoding:"utf-8",stdio:["pipe","pipe","ignore"],windowsHide:!0}).trim()||null}catch{try{let t=execSync("git rev-parse --abbrev-ref HEAD",{cwd:r,encoding:"utf-8",stdio:["pipe","pipe","ignore"],windowsHide:!0}).trim();if(t==="HEAD"){let n=execSync("git rev-parse --short HEAD",{cwd:r,encoding:"utf-8",stdio:["pipe","pipe","ignore"],windowsHide:!0}).trim();return n?`detached-${n}`:null}return t||null}catch{return null}}}function G(r){return A(r)||C}function I(r){let t=m(r);return existsSync(t.dir)||mkdirSync(t.dir,{recursive:true}),t.dir}function N(){let r=v();return existsSync(r.dir)||mkdirSync(r.dir,{recursive:true}),r.dir}function z(r,t){let{branchesDir:n}=m(r),o=t.replace(/[<>:"/\\|?*]/g,"_"),f=join(n,o);return {dir:f,graphDbPath:join(f,"graph.db"),vectorsDbPath:join(f,"vectors.db")}}function M(r,t){let n=u(r),o=g(t);return existsSync(n)||mkdirSync(n,{recursive:true}),join(n,`faiss-${o}.bin`)}function O(r,t){let n=join(a(),r),o=g(t);return existsSync(n)||mkdirSync(n,{recursive:true}),join(n,`faiss-${o}.bin`)}function R(r,t){let n=u(r),o=g(t);return join(n,`faiss-${o}.idmap.json`)}function U(r,t){let n=u(r),o=g(t);return join(n,`faiss-${o}-hot.bin`)}function J(){return join(p(),"tree-sitter")}function X(){return join(p(),"ast")}function q(){let r=[i(),x(),a(),P(),l()];for(let t of r)existsSync(t)||mkdirSync(t,{recursive:true});}var C,$,Q=b$1(()=>{c();C="main",$=["main","master","dev","develop","trunk"];});export{M as A,O as B,R as C,U as D,J as E,X as F,q as G,K as H,Q as I,i as a,H as b,S as c,x as d,p as e,a as f,P as g,l as h,y as i,E as j,L as k,k as l,D as m,u as n,m as o,v as p,T as q,_ as r,g as s,C as t,F as u,A as v,G as w,I as x,N as y,z};
|
|
@@ -0,0 +1,167 @@
|
|
|
1
|
+
import { init_storage_paths, getProjectPaths, getProjectDir, ensureProjectDir } from './chunk-LH4OUKNZ.js';
|
|
2
|
+
import { init_logging, log } from './chunk-VCCBEJQ5.js';
|
|
3
|
+
import { __require } from './chunk-NAQKA54E.js';
|
|
4
|
+
import { existsSync } from 'fs';
|
|
5
|
+
import { resolve } from 'path';
|
|
6
|
+
|
|
7
|
+
// src/shared/project-context.ts
|
|
8
|
+
init_logging();
|
|
9
|
+
init_storage_paths();
|
|
10
|
+
var ProjectContextManager = class {
|
|
11
|
+
state;
|
|
12
|
+
constructor() {
|
|
13
|
+
const cwd = process.cwd();
|
|
14
|
+
log.i("PROJCTX", `[ProjectContextManager] Initializing with cwd: ${cwd}`);
|
|
15
|
+
this.state = {
|
|
16
|
+
currentProject: cwd,
|
|
17
|
+
previousProject: null
|
|
18
|
+
};
|
|
19
|
+
}
|
|
20
|
+
indexingInProgress = /* @__PURE__ */ new Set();
|
|
21
|
+
onProjectChangeCallbacks = [];
|
|
22
|
+
/**
|
|
23
|
+
* Get current project path
|
|
24
|
+
*/
|
|
25
|
+
getCurrentProject() {
|
|
26
|
+
return this.state.currentProject;
|
|
27
|
+
}
|
|
28
|
+
/**
|
|
29
|
+
* Resolve and normalize project path
|
|
30
|
+
* - If absolute path provided, use it
|
|
31
|
+
* - If relative path, resolve from CWD
|
|
32
|
+
* - If undefined/null, use current project
|
|
33
|
+
*/
|
|
34
|
+
resolveProjectPath(projectPath) {
|
|
35
|
+
if (!projectPath) {
|
|
36
|
+
return this.state.currentProject;
|
|
37
|
+
}
|
|
38
|
+
const resolved = resolve(projectPath);
|
|
39
|
+
return resolved;
|
|
40
|
+
}
|
|
41
|
+
/**
|
|
42
|
+
* Get project info including indexing status
|
|
43
|
+
*/
|
|
44
|
+
getProjectInfo(projectPath) {
|
|
45
|
+
const path = this.resolveProjectPath(projectPath);
|
|
46
|
+
const paths = getProjectPaths(path);
|
|
47
|
+
const projectDir = getProjectDir(path);
|
|
48
|
+
const hash = projectDir.split(/[/\\]/).pop() || "";
|
|
49
|
+
const hasGraphDb = existsSync(paths.graphDbPath);
|
|
50
|
+
const hasVectorsDb = existsSync(paths.vectorsDbPath);
|
|
51
|
+
const isIndexed = hasGraphDb;
|
|
52
|
+
let lastIndexedAt;
|
|
53
|
+
if (existsSync(paths.metaPath)) {
|
|
54
|
+
try {
|
|
55
|
+
const meta = JSON.parse(__require("fs").readFileSync(paths.metaPath, "utf-8"));
|
|
56
|
+
lastIndexedAt = meta.lastIndexedAt;
|
|
57
|
+
} catch {
|
|
58
|
+
}
|
|
59
|
+
}
|
|
60
|
+
return {
|
|
61
|
+
path,
|
|
62
|
+
hash,
|
|
63
|
+
isIndexed,
|
|
64
|
+
hasGraphDb,
|
|
65
|
+
hasVectorsDb,
|
|
66
|
+
lastIndexedAt
|
|
67
|
+
};
|
|
68
|
+
}
|
|
69
|
+
/**
|
|
70
|
+
* Check if project is indexed
|
|
71
|
+
*/
|
|
72
|
+
isProjectIndexed(projectPath) {
|
|
73
|
+
const info = this.getProjectInfo(projectPath);
|
|
74
|
+
return info.isIndexed;
|
|
75
|
+
}
|
|
76
|
+
/**
|
|
77
|
+
* Switch to a different project context
|
|
78
|
+
* Returns true if switch was successful
|
|
79
|
+
*/
|
|
80
|
+
async switchProject(projectPath) {
|
|
81
|
+
const resolved = this.resolveProjectPath(projectPath);
|
|
82
|
+
if (resolved === this.state.currentProject) {
|
|
83
|
+
return true;
|
|
84
|
+
}
|
|
85
|
+
ensureProjectDir(resolved);
|
|
86
|
+
this.state.previousProject = this.state.currentProject;
|
|
87
|
+
this.state.currentProject = resolved;
|
|
88
|
+
log.i("PROJCTX", `[ProjectContext] Switched project: ${this.state.previousProject} -> ${resolved}`);
|
|
89
|
+
for (const callback of this.onProjectChangeCallbacks) {
|
|
90
|
+
try {
|
|
91
|
+
callback(resolved, this.state.previousProject);
|
|
92
|
+
} catch (error) {
|
|
93
|
+
log.e("PROJCTX", "callback_error", { err: String(error) });
|
|
94
|
+
}
|
|
95
|
+
}
|
|
96
|
+
return true;
|
|
97
|
+
}
|
|
98
|
+
/**
|
|
99
|
+
* Get storage paths for current or specified project
|
|
100
|
+
*/
|
|
101
|
+
getStoragePaths(projectPath) {
|
|
102
|
+
const resolved = this.resolveProjectPath(projectPath);
|
|
103
|
+
return getProjectPaths(resolved);
|
|
104
|
+
}
|
|
105
|
+
/**
|
|
106
|
+
* Check if indexing is in progress for a project
|
|
107
|
+
*/
|
|
108
|
+
isIndexingInProgress(projectPath) {
|
|
109
|
+
const resolved = this.resolveProjectPath(projectPath);
|
|
110
|
+
return this.indexingInProgress.has(resolved);
|
|
111
|
+
}
|
|
112
|
+
/**
|
|
113
|
+
* Mark indexing as started for a project
|
|
114
|
+
*/
|
|
115
|
+
startIndexing(projectPath) {
|
|
116
|
+
const resolved = this.resolveProjectPath(projectPath);
|
|
117
|
+
this.indexingInProgress.add(resolved);
|
|
118
|
+
log.i("PROJCTX", `[ProjectContext] Indexing started for: ${resolved}`);
|
|
119
|
+
}
|
|
120
|
+
/**
|
|
121
|
+
* Mark indexing as completed for a project
|
|
122
|
+
*/
|
|
123
|
+
finishIndexing(projectPath) {
|
|
124
|
+
const resolved = this.resolveProjectPath(projectPath);
|
|
125
|
+
this.indexingInProgress.delete(resolved);
|
|
126
|
+
log.i("PROJCTX", `[ProjectContext] Indexing completed for: ${resolved}`);
|
|
127
|
+
}
|
|
128
|
+
/**
|
|
129
|
+
* Register callback for project changes
|
|
130
|
+
*/
|
|
131
|
+
onProjectChange(callback) {
|
|
132
|
+
this.onProjectChangeCallbacks.push(callback);
|
|
133
|
+
}
|
|
134
|
+
/**
|
|
135
|
+
* Get status summary for debugging
|
|
136
|
+
*/
|
|
137
|
+
getStatus() {
|
|
138
|
+
return {
|
|
139
|
+
currentProject: this.state.currentProject,
|
|
140
|
+
previousProject: this.state.previousProject,
|
|
141
|
+
isIndexed: this.isProjectIndexed(),
|
|
142
|
+
indexingInProgress: Array.from(this.indexingInProgress)
|
|
143
|
+
};
|
|
144
|
+
}
|
|
145
|
+
/**
|
|
146
|
+
* Reset to default state (mainly for testing)
|
|
147
|
+
*/
|
|
148
|
+
reset() {
|
|
149
|
+
this.state = {
|
|
150
|
+
currentProject: process.cwd(),
|
|
151
|
+
previousProject: null
|
|
152
|
+
};
|
|
153
|
+
this.indexingInProgress.clear();
|
|
154
|
+
this.onProjectChangeCallbacks = [];
|
|
155
|
+
}
|
|
156
|
+
};
|
|
157
|
+
var instance = null;
|
|
158
|
+
function getProjectContext() {
|
|
159
|
+
if (!instance) {
|
|
160
|
+
instance = new ProjectContextManager();
|
|
161
|
+
}
|
|
162
|
+
return instance;
|
|
163
|
+
}
|
|
164
|
+
|
|
165
|
+
export { getProjectContext };
|
|
166
|
+
//# sourceMappingURL=chunk-TCHCDCDO.js.map
|
|
167
|
+
//# sourceMappingURL=chunk-TCHCDCDO.js.map
|