@elytrasec/engine 0.4.0 → 0.4.1
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/index.js +25 -21
- package/package.json +12 -3
- package/dist/index.d.ts +0 -1358
package/dist/index.d.ts
DELETED
|
@@ -1,1358 +0,0 @@
|
|
|
1
|
-
import { z } from 'zod';
|
|
2
|
-
|
|
3
|
-
/**
|
|
4
|
-
* Unified diff parser.
|
|
5
|
-
*
|
|
6
|
-
* Parses the standard unified-diff format produced by `git diff` and used in
|
|
7
|
-
* GitHub PR diffs into a structured representation of files, hunks, and
|
|
8
|
-
* individual line changes.
|
|
9
|
-
*/
|
|
10
|
-
type ChangeType = "add" | "delete" | "context";
|
|
11
|
-
interface DiffChange {
|
|
12
|
-
type: ChangeType;
|
|
13
|
-
content: string;
|
|
14
|
-
lineNumber: number;
|
|
15
|
-
}
|
|
16
|
-
interface DiffHunk {
|
|
17
|
-
oldStart: number;
|
|
18
|
-
oldLines: number;
|
|
19
|
-
newStart: number;
|
|
20
|
-
newLines: number;
|
|
21
|
-
changes: DiffChange[];
|
|
22
|
-
}
|
|
23
|
-
type FileStatus = "added" | "modified" | "deleted" | "renamed";
|
|
24
|
-
interface DiffFile {
|
|
25
|
-
path: string;
|
|
26
|
-
oldPath: string;
|
|
27
|
-
status: FileStatus;
|
|
28
|
-
hunks: DiffHunk[];
|
|
29
|
-
}
|
|
30
|
-
interface ParsedDiff {
|
|
31
|
-
files: DiffFile[];
|
|
32
|
-
}
|
|
33
|
-
declare function parseDiff(raw: string): ParsedDiff;
|
|
34
|
-
|
|
35
|
-
/**
|
|
36
|
-
* File classifier.
|
|
37
|
-
*
|
|
38
|
-
* Detects language and blockchain ecosystem from file path and optional source
|
|
39
|
-
* content. Used to select the appropriate review rules and prompt sections.
|
|
40
|
-
*/
|
|
41
|
-
type Language = "solidity" | "rust" | "typescript" | "javascript" | "python" | "go" | "java" | "unknown";
|
|
42
|
-
type Chain = "solidity";
|
|
43
|
-
interface FileClassification {
|
|
44
|
-
language: Language;
|
|
45
|
-
chain?: Chain;
|
|
46
|
-
isSmartContract: boolean;
|
|
47
|
-
}
|
|
48
|
-
declare function classifyFile(filePath: string, content?: string): FileClassification;
|
|
49
|
-
|
|
50
|
-
/**
|
|
51
|
-
* Chunk splitter.
|
|
52
|
-
*
|
|
53
|
-
* Splits a list of parsed diff files into chunks that fit within a given
|
|
54
|
-
* token budget so each chunk can be sent to the AI model independently.
|
|
55
|
-
*
|
|
56
|
-
* Token estimation: 1 token ~ 4 characters.
|
|
57
|
-
*/
|
|
58
|
-
|
|
59
|
-
interface DiffChunk {
|
|
60
|
-
/** Files (or partial files) included in this chunk. */
|
|
61
|
-
files: DiffFile[];
|
|
62
|
-
/** Estimated token count for this chunk. */
|
|
63
|
-
estimatedTokens: number;
|
|
64
|
-
}
|
|
65
|
-
declare function splitIntoChunks(files: DiffFile[], maxChunkTokens: number): DiffChunk[];
|
|
66
|
-
|
|
67
|
-
declare const SeveritySchema: z.ZodEnum<["critical", "high", "medium", "low", "info"]>;
|
|
68
|
-
type Severity = z.infer<typeof SeveritySchema>;
|
|
69
|
-
declare const FindingSchema: z.ZodObject<{
|
|
70
|
-
severity: z.ZodEnum<["critical", "high", "medium", "low", "info"]>;
|
|
71
|
-
category: z.ZodString;
|
|
72
|
-
title: z.ZodString;
|
|
73
|
-
description: z.ZodString;
|
|
74
|
-
filePath: z.ZodString;
|
|
75
|
-
startLine: z.ZodNumber;
|
|
76
|
-
endLine: z.ZodNumber;
|
|
77
|
-
codeSnippet: z.ZodString;
|
|
78
|
-
suggestion: z.ZodString;
|
|
79
|
-
fixDiff: z.ZodString;
|
|
80
|
-
ruleId: z.ZodString;
|
|
81
|
-
cweIds: z.ZodOptional<z.ZodArray<z.ZodString, "many">>;
|
|
82
|
-
owaspCategory: z.ZodOptional<z.ZodString>;
|
|
83
|
-
confidence: z.ZodOptional<z.ZodEnum<["high", "medium", "low"]>>;
|
|
84
|
-
}, "strip", z.ZodTypeAny, {
|
|
85
|
-
severity: "critical" | "high" | "medium" | "low" | "info";
|
|
86
|
-
category: string;
|
|
87
|
-
title: string;
|
|
88
|
-
description: string;
|
|
89
|
-
filePath: string;
|
|
90
|
-
startLine: number;
|
|
91
|
-
endLine: number;
|
|
92
|
-
codeSnippet: string;
|
|
93
|
-
suggestion: string;
|
|
94
|
-
fixDiff: string;
|
|
95
|
-
ruleId: string;
|
|
96
|
-
cweIds?: string[] | undefined;
|
|
97
|
-
owaspCategory?: string | undefined;
|
|
98
|
-
confidence?: "high" | "medium" | "low" | undefined;
|
|
99
|
-
}, {
|
|
100
|
-
severity: "critical" | "high" | "medium" | "low" | "info";
|
|
101
|
-
category: string;
|
|
102
|
-
title: string;
|
|
103
|
-
description: string;
|
|
104
|
-
filePath: string;
|
|
105
|
-
startLine: number;
|
|
106
|
-
endLine: number;
|
|
107
|
-
codeSnippet: string;
|
|
108
|
-
suggestion: string;
|
|
109
|
-
fixDiff: string;
|
|
110
|
-
ruleId: string;
|
|
111
|
-
cweIds?: string[] | undefined;
|
|
112
|
-
owaspCategory?: string | undefined;
|
|
113
|
-
confidence?: "high" | "medium" | "low" | undefined;
|
|
114
|
-
}>;
|
|
115
|
-
type Finding = z.infer<typeof FindingSchema>;
|
|
116
|
-
declare const SecurityScoreSchema: z.ZodObject<{
|
|
117
|
-
score: z.ZodNumber;
|
|
118
|
-
grade: z.ZodEnum<["A", "B", "C", "D", "F"]>;
|
|
119
|
-
breakdown: z.ZodRecord<z.ZodEnum<["critical", "high", "medium", "low", "info"]>, z.ZodObject<{
|
|
120
|
-
count: z.ZodNumber;
|
|
121
|
-
deducted: z.ZodNumber;
|
|
122
|
-
}, "strip", z.ZodTypeAny, {
|
|
123
|
-
count: number;
|
|
124
|
-
deducted: number;
|
|
125
|
-
}, {
|
|
126
|
-
count: number;
|
|
127
|
-
deducted: number;
|
|
128
|
-
}>>;
|
|
129
|
-
}, "strip", z.ZodTypeAny, {
|
|
130
|
-
score: number;
|
|
131
|
-
grade: "A" | "B" | "C" | "D" | "F";
|
|
132
|
-
breakdown: Partial<Record<"critical" | "high" | "medium" | "low" | "info", {
|
|
133
|
-
count: number;
|
|
134
|
-
deducted: number;
|
|
135
|
-
}>>;
|
|
136
|
-
}, {
|
|
137
|
-
score: number;
|
|
138
|
-
grade: "A" | "B" | "C" | "D" | "F";
|
|
139
|
-
breakdown: Partial<Record<"critical" | "high" | "medium" | "low" | "info", {
|
|
140
|
-
count: number;
|
|
141
|
-
deducted: number;
|
|
142
|
-
}>>;
|
|
143
|
-
}>;
|
|
144
|
-
type SecurityScoreOutput = z.infer<typeof SecurityScoreSchema>;
|
|
145
|
-
declare const ReviewResultSchema: z.ZodObject<{
|
|
146
|
-
findings: z.ZodArray<z.ZodObject<{
|
|
147
|
-
severity: z.ZodEnum<["critical", "high", "medium", "low", "info"]>;
|
|
148
|
-
category: z.ZodString;
|
|
149
|
-
title: z.ZodString;
|
|
150
|
-
description: z.ZodString;
|
|
151
|
-
filePath: z.ZodString;
|
|
152
|
-
startLine: z.ZodNumber;
|
|
153
|
-
endLine: z.ZodNumber;
|
|
154
|
-
codeSnippet: z.ZodString;
|
|
155
|
-
suggestion: z.ZodString;
|
|
156
|
-
fixDiff: z.ZodString;
|
|
157
|
-
ruleId: z.ZodString;
|
|
158
|
-
cweIds: z.ZodOptional<z.ZodArray<z.ZodString, "many">>;
|
|
159
|
-
owaspCategory: z.ZodOptional<z.ZodString>;
|
|
160
|
-
confidence: z.ZodOptional<z.ZodEnum<["high", "medium", "low"]>>;
|
|
161
|
-
}, "strip", z.ZodTypeAny, {
|
|
162
|
-
severity: "critical" | "high" | "medium" | "low" | "info";
|
|
163
|
-
category: string;
|
|
164
|
-
title: string;
|
|
165
|
-
description: string;
|
|
166
|
-
filePath: string;
|
|
167
|
-
startLine: number;
|
|
168
|
-
endLine: number;
|
|
169
|
-
codeSnippet: string;
|
|
170
|
-
suggestion: string;
|
|
171
|
-
fixDiff: string;
|
|
172
|
-
ruleId: string;
|
|
173
|
-
cweIds?: string[] | undefined;
|
|
174
|
-
owaspCategory?: string | undefined;
|
|
175
|
-
confidence?: "high" | "medium" | "low" | undefined;
|
|
176
|
-
}, {
|
|
177
|
-
severity: "critical" | "high" | "medium" | "low" | "info";
|
|
178
|
-
category: string;
|
|
179
|
-
title: string;
|
|
180
|
-
description: string;
|
|
181
|
-
filePath: string;
|
|
182
|
-
startLine: number;
|
|
183
|
-
endLine: number;
|
|
184
|
-
codeSnippet: string;
|
|
185
|
-
suggestion: string;
|
|
186
|
-
fixDiff: string;
|
|
187
|
-
ruleId: string;
|
|
188
|
-
cweIds?: string[] | undefined;
|
|
189
|
-
owaspCategory?: string | undefined;
|
|
190
|
-
confidence?: "high" | "medium" | "low" | undefined;
|
|
191
|
-
}>, "many">;
|
|
192
|
-
summary: z.ZodString;
|
|
193
|
-
score: z.ZodOptional<z.ZodObject<{
|
|
194
|
-
score: z.ZodNumber;
|
|
195
|
-
grade: z.ZodEnum<["A", "B", "C", "D", "F"]>;
|
|
196
|
-
breakdown: z.ZodRecord<z.ZodEnum<["critical", "high", "medium", "low", "info"]>, z.ZodObject<{
|
|
197
|
-
count: z.ZodNumber;
|
|
198
|
-
deducted: z.ZodNumber;
|
|
199
|
-
}, "strip", z.ZodTypeAny, {
|
|
200
|
-
count: number;
|
|
201
|
-
deducted: number;
|
|
202
|
-
}, {
|
|
203
|
-
count: number;
|
|
204
|
-
deducted: number;
|
|
205
|
-
}>>;
|
|
206
|
-
}, "strip", z.ZodTypeAny, {
|
|
207
|
-
score: number;
|
|
208
|
-
grade: "A" | "B" | "C" | "D" | "F";
|
|
209
|
-
breakdown: Partial<Record<"critical" | "high" | "medium" | "low" | "info", {
|
|
210
|
-
count: number;
|
|
211
|
-
deducted: number;
|
|
212
|
-
}>>;
|
|
213
|
-
}, {
|
|
214
|
-
score: number;
|
|
215
|
-
grade: "A" | "B" | "C" | "D" | "F";
|
|
216
|
-
breakdown: Partial<Record<"critical" | "high" | "medium" | "low" | "info", {
|
|
217
|
-
count: number;
|
|
218
|
-
deducted: number;
|
|
219
|
-
}>>;
|
|
220
|
-
}>>;
|
|
221
|
-
/** keyed by "${ruleId}:${filePath}:${startLine}" — only present when runPoc=true */
|
|
222
|
-
pocs: z.ZodOptional<z.ZodRecord<z.ZodString, z.ZodObject<{
|
|
223
|
-
status: z.ZodEnum<["confirmed", "not-exploitable", "generated", "error"]>;
|
|
224
|
-
pocCode: z.ZodString;
|
|
225
|
-
output: z.ZodString;
|
|
226
|
-
rpcUrl: z.ZodOptional<z.ZodString>;
|
|
227
|
-
}, "strip", z.ZodTypeAny, {
|
|
228
|
-
status: "confirmed" | "not-exploitable" | "generated" | "error";
|
|
229
|
-
pocCode: string;
|
|
230
|
-
output: string;
|
|
231
|
-
rpcUrl?: string | undefined;
|
|
232
|
-
}, {
|
|
233
|
-
status: "confirmed" | "not-exploitable" | "generated" | "error";
|
|
234
|
-
pocCode: string;
|
|
235
|
-
output: string;
|
|
236
|
-
rpcUrl?: string | undefined;
|
|
237
|
-
}>>>;
|
|
238
|
-
}, "strip", z.ZodTypeAny, {
|
|
239
|
-
findings: {
|
|
240
|
-
severity: "critical" | "high" | "medium" | "low" | "info";
|
|
241
|
-
category: string;
|
|
242
|
-
title: string;
|
|
243
|
-
description: string;
|
|
244
|
-
filePath: string;
|
|
245
|
-
startLine: number;
|
|
246
|
-
endLine: number;
|
|
247
|
-
codeSnippet: string;
|
|
248
|
-
suggestion: string;
|
|
249
|
-
fixDiff: string;
|
|
250
|
-
ruleId: string;
|
|
251
|
-
cweIds?: string[] | undefined;
|
|
252
|
-
owaspCategory?: string | undefined;
|
|
253
|
-
confidence?: "high" | "medium" | "low" | undefined;
|
|
254
|
-
}[];
|
|
255
|
-
summary: string;
|
|
256
|
-
score?: {
|
|
257
|
-
score: number;
|
|
258
|
-
grade: "A" | "B" | "C" | "D" | "F";
|
|
259
|
-
breakdown: Partial<Record<"critical" | "high" | "medium" | "low" | "info", {
|
|
260
|
-
count: number;
|
|
261
|
-
deducted: number;
|
|
262
|
-
}>>;
|
|
263
|
-
} | undefined;
|
|
264
|
-
pocs?: Record<string, {
|
|
265
|
-
status: "confirmed" | "not-exploitable" | "generated" | "error";
|
|
266
|
-
pocCode: string;
|
|
267
|
-
output: string;
|
|
268
|
-
rpcUrl?: string | undefined;
|
|
269
|
-
}> | undefined;
|
|
270
|
-
}, {
|
|
271
|
-
findings: {
|
|
272
|
-
severity: "critical" | "high" | "medium" | "low" | "info";
|
|
273
|
-
category: string;
|
|
274
|
-
title: string;
|
|
275
|
-
description: string;
|
|
276
|
-
filePath: string;
|
|
277
|
-
startLine: number;
|
|
278
|
-
endLine: number;
|
|
279
|
-
codeSnippet: string;
|
|
280
|
-
suggestion: string;
|
|
281
|
-
fixDiff: string;
|
|
282
|
-
ruleId: string;
|
|
283
|
-
cweIds?: string[] | undefined;
|
|
284
|
-
owaspCategory?: string | undefined;
|
|
285
|
-
confidence?: "high" | "medium" | "low" | undefined;
|
|
286
|
-
}[];
|
|
287
|
-
summary: string;
|
|
288
|
-
score?: {
|
|
289
|
-
score: number;
|
|
290
|
-
grade: "A" | "B" | "C" | "D" | "F";
|
|
291
|
-
breakdown: Partial<Record<"critical" | "high" | "medium" | "low" | "info", {
|
|
292
|
-
count: number;
|
|
293
|
-
deducted: number;
|
|
294
|
-
}>>;
|
|
295
|
-
} | undefined;
|
|
296
|
-
pocs?: Record<string, {
|
|
297
|
-
status: "confirmed" | "not-exploitable" | "generated" | "error";
|
|
298
|
-
pocCode: string;
|
|
299
|
-
output: string;
|
|
300
|
-
rpcUrl?: string | undefined;
|
|
301
|
-
}> | undefined;
|
|
302
|
-
}>;
|
|
303
|
-
type ReviewResult = z.infer<typeof ReviewResultSchema>;
|
|
304
|
-
|
|
305
|
-
/**
|
|
306
|
-
* Pluggable AI provider interface.
|
|
307
|
-
*
|
|
308
|
-
* Any AI backend that can perform message-based completions implements this
|
|
309
|
-
* interface. The engine never imports a specific SDK directly — it goes
|
|
310
|
-
* through an AIProvider.
|
|
311
|
-
*/
|
|
312
|
-
interface AIMessage {
|
|
313
|
-
role: "system" | "user" | "assistant";
|
|
314
|
-
content: string;
|
|
315
|
-
}
|
|
316
|
-
interface AICompleteParams {
|
|
317
|
-
messages: AIMessage[];
|
|
318
|
-
maxTokens: number;
|
|
319
|
-
model?: string;
|
|
320
|
-
}
|
|
321
|
-
interface AICompleteResult {
|
|
322
|
-
text: string;
|
|
323
|
-
}
|
|
324
|
-
interface AIProvider {
|
|
325
|
-
/** Human-readable name for logs, e.g. "anthropic", "openai", "ollama". */
|
|
326
|
-
readonly name: string;
|
|
327
|
-
/**
|
|
328
|
-
* Send a chat completion request and return the assistant's text response.
|
|
329
|
-
* Implementations handle their own retry/rate-limit logic.
|
|
330
|
-
*/
|
|
331
|
-
complete(params: AICompleteParams): Promise<AICompleteResult>;
|
|
332
|
-
}
|
|
333
|
-
|
|
334
|
-
/**
|
|
335
|
-
* AI client wrapper.
|
|
336
|
-
*
|
|
337
|
-
* Handles communication with any AI provider through the pluggable
|
|
338
|
-
* AIProvider interface. Parses structured output with Zod and handles
|
|
339
|
-
* JSON extraction from model responses.
|
|
340
|
-
*
|
|
341
|
-
* Backward compatible: accepts either an AIProvider instance or a raw
|
|
342
|
-
* API key string (which auto-creates an AnthropicProvider).
|
|
343
|
-
*/
|
|
344
|
-
|
|
345
|
-
interface AnalyzeCodeParams {
|
|
346
|
-
systemPrompt: string;
|
|
347
|
-
diff: string;
|
|
348
|
-
fileClassifications: FileClassification[];
|
|
349
|
-
rules: string[];
|
|
350
|
-
}
|
|
351
|
-
interface AnalyzeFileParams {
|
|
352
|
-
systemPrompt: string;
|
|
353
|
-
filePath: string;
|
|
354
|
-
content: string;
|
|
355
|
-
classification: FileClassification;
|
|
356
|
-
rules: string[];
|
|
357
|
-
}
|
|
358
|
-
declare class AIClient {
|
|
359
|
-
private provider;
|
|
360
|
-
/**
|
|
361
|
-
* Create an AIClient.
|
|
362
|
-
*
|
|
363
|
-
* @overload New: pass an AIProvider directly.
|
|
364
|
-
* @overload Legacy: pass an API key string to auto-create an AnthropicProvider.
|
|
365
|
-
*/
|
|
366
|
-
constructor(providerOrApiKey: AIProvider | string, model?: string);
|
|
367
|
-
/**
|
|
368
|
-
* Send a diff chunk to the AI for analysis and return structured findings.
|
|
369
|
-
*/
|
|
370
|
-
analyzeCode(params: AnalyzeCodeParams): Promise<Finding[]>;
|
|
371
|
-
/**
|
|
372
|
-
* Send a full source file to the AI for security review.
|
|
373
|
-
*/
|
|
374
|
-
analyzeFile(params: AnalyzeFileParams): Promise<Finding[]>;
|
|
375
|
-
}
|
|
376
|
-
|
|
377
|
-
/**
|
|
378
|
-
* System prompt builder for the AI review engine.
|
|
379
|
-
*
|
|
380
|
-
* Constructs a detailed system prompt that instructs Claude to perform a code
|
|
381
|
-
* review, covering general best practices plus chain-specific security
|
|
382
|
-
* guidance when crypto-related files are detected.
|
|
383
|
-
*/
|
|
384
|
-
|
|
385
|
-
declare function getSystemPrompt(classifications: FileClassification[], ruleDescriptions: string[], staticAnalysisContext?: string): string;
|
|
386
|
-
|
|
387
|
-
/**
|
|
388
|
-
* Anthropic (Claude) AI provider.
|
|
389
|
-
*
|
|
390
|
-
* Requires `@anthropic-ai/sdk` as an optional peer dependency.
|
|
391
|
-
*/
|
|
392
|
-
|
|
393
|
-
declare class AnthropicProvider implements AIProvider {
|
|
394
|
-
readonly name = "anthropic";
|
|
395
|
-
private apiKey;
|
|
396
|
-
private defaultModel;
|
|
397
|
-
constructor(apiKey: string, model?: string);
|
|
398
|
-
complete(params: AICompleteParams): Promise<AICompleteResult>;
|
|
399
|
-
private withRetry;
|
|
400
|
-
}
|
|
401
|
-
|
|
402
|
-
/**
|
|
403
|
-
* OpenAI AI provider.
|
|
404
|
-
*
|
|
405
|
-
* Requires `openai` as an optional peer dependency.
|
|
406
|
-
* Uses dynamic require/import to avoid build failures when the package isn't installed.
|
|
407
|
-
*/
|
|
408
|
-
|
|
409
|
-
declare class OpenAIProvider implements AIProvider {
|
|
410
|
-
readonly name = "openai";
|
|
411
|
-
private apiKey;
|
|
412
|
-
private defaultModel;
|
|
413
|
-
constructor(apiKey: string, model?: string);
|
|
414
|
-
complete(params: AICompleteParams): Promise<AICompleteResult>;
|
|
415
|
-
private withRetry;
|
|
416
|
-
}
|
|
417
|
-
|
|
418
|
-
/**
|
|
419
|
-
* Ollama AI provider.
|
|
420
|
-
*
|
|
421
|
-
* Uses Ollama's OpenAI-compatible API via native fetch. No external
|
|
422
|
-
* dependencies required.
|
|
423
|
-
*/
|
|
424
|
-
|
|
425
|
-
declare class OllamaProvider implements AIProvider {
|
|
426
|
-
readonly name = "ollama";
|
|
427
|
-
private baseUrl;
|
|
428
|
-
private defaultModel;
|
|
429
|
-
constructor(baseUrl?: string, model?: string);
|
|
430
|
-
complete(params: AICompleteParams): Promise<AICompleteResult>;
|
|
431
|
-
}
|
|
432
|
-
|
|
433
|
-
/**
|
|
434
|
-
* Mock AI provider for tests.
|
|
435
|
-
*
|
|
436
|
-
* Returns canned responses. No network calls, no dependencies.
|
|
437
|
-
*/
|
|
438
|
-
|
|
439
|
-
interface MockResponse {
|
|
440
|
-
/** Substring match on the user message to trigger this response. */
|
|
441
|
-
match?: string;
|
|
442
|
-
/** The response text to return. */
|
|
443
|
-
text: string;
|
|
444
|
-
}
|
|
445
|
-
declare class MockProvider implements AIProvider {
|
|
446
|
-
readonly name = "mock";
|
|
447
|
-
private responses;
|
|
448
|
-
/** Number of times `complete` has been called. */
|
|
449
|
-
callCount: number;
|
|
450
|
-
/** Record of all calls for assertion. */
|
|
451
|
-
calls: AICompleteParams[];
|
|
452
|
-
constructor(responses?: MockResponse[]);
|
|
453
|
-
complete(params: AICompleteParams): Promise<AICompleteResult>;
|
|
454
|
-
}
|
|
455
|
-
|
|
456
|
-
/**
|
|
457
|
-
* Provider factory.
|
|
458
|
-
*
|
|
459
|
-
* Creates the appropriate AIProvider from environment-style configuration.
|
|
460
|
-
*/
|
|
461
|
-
|
|
462
|
-
interface CreateProviderOptions {
|
|
463
|
-
provider: "anthropic" | "openai" | "ollama" | "mock";
|
|
464
|
-
apiKey?: string;
|
|
465
|
-
model?: string;
|
|
466
|
-
/** Ollama base URL (default http://localhost:11434). */
|
|
467
|
-
ollamaUrl?: string;
|
|
468
|
-
}
|
|
469
|
-
/**
|
|
470
|
-
* Create an AIProvider from a config object.
|
|
471
|
-
*
|
|
472
|
-
* ```ts
|
|
473
|
-
* const provider = createProvider({ provider: "openai", apiKey: "sk-..." });
|
|
474
|
-
* ```
|
|
475
|
-
*/
|
|
476
|
-
declare function createProvider(options: CreateProviderOptions): AIProvider;
|
|
477
|
-
|
|
478
|
-
/**
|
|
479
|
-
* Rule registry.
|
|
480
|
-
*
|
|
481
|
-
* Central catalogue of all available review rules. Consumers select rules by
|
|
482
|
-
* chain or ruleset category when starting a review.
|
|
483
|
-
*/
|
|
484
|
-
|
|
485
|
-
interface Rule {
|
|
486
|
-
id: string;
|
|
487
|
-
name: string;
|
|
488
|
-
description: string;
|
|
489
|
-
category: string;
|
|
490
|
-
chain?: string;
|
|
491
|
-
severity: Severity;
|
|
492
|
-
enabled: boolean;
|
|
493
|
-
}
|
|
494
|
-
/**
|
|
495
|
-
* Returns every registered rule.
|
|
496
|
-
*/
|
|
497
|
-
declare function getAllRules(): Rule[];
|
|
498
|
-
/**
|
|
499
|
-
* Returns rules relevant to the given set of chains, plus all general
|
|
500
|
-
* (chain-agnostic) rules.
|
|
501
|
-
*/
|
|
502
|
-
declare function getRulesForChains(chains: string[]): Rule[];
|
|
503
|
-
|
|
504
|
-
/**
|
|
505
|
-
* CWE / OWASP Top 10 (2021) mapping for every engine rule.
|
|
506
|
-
*
|
|
507
|
-
* Security rules map to specific CWEs and OWASP categories.
|
|
508
|
-
* Quality, gas, and performance rules have empty arrays (not security weaknesses).
|
|
509
|
-
*/
|
|
510
|
-
interface CweOwaspEntry {
|
|
511
|
-
cweIds: string[];
|
|
512
|
-
owaspCategory?: string;
|
|
513
|
-
}
|
|
514
|
-
/**
|
|
515
|
-
* Maps each ruleId to its CWE identifiers and OWASP 2021 category.
|
|
516
|
-
*/
|
|
517
|
-
declare const CWE_OWASP_MAP: Record<string, CweOwaspEntry>;
|
|
518
|
-
/**
|
|
519
|
-
* Look up CWE/OWASP data for a given rule. Returns empty arrays for unknown
|
|
520
|
-
* rules so callers never need to null-check.
|
|
521
|
-
*/
|
|
522
|
-
declare function getCweOwasp(ruleId: string): CweOwaspEntry;
|
|
523
|
-
|
|
524
|
-
/**
|
|
525
|
-
* Security score calculator.
|
|
526
|
-
*
|
|
527
|
-
* Produces a 0-100 score from a list of findings, with a letter grade and
|
|
528
|
-
* per-severity breakdown.
|
|
529
|
-
*
|
|
530
|
-
* Features:
|
|
531
|
-
* - Per-rule cap: max 30 points deducted from the same ruleId
|
|
532
|
-
* - Severity tier caps: INFO ≤5, LOW ≤25, MEDIUM ≤30, HIGH ≤30, CRITICAL ≤100
|
|
533
|
-
* - Confidence multiplier: high=1.0, medium=0.6, low=0.3
|
|
534
|
-
* - Density normalization: LOW/INFO deductions scale with findings-per-file
|
|
535
|
-
*/
|
|
536
|
-
|
|
537
|
-
type Grade = "A" | "B" | "C" | "D" | "F";
|
|
538
|
-
interface SecurityScore {
|
|
539
|
-
/** Numeric score, 0 (worst) to 100 (perfect). */
|
|
540
|
-
score: number;
|
|
541
|
-
/** Letter grade: A, B, C, D, or F. */
|
|
542
|
-
grade: Grade;
|
|
543
|
-
/** How many points were deducted per severity bucket. */
|
|
544
|
-
breakdown: Record<Severity, {
|
|
545
|
-
count: number;
|
|
546
|
-
deducted: number;
|
|
547
|
-
}>;
|
|
548
|
-
}
|
|
549
|
-
/**
|
|
550
|
-
* Compute a security score from a set of findings.
|
|
551
|
-
*
|
|
552
|
-
* 1. Accumulate per-finding deductions (severity × confidence × per-rule cap)
|
|
553
|
-
* 2. Apply severity tier caps
|
|
554
|
-
* 3. Normalize LOW/INFO deductions by file density (findings-per-file)
|
|
555
|
-
* 4. Security tiers (CRITICAL/HIGH/MEDIUM) always count at full weight
|
|
556
|
-
*/
|
|
557
|
-
declare function computeScore(findings: Finding[], fileCount?: number): SecurityScore;
|
|
558
|
-
|
|
559
|
-
declare const solidityRules: Rule[];
|
|
560
|
-
|
|
561
|
-
declare const generalRules: Rule[];
|
|
562
|
-
|
|
563
|
-
declare const reconRules: Rule[];
|
|
564
|
-
|
|
565
|
-
declare const authRules: Rule[];
|
|
566
|
-
|
|
567
|
-
declare const injectionRules: Rule[];
|
|
568
|
-
|
|
569
|
-
declare const apiRules: Rule[];
|
|
570
|
-
|
|
571
|
-
declare const complexityRules: Rule[];
|
|
572
|
-
|
|
573
|
-
declare const namingRules: Rule[];
|
|
574
|
-
|
|
575
|
-
declare const deadCodeRules: Rule[];
|
|
576
|
-
|
|
577
|
-
declare const gasRules: Rule[];
|
|
578
|
-
|
|
579
|
-
declare const bestPracticeRules: Rule[];
|
|
580
|
-
|
|
581
|
-
/**
|
|
582
|
-
* GitHub PR review comment formatter.
|
|
583
|
-
*
|
|
584
|
-
* Converts engine findings into the format expected by the GitHub Pull Request
|
|
585
|
-
* Review Comments API.
|
|
586
|
-
*/
|
|
587
|
-
|
|
588
|
-
interface GitHubReviewComment {
|
|
589
|
-
path: string;
|
|
590
|
-
line: number;
|
|
591
|
-
side: "RIGHT";
|
|
592
|
-
body: string;
|
|
593
|
-
}
|
|
594
|
-
/**
|
|
595
|
-
* Convert findings into GitHub review comments, filtering to only files
|
|
596
|
-
* present in the PR.
|
|
597
|
-
*/
|
|
598
|
-
declare function formatAsReviewComments(findings: Finding[], prFiles: string[]): GitHubReviewComment[];
|
|
599
|
-
|
|
600
|
-
/**
|
|
601
|
-
* Markdown security report generator.
|
|
602
|
-
*
|
|
603
|
-
* Produces a standalone markdown document suitable for sharing with a CISO or
|
|
604
|
-
* attaching to a compliance ticket.
|
|
605
|
-
*/
|
|
606
|
-
|
|
607
|
-
interface ReportOptions {
|
|
608
|
-
projectName?: string;
|
|
609
|
-
timestamp?: string | Date;
|
|
610
|
-
}
|
|
611
|
-
/**
|
|
612
|
-
* Generate a complete markdown security report.
|
|
613
|
-
*/
|
|
614
|
-
declare function generateMarkdownReport(findings: Finding[], score: SecurityScore, options?: ReportOptions): string;
|
|
615
|
-
|
|
616
|
-
/**
|
|
617
|
-
* Shared types for static analysis tool integrations.
|
|
618
|
-
*/
|
|
619
|
-
|
|
620
|
-
/** A finding produced by a static analysis tool (before mapping to our schema). */
|
|
621
|
-
interface StaticFinding {
|
|
622
|
-
tool: string;
|
|
623
|
-
ruleId: string;
|
|
624
|
-
severity: Severity;
|
|
625
|
-
category: string;
|
|
626
|
-
title: string;
|
|
627
|
-
description: string;
|
|
628
|
-
filePath: string;
|
|
629
|
-
startLine: number;
|
|
630
|
-
endLine: number;
|
|
631
|
-
codeSnippet: string;
|
|
632
|
-
suggestion: string;
|
|
633
|
-
fixDiff: string;
|
|
634
|
-
/** Confidence: "high" = deterministic tool, "medium" = heuristic, "low" = pattern match */
|
|
635
|
-
confidence: "high" | "medium" | "low";
|
|
636
|
-
}
|
|
637
|
-
/** Options passed to every tool runner. */
|
|
638
|
-
interface ToolRunnerOptions {
|
|
639
|
-
/** Absolute path to the repository root. */
|
|
640
|
-
repoPath: string;
|
|
641
|
-
/** Files that were changed in the PR (relative paths). */
|
|
642
|
-
changedFiles: string[];
|
|
643
|
-
/** Changed line ranges per file: { "path/to/file.sol": [[10,15], [30,40]] } */
|
|
644
|
-
changedLineRanges: Record<string, [number, number][]>;
|
|
645
|
-
/** Timeout in ms for tool execution. */
|
|
646
|
-
timeout?: number;
|
|
647
|
-
}
|
|
648
|
-
/** Interface that every tool runner must implement. */
|
|
649
|
-
interface ToolRunner {
|
|
650
|
-
/** Tool name (e.g., "slither", "semgrep", "gitleaks"). */
|
|
651
|
-
name: string;
|
|
652
|
-
/** Check if the tool is installed and available. */
|
|
653
|
-
isAvailable(): Promise<boolean>;
|
|
654
|
-
/** Check if this tool is relevant for the given files. */
|
|
655
|
-
isRelevant(changedFiles: string[]): boolean;
|
|
656
|
-
/** Run analysis and return findings. */
|
|
657
|
-
run(options: ToolRunnerOptions): Promise<StaticFinding[]>;
|
|
658
|
-
}
|
|
659
|
-
|
|
660
|
-
/**
|
|
661
|
-
* Static analysis orchestrator.
|
|
662
|
-
*
|
|
663
|
-
* Runs all available tools in parallel, collects findings, filters to
|
|
664
|
-
* changed lines only, deduplicates, and returns unified results.
|
|
665
|
-
*/
|
|
666
|
-
|
|
667
|
-
interface StaticAnalysisOptions {
|
|
668
|
-
/** Absolute path to the repository root. */
|
|
669
|
-
repoPath: string;
|
|
670
|
-
/** Files that were changed in the PR (relative paths). */
|
|
671
|
-
changedFiles: string[];
|
|
672
|
-
/** Changed line ranges per file: { "path/to/file.sol": [[10,15], [30,40]] } */
|
|
673
|
-
changedLineRanges: Record<string, [number, number][]>;
|
|
674
|
-
/** Timeout per tool in ms. Defaults to 120000 (2 min). */
|
|
675
|
-
toolTimeout?: number;
|
|
676
|
-
}
|
|
677
|
-
interface StaticAnalysisResult {
|
|
678
|
-
/** Findings mapped to our standard Finding schema. */
|
|
679
|
-
findings: Finding[];
|
|
680
|
-
/** Raw findings with tool metadata (for passing context to AI). */
|
|
681
|
-
rawFindings: StaticFinding[];
|
|
682
|
-
/** Which tools ran successfully. */
|
|
683
|
-
toolsRan: string[];
|
|
684
|
-
/** Which tools were skipped (not available or not relevant). */
|
|
685
|
-
toolsSkipped: string[];
|
|
686
|
-
/** Errors encountered. */
|
|
687
|
-
errors: {
|
|
688
|
-
tool: string;
|
|
689
|
-
error: string;
|
|
690
|
-
}[];
|
|
691
|
-
}
|
|
692
|
-
/**
|
|
693
|
-
* Run all available static analysis tools in parallel.
|
|
694
|
-
*
|
|
695
|
-
* Returns findings filtered to changed lines only, deduplicated.
|
|
696
|
-
*/
|
|
697
|
-
declare function runStaticAnalysis(options: StaticAnalysisOptions): Promise<StaticAnalysisResult>;
|
|
698
|
-
/**
|
|
699
|
-
* Format static findings as context for the AI prompt.
|
|
700
|
-
* This helps the AI understand what static tools already caught,
|
|
701
|
-
* so it can focus on higher-level issues and avoid duplicating.
|
|
702
|
-
*/
|
|
703
|
-
declare function formatStaticFindingsForAI(rawFindings: StaticFinding[]): string;
|
|
704
|
-
|
|
705
|
-
/**
|
|
706
|
-
* Slither integration — Solidity static analysis.
|
|
707
|
-
*
|
|
708
|
-
* Slither (by Trail of Bits) has 80+ detectors for common Solidity
|
|
709
|
-
* vulnerabilities. We run it on the repo, parse JSON output, and map
|
|
710
|
-
* findings to our schema — filtered to only changed lines.
|
|
711
|
-
*/
|
|
712
|
-
|
|
713
|
-
declare const slitherRunner: ToolRunner;
|
|
714
|
-
|
|
715
|
-
/**
|
|
716
|
-
* Semgrep integration — polyglot static analysis.
|
|
717
|
-
*
|
|
718
|
-
* Runs Semgrep with our custom crypto rules + community security packs.
|
|
719
|
-
* Parses JSON output and maps to our Finding schema.
|
|
720
|
-
*/
|
|
721
|
-
|
|
722
|
-
declare const semgrepRunner: ToolRunner;
|
|
723
|
-
|
|
724
|
-
/**
|
|
725
|
-
* Gitleaks integration — secret detection.
|
|
726
|
-
*
|
|
727
|
-
* Scans for hardcoded secrets, API keys, private keys, passwords.
|
|
728
|
-
* Maps findings to our schema, filtered to changed files/lines.
|
|
729
|
-
*/
|
|
730
|
-
|
|
731
|
-
declare const gitleaksRunner: ToolRunner;
|
|
732
|
-
|
|
733
|
-
/**
|
|
734
|
-
* PROPRIETARY — Detection rule definitions.
|
|
735
|
-
*
|
|
736
|
-
* This file contains Elytra's vulnerability detection patterns.
|
|
737
|
-
* It is NOT tracked in git when the repository is public.
|
|
738
|
-
* For open-source builds, see pattern-rules.private.example.ts.
|
|
739
|
-
*/
|
|
740
|
-
|
|
741
|
-
interface PatternRule$1 {
|
|
742
|
-
id: string;
|
|
743
|
-
title: string;
|
|
744
|
-
description: string;
|
|
745
|
-
suggestion: string;
|
|
746
|
-
pattern: RegExp;
|
|
747
|
-
multilinePattern?: RegExp;
|
|
748
|
-
severity: Severity;
|
|
749
|
-
category: string;
|
|
750
|
-
confidence: "high" | "medium" | "low";
|
|
751
|
-
languages: string[];
|
|
752
|
-
pathPattern?: RegExp;
|
|
753
|
-
fixTemplate?: string;
|
|
754
|
-
fixFn?: (line: string) => string;
|
|
755
|
-
multilineFixFn?: (matchedText: string) => string;
|
|
756
|
-
}
|
|
757
|
-
declare const ALL_RULES: PatternRule$1[];
|
|
758
|
-
|
|
759
|
-
/**
|
|
760
|
-
* Pattern Scanner — pure TypeScript regex-based vulnerability scanner.
|
|
761
|
-
*
|
|
762
|
-
* No external binary dependencies. Reads source files and matches regex
|
|
763
|
-
* patterns against their content to find security issues, bugs, and
|
|
764
|
-
* code-quality problems.
|
|
765
|
-
*/
|
|
766
|
-
|
|
767
|
-
interface PatternRule {
|
|
768
|
-
id: string;
|
|
769
|
-
title: string;
|
|
770
|
-
description: string;
|
|
771
|
-
suggestion: string;
|
|
772
|
-
/** Applied once per line. */
|
|
773
|
-
pattern: RegExp;
|
|
774
|
-
/** Applied against the full file content (use sparingly). */
|
|
775
|
-
multilinePattern?: RegExp;
|
|
776
|
-
severity: Severity;
|
|
777
|
-
category: string;
|
|
778
|
-
confidence: "high" | "medium" | "low";
|
|
779
|
-
/** File extensions this rule applies to. `["*"]` means every file. Empty array = path-pattern only. */
|
|
780
|
-
languages: string[];
|
|
781
|
-
/**
|
|
782
|
-
* Optional regex matched against the full relative file path.
|
|
783
|
-
* - If `languages` is non-empty: both extension AND path must match.
|
|
784
|
-
* - If `languages` is empty: only path is checked (used for extensionless files like Dockerfile).
|
|
785
|
-
*/
|
|
786
|
-
pathPattern?: RegExp;
|
|
787
|
-
/** Optional template for fixDiff — `$0` is replaced with the matched text. */
|
|
788
|
-
fixTemplate?: string;
|
|
789
|
-
/** Optional function that transforms the matched line into the fixed line. */
|
|
790
|
-
fixFn?: (line: string) => string;
|
|
791
|
-
/** Optional function that transforms a multiline match into the fixed text. Empty string = delete. */
|
|
792
|
-
multilineFixFn?: (matchedText: string) => string;
|
|
793
|
-
}
|
|
794
|
-
/**
|
|
795
|
-
* Scan a single file against all applicable rules.
|
|
796
|
-
*
|
|
797
|
-
* Returns findings filtered to changed line ranges only.
|
|
798
|
-
*/
|
|
799
|
-
declare function scanFile(relPath: string, content: string, rules: PatternRule[], changedRanges: [number, number][] | undefined): StaticFinding[];
|
|
800
|
-
|
|
801
|
-
declare const patternScannerRunner: ToolRunner;
|
|
802
|
-
|
|
803
|
-
type Ecosystem = "node" | "rust" | "python" | "solidity" | "go" | "unknown";
|
|
804
|
-
type Framework = "nextjs" | "react" | "express" | "nestjs" | "fastify" | "hardhat" | "foundry" | "anchor" | "truffle" | "django" | "flask" | "fastapi" | "actix" | "rocket" | "unknown";
|
|
805
|
-
interface ProjectFile {
|
|
806
|
-
path: string;
|
|
807
|
-
language: string;
|
|
808
|
-
sizeBytes: number;
|
|
809
|
-
lineCount: number;
|
|
810
|
-
}
|
|
811
|
-
interface ProjectSummary {
|
|
812
|
-
/** Repo name. */
|
|
813
|
-
name: string;
|
|
814
|
-
/** Short AI-generated description of what the project does. */
|
|
815
|
-
description: string;
|
|
816
|
-
/** Detected primary ecosystem. */
|
|
817
|
-
ecosystem: Ecosystem;
|
|
818
|
-
/** Detected framework. */
|
|
819
|
-
framework: Framework;
|
|
820
|
-
/** All detected ecosystems in the repo. */
|
|
821
|
-
ecosystems: Ecosystem[];
|
|
822
|
-
/** Total files. */
|
|
823
|
-
totalFiles: number;
|
|
824
|
-
/** Total lines of code. */
|
|
825
|
-
totalLines: number;
|
|
826
|
-
/** Files broken down by language. */
|
|
827
|
-
filesByLanguage: Record<string, number>;
|
|
828
|
-
/** Key entry points / main files. */
|
|
829
|
-
entryPoints: string[];
|
|
830
|
-
/** Config files found. */
|
|
831
|
-
configFiles: string[];
|
|
832
|
-
/** Has test directory/files. */
|
|
833
|
-
hasTests: boolean;
|
|
834
|
-
/** Has CI/CD config. */
|
|
835
|
-
hasCI: boolean;
|
|
836
|
-
/** All project files (for reference). */
|
|
837
|
-
files: ProjectFile[];
|
|
838
|
-
}
|
|
839
|
-
interface DepVulnerability {
|
|
840
|
-
id: string;
|
|
841
|
-
severity: Severity;
|
|
842
|
-
title: string;
|
|
843
|
-
url: string;
|
|
844
|
-
fixAvailable: boolean;
|
|
845
|
-
fixVersion?: string;
|
|
846
|
-
}
|
|
847
|
-
interface DepInfo {
|
|
848
|
-
name: string;
|
|
849
|
-
currentVersion: string;
|
|
850
|
-
latestVersion: string;
|
|
851
|
-
isOutdated: boolean;
|
|
852
|
-
isDeprecated: boolean;
|
|
853
|
-
/** Major version behind. */
|
|
854
|
-
majorsBehind: number;
|
|
855
|
-
vulnerabilities: DepVulnerability[];
|
|
856
|
-
/** Suggested replacement (e.g., moment → dayjs). */
|
|
857
|
-
replacement?: string;
|
|
858
|
-
}
|
|
859
|
-
interface DependencyReport {
|
|
860
|
-
ecosystem: Ecosystem;
|
|
861
|
-
totalDeps: number;
|
|
862
|
-
outdatedCount: number;
|
|
863
|
-
deprecatedCount: number;
|
|
864
|
-
vulnerableCount: number;
|
|
865
|
-
deps: DepInfo[];
|
|
866
|
-
}
|
|
867
|
-
type IssueCategory = "security" | "deprecated-pattern" | "dead-code" | "anti-pattern" | "performance" | "type-safety" | "error-handling" | "modernization";
|
|
868
|
-
interface AuditIssue {
|
|
869
|
-
category: IssueCategory;
|
|
870
|
-
severity: Severity;
|
|
871
|
-
title: string;
|
|
872
|
-
description: string;
|
|
873
|
-
filePath: string;
|
|
874
|
-
startLine: number;
|
|
875
|
-
endLine: number;
|
|
876
|
-
codeSnippet: string;
|
|
877
|
-
/** Source: "static" (tool) or "ai" (LLM). */
|
|
878
|
-
source: "static" | "ai";
|
|
879
|
-
tool?: string;
|
|
880
|
-
}
|
|
881
|
-
interface AuditReport {
|
|
882
|
-
issues: AuditIssue[];
|
|
883
|
-
/** Which static tools ran. */
|
|
884
|
-
toolsRan: string[];
|
|
885
|
-
/** Summary stats. */
|
|
886
|
-
stats: {
|
|
887
|
-
totalIssues: number;
|
|
888
|
-
bySeverity: Record<string, number>;
|
|
889
|
-
byCategory: Record<string, number>;
|
|
890
|
-
};
|
|
891
|
-
}
|
|
892
|
-
type UpgradeType = "dependency-update" | "security-fix" | "bug-fix" | "modernization" | "performance" | "code-quality" | "deprecation-fix";
|
|
893
|
-
interface UpgradeItem {
|
|
894
|
-
id: string;
|
|
895
|
-
type: UpgradeType;
|
|
896
|
-
priority: number;
|
|
897
|
-
severity: Severity;
|
|
898
|
-
title: string;
|
|
899
|
-
description: string;
|
|
900
|
-
/** Files that need to change. */
|
|
901
|
-
affectedFiles: string[];
|
|
902
|
-
/** Risk level of this change. */
|
|
903
|
-
risk: "low" | "medium" | "high";
|
|
904
|
-
/** Estimated effort. */
|
|
905
|
-
effort: "trivial" | "small" | "medium" | "large";
|
|
906
|
-
/** Whether this can be auto-fixed. */
|
|
907
|
-
autoFixable: boolean;
|
|
908
|
-
}
|
|
909
|
-
interface UpgradePlan {
|
|
910
|
-
/** AI-generated summary of the overall upgrade strategy. */
|
|
911
|
-
summary: string;
|
|
912
|
-
/** Total items in the plan. */
|
|
913
|
-
totalItems: number;
|
|
914
|
-
/** Items grouped and prioritized. */
|
|
915
|
-
items: UpgradeItem[];
|
|
916
|
-
/** Items that can be auto-fixed. */
|
|
917
|
-
autoFixableCount: number;
|
|
918
|
-
}
|
|
919
|
-
interface FileTransform {
|
|
920
|
-
/** Path to the file. */
|
|
921
|
-
filePath: string;
|
|
922
|
-
/** Original content. */
|
|
923
|
-
originalContent: string;
|
|
924
|
-
/** New content after transform. */
|
|
925
|
-
newContent: string;
|
|
926
|
-
/** Unified diff. */
|
|
927
|
-
diff: string;
|
|
928
|
-
/** Which upgrade items this addresses. */
|
|
929
|
-
upgradeItemIds: string[];
|
|
930
|
-
/** Explanation of changes. */
|
|
931
|
-
explanation: string;
|
|
932
|
-
}
|
|
933
|
-
interface TransformResult {
|
|
934
|
-
transforms: FileTransform[];
|
|
935
|
-
/** Files to delete. */
|
|
936
|
-
filesToDelete: string[];
|
|
937
|
-
/** New files to create. */
|
|
938
|
-
newFiles: {
|
|
939
|
-
path: string;
|
|
940
|
-
content: string;
|
|
941
|
-
}[];
|
|
942
|
-
/** Package.json changes (deps to update/remove/add). */
|
|
943
|
-
packageChanges?: {
|
|
944
|
-
update: Record<string, string>;
|
|
945
|
-
remove: string[];
|
|
946
|
-
add: Record<string, string>;
|
|
947
|
-
};
|
|
948
|
-
}
|
|
949
|
-
interface UpgradeResult {
|
|
950
|
-
project: ProjectSummary;
|
|
951
|
-
dependencies: DependencyReport;
|
|
952
|
-
audit: AuditReport;
|
|
953
|
-
plan: UpgradePlan;
|
|
954
|
-
transforms: TransformResult;
|
|
955
|
-
/** Total time in ms. */
|
|
956
|
-
duration: number;
|
|
957
|
-
}
|
|
958
|
-
interface UpgradeOptions {
|
|
959
|
-
/** GitHub repo URL or local path. */
|
|
960
|
-
repoUrl: string;
|
|
961
|
-
/** Branch to analyze (default: main/master). */
|
|
962
|
-
branch?: string;
|
|
963
|
-
/** Pluggable AI provider. Takes precedence over apiKey. */
|
|
964
|
-
provider?: AIProvider;
|
|
965
|
-
/** AI API key for intelligent analysis. Optional — static-only without it. */
|
|
966
|
-
apiKey?: string;
|
|
967
|
-
/** AI model to use. */
|
|
968
|
-
model?: string;
|
|
969
|
-
/** Skip AI analysis entirely (static tools only). */
|
|
970
|
-
staticOnly?: boolean;
|
|
971
|
-
/** Skip code transforms (analysis + plan only). */
|
|
972
|
-
planOnly?: boolean;
|
|
973
|
-
/** Max files to transform (to control cost). */
|
|
974
|
-
maxTransformFiles?: number;
|
|
975
|
-
}
|
|
976
|
-
|
|
977
|
-
/**
|
|
978
|
-
* Upgrade pipeline — main orchestrator.
|
|
979
|
-
*
|
|
980
|
-
* Takes a repo URL, runs the full upgrade pipeline:
|
|
981
|
-
* ingest → deps → audit → plan → transform
|
|
982
|
-
*/
|
|
983
|
-
|
|
984
|
-
/**
|
|
985
|
-
* Run the full upgrade pipeline on a repository.
|
|
986
|
-
*/
|
|
987
|
-
declare function runUpgrade(options: UpgradeOptions): Promise<UpgradeResult>;
|
|
988
|
-
|
|
989
|
-
/**
|
|
990
|
-
* Repo ingestion and project understanding.
|
|
991
|
-
*
|
|
992
|
-
* Clones a repo, walks the file tree, detects ecosystem/framework,
|
|
993
|
-
* and builds a structured summary of the project.
|
|
994
|
-
*/
|
|
995
|
-
|
|
996
|
-
/**
|
|
997
|
-
* Clone a repo and build a project summary.
|
|
998
|
-
* Returns the cloned path and project summary.
|
|
999
|
-
*/
|
|
1000
|
-
declare function ingestRepo(repoUrl: string, branch?: string): Promise<{
|
|
1001
|
-
repoPath: string;
|
|
1002
|
-
summary: ProjectSummary;
|
|
1003
|
-
}>;
|
|
1004
|
-
/**
|
|
1005
|
-
* Read a file's content from the cloned repo.
|
|
1006
|
-
*/
|
|
1007
|
-
declare function readRepoFile(repoPath: string, filePath: string): Promise<string>;
|
|
1008
|
-
/**
|
|
1009
|
-
* Read multiple files (up to maxSize total).
|
|
1010
|
-
*/
|
|
1011
|
-
declare function readRepoFiles(repoPath: string, filePaths: string[], maxTotalSize?: number): Promise<Record<string, string>>;
|
|
1012
|
-
|
|
1013
|
-
/**
|
|
1014
|
-
* Dependency analyzer.
|
|
1015
|
-
*
|
|
1016
|
-
* Checks for outdated, deprecated, and vulnerable dependencies
|
|
1017
|
-
* across Node.js, Rust, and Python ecosystems.
|
|
1018
|
-
*/
|
|
1019
|
-
|
|
1020
|
-
/**
|
|
1021
|
-
* Analyze all dependencies in a repo across detected ecosystems.
|
|
1022
|
-
*/
|
|
1023
|
-
declare function analyzeDependencies(repoPath: string, ecosystems: Ecosystem[]): Promise<DependencyReport>;
|
|
1024
|
-
|
|
1025
|
-
/**
|
|
1026
|
-
* Full codebase auditor.
|
|
1027
|
-
*
|
|
1028
|
-
* Runs static analysis tools on the entire repo (not just diffs)
|
|
1029
|
-
* and produces a comprehensive audit report.
|
|
1030
|
-
*/
|
|
1031
|
-
|
|
1032
|
-
/**
|
|
1033
|
-
* Run a full audit on the entire codebase.
|
|
1034
|
-
*/
|
|
1035
|
-
declare function auditCodebase(repoPath: string, summary: ProjectSummary): Promise<AuditReport>;
|
|
1036
|
-
|
|
1037
|
-
/**
|
|
1038
|
-
* AI-powered upgrade planner.
|
|
1039
|
-
*
|
|
1040
|
-
* Takes the project summary, dependency report, and audit results,
|
|
1041
|
-
* and generates a prioritized upgrade plan using AI.
|
|
1042
|
-
*/
|
|
1043
|
-
|
|
1044
|
-
/**
|
|
1045
|
-
* Generate an upgrade plan using AI.
|
|
1046
|
-
*
|
|
1047
|
-
* Accepts either an AIProvider or a legacy apiKey string.
|
|
1048
|
-
*/
|
|
1049
|
-
declare function generateUpgradePlan(summary: ProjectSummary, deps: DependencyReport, audit: AuditReport, apiKeyOrProvider: string | AIProvider, model?: string): Promise<UpgradePlan>;
|
|
1050
|
-
/**
|
|
1051
|
-
* Generate a basic plan without AI (from static analysis + deps only).
|
|
1052
|
-
*/
|
|
1053
|
-
declare function generateFallbackPlan(deps: DependencyReport, audit: AuditReport): UpgradePlan;
|
|
1054
|
-
|
|
1055
|
-
/**
|
|
1056
|
-
* AI-powered code transformer.
|
|
1057
|
-
*
|
|
1058
|
-
* Takes the upgrade plan and original file contents,
|
|
1059
|
-
* and generates improved versions of each file.
|
|
1060
|
-
*/
|
|
1061
|
-
|
|
1062
|
-
/**
|
|
1063
|
-
* Transform files according to the upgrade plan.
|
|
1064
|
-
*
|
|
1065
|
-
* Accepts either an AIProvider or a legacy apiKey string.
|
|
1066
|
-
*/
|
|
1067
|
-
declare function transformFiles(repoPath: string, plan: UpgradePlan, summary: ProjectSummary, deps: DependencyReport, apiKeyOrProvider: string | AIProvider, model?: string, maxFiles?: number): Promise<TransformResult>;
|
|
1068
|
-
|
|
1069
|
-
/**
|
|
1070
|
-
* Fix applicator.
|
|
1071
|
-
*
|
|
1072
|
-
* Takes review findings with fixDiff and original file contents, applies the
|
|
1073
|
-
* fixes, and returns the updated content for each file. Applies bottom-to-top
|
|
1074
|
-
* to preserve line numbers.
|
|
1075
|
-
*/
|
|
1076
|
-
|
|
1077
|
-
interface FileFixInput {
|
|
1078
|
-
/** Path to the file (relative to repo root). */
|
|
1079
|
-
filePath: string;
|
|
1080
|
-
/** Original file content from GitHub. */
|
|
1081
|
-
originalContent: string;
|
|
1082
|
-
}
|
|
1083
|
-
interface FileFixResult {
|
|
1084
|
-
filePath: string;
|
|
1085
|
-
newContent: string;
|
|
1086
|
-
appliedFindings: Finding[];
|
|
1087
|
-
}
|
|
1088
|
-
interface ApplyFixesResult {
|
|
1089
|
-
/** Successfully fixed files. */
|
|
1090
|
-
files: FileFixResult[];
|
|
1091
|
-
/** Findings that couldn't be applied. */
|
|
1092
|
-
skipped: Array<{
|
|
1093
|
-
finding: Finding;
|
|
1094
|
-
reason: string;
|
|
1095
|
-
}>;
|
|
1096
|
-
}
|
|
1097
|
-
/**
|
|
1098
|
-
* Check if the fixed content is syntactically valid JS/TS.
|
|
1099
|
-
* Returns null if valid (or non-JS/TS file), or an error message if invalid.
|
|
1100
|
-
*/
|
|
1101
|
-
declare function validateFixedSyntax(filePath: string, content: string): string | null;
|
|
1102
|
-
/**
|
|
1103
|
-
* Apply auto-fixes from findings to original file contents.
|
|
1104
|
-
*
|
|
1105
|
-
* Processes all findings that have a non-empty fixDiff.
|
|
1106
|
-
*
|
|
1107
|
-
* Applies fixes bottom-to-top within each file to preserve line numbers.
|
|
1108
|
-
* If any fix in a file fails to apply, all fixes for that file are skipped
|
|
1109
|
-
* (all-or-nothing per file).
|
|
1110
|
-
*/
|
|
1111
|
-
declare function applyFixes(findings: Finding[], fileInputs: FileFixInput[]): ApplyFixesResult;
|
|
1112
|
-
|
|
1113
|
-
/**
|
|
1114
|
-
* Full-file rewrite module.
|
|
1115
|
-
*
|
|
1116
|
-
* Takes a source file together with its security/quality findings and asks
|
|
1117
|
-
* the AI provider to rewrite the entire file, fixing every reported issue
|
|
1118
|
-
* while preserving the original purpose and public API surface.
|
|
1119
|
-
*/
|
|
1120
|
-
|
|
1121
|
-
interface RewriteResult {
|
|
1122
|
-
filePath: string;
|
|
1123
|
-
originalContent: string;
|
|
1124
|
-
rewrittenContent: string;
|
|
1125
|
-
changesSummary: string[];
|
|
1126
|
-
}
|
|
1127
|
-
interface RewriteFileParams {
|
|
1128
|
-
provider: AIProvider;
|
|
1129
|
-
filePath: string;
|
|
1130
|
-
content: string;
|
|
1131
|
-
findings: Finding[];
|
|
1132
|
-
}
|
|
1133
|
-
declare function rewriteFile(params: RewriteFileParams): Promise<RewriteResult>;
|
|
1134
|
-
declare function rewriteFiles(params: Omit<RewriteFileParams, "filePath" | "content" | "findings"> & {
|
|
1135
|
-
files: Array<{
|
|
1136
|
-
filePath: string;
|
|
1137
|
-
content: string;
|
|
1138
|
-
findings: Finding[];
|
|
1139
|
-
}>;
|
|
1140
|
-
}): Promise<RewriteResult[]>;
|
|
1141
|
-
|
|
1142
|
-
/**
|
|
1143
|
-
* Config loader — reads and validates `.elytra.yml` configuration files.
|
|
1144
|
-
* Uses Zod for schema validation with helpful error messages.
|
|
1145
|
-
*/
|
|
1146
|
-
interface ElytraConfig {
|
|
1147
|
-
/** Which rulesets to enable: "general", "quality", "attack", "solidity" */
|
|
1148
|
-
rulesets: string[];
|
|
1149
|
-
/** Minimum severity to report: "critical", "high", "medium", "low", "info" */
|
|
1150
|
-
severity_threshold: string;
|
|
1151
|
-
/** Glob patterns of files/dirs to ignore */
|
|
1152
|
-
ignore: string[];
|
|
1153
|
-
/** Rule IDs to disable: ["cp-qual-todo-fixme", "cp-sec-eval"] */
|
|
1154
|
-
disable: string[];
|
|
1155
|
-
}
|
|
1156
|
-
/**
|
|
1157
|
-
* Load `.elytra.yml` from the given directory.
|
|
1158
|
-
* Returns the parsed config merged with defaults, or null if no config file exists.
|
|
1159
|
-
*/
|
|
1160
|
-
declare function loadConfig(dir: string): ElytraConfig | null;
|
|
1161
|
-
/**
|
|
1162
|
-
* Filter findings by config — removes disabled rules and below-threshold severities.
|
|
1163
|
-
*/
|
|
1164
|
-
declare function filterByConfig<T extends {
|
|
1165
|
-
ruleId: string;
|
|
1166
|
-
severity: string;
|
|
1167
|
-
}>(findings: T[], config: ElytraConfig): T[];
|
|
1168
|
-
|
|
1169
|
-
/**
|
|
1170
|
-
* Minimal structured logger for @elytrasec/engine.
|
|
1171
|
-
*
|
|
1172
|
-
* Respects ELYTRA_LOG_LEVEL env var (debug | info | warn | error | silent).
|
|
1173
|
-
* Writes to stderr so stdout stays clean for CLI/CI output.
|
|
1174
|
-
*/
|
|
1175
|
-
declare const logger: {
|
|
1176
|
-
debug(msg: string): void;
|
|
1177
|
-
info(msg: string): void;
|
|
1178
|
-
warn(msg: string): void;
|
|
1179
|
-
error(msg: string): void;
|
|
1180
|
-
};
|
|
1181
|
-
|
|
1182
|
-
interface HardenSuggestion {
|
|
1183
|
-
id: string;
|
|
1184
|
-
title: string;
|
|
1185
|
-
description: string;
|
|
1186
|
-
/** File where the control should be added (or "project" for project-wide) */
|
|
1187
|
-
filePath: string;
|
|
1188
|
-
/** What the user should add */
|
|
1189
|
-
suggestedCode: string;
|
|
1190
|
-
/** Can --apply auto-fix this? */
|
|
1191
|
-
autoFixable: boolean;
|
|
1192
|
-
severity: "high" | "medium" | "low";
|
|
1193
|
-
}
|
|
1194
|
-
interface HardenResult {
|
|
1195
|
-
suggestions: HardenSuggestion[];
|
|
1196
|
-
projectPath: string;
|
|
1197
|
-
frameworksDetected: string[];
|
|
1198
|
-
}
|
|
1199
|
-
declare function applyHardenFix(projectPath: string, suggestion: HardenSuggestion): boolean;
|
|
1200
|
-
declare function runHarden(projectPath: string): HardenResult;
|
|
1201
|
-
|
|
1202
|
-
/**
|
|
1203
|
-
* Main review orchestrator — Hybrid Static + AI Pipeline.
|
|
1204
|
-
*
|
|
1205
|
-
* Pipeline:
|
|
1206
|
-
* 1. Parse the unified diff into structured data
|
|
1207
|
-
* 2. Classify each file by language and blockchain chain
|
|
1208
|
-
* 3. Run static analysis tools (slither, semgrep, gitleaks) in parallel
|
|
1209
|
-
* 4. Select the relevant review rules
|
|
1210
|
-
* 5. Build system prompt with static findings as context
|
|
1211
|
-
* 6. Chunk the diff to fit within AI context windows
|
|
1212
|
-
* 7. Send each chunk to the AI client for analysis
|
|
1213
|
-
* 8. Merge static + AI findings, deduplicate, sort by severity
|
|
1214
|
-
*/
|
|
1215
|
-
|
|
1216
|
-
interface AnalyzeParams {
|
|
1217
|
-
/** Raw unified diff string. */
|
|
1218
|
-
diff: string;
|
|
1219
|
-
/** Ruleset categories to enable (e.g. ["general", "solidity"]). */
|
|
1220
|
-
enabledRulesets: string[];
|
|
1221
|
-
/** Explicit chain targets to include rules for. */
|
|
1222
|
-
targetChains?: string[];
|
|
1223
|
-
/**
|
|
1224
|
-
* Pluggable AI provider. Takes precedence over `apiKey`.
|
|
1225
|
-
* Use `createProvider()` to build one from env vars.
|
|
1226
|
-
*/
|
|
1227
|
-
provider?: AIProvider;
|
|
1228
|
-
/** Anthropic API key. If not provided (and no provider), only static analysis runs. */
|
|
1229
|
-
apiKey?: string;
|
|
1230
|
-
/** Max tokens per chunk sent to the AI model. Defaults to 12000. */
|
|
1231
|
-
maxChunkTokens?: number;
|
|
1232
|
-
/** Claude model to use. */
|
|
1233
|
-
model?: string;
|
|
1234
|
-
/**
|
|
1235
|
-
* Absolute path to the checked-out repo for static analysis.
|
|
1236
|
-
* If not provided, static analysis is skipped and only AI review runs.
|
|
1237
|
-
*/
|
|
1238
|
-
repoPath?: string;
|
|
1239
|
-
/** Whether to skip AI analysis (static-only mode). */
|
|
1240
|
-
staticOnly?: boolean;
|
|
1241
|
-
/** Whether to skip static analysis (AI-only mode, legacy behavior). */
|
|
1242
|
-
skipStatic?: boolean;
|
|
1243
|
-
/** AI concurrency limit. Defaults to AI_CONCURRENCY env var or 3. */
|
|
1244
|
-
aiConcurrency?: number;
|
|
1245
|
-
/**
|
|
1246
|
-
* Run agentic PoC generation on critical/high Solidity findings.
|
|
1247
|
-
* Requires an AI provider. If forge is installed, attempts to confirm
|
|
1248
|
-
* exploitability by running the generated test against Anvil.
|
|
1249
|
-
*/
|
|
1250
|
-
runPoc?: boolean;
|
|
1251
|
-
/** Optional RPC URL for forked Anvil PoC execution (e.g. Base/mainnet). */
|
|
1252
|
-
pocRpcUrl?: string;
|
|
1253
|
-
}
|
|
1254
|
-
/**
|
|
1255
|
-
* Deduplicate findings by (filePath, startLine, ruleId).
|
|
1256
|
-
* Generic — works for both Finding and StaticFinding.
|
|
1257
|
-
*/
|
|
1258
|
-
declare function dedupeFindings<T extends {
|
|
1259
|
-
filePath: string;
|
|
1260
|
-
startLine: number;
|
|
1261
|
-
ruleId: string;
|
|
1262
|
-
severity: string;
|
|
1263
|
-
}>(findings: T[]): T[];
|
|
1264
|
-
declare function analyze(params: AnalyzeParams): Promise<ReviewResult>;
|
|
1265
|
-
|
|
1266
|
-
/**
|
|
1267
|
-
* Full-codebase scanner.
|
|
1268
|
-
*
|
|
1269
|
-
* Scans every source file in a project instead of reviewing a diff.
|
|
1270
|
-
* Reuses static analysis tools and AI review from the existing engine.
|
|
1271
|
-
*
|
|
1272
|
-
* Pipeline:
|
|
1273
|
-
* 1. Discover all source files (git ls-files or directory walk)
|
|
1274
|
-
* 2. Classify each file by language/chain
|
|
1275
|
-
* 3. Run static analysis tools on all files (no line-range filtering)
|
|
1276
|
-
* 4. Optionally send files to AI for deep review (chunked by token budget)
|
|
1277
|
-
* 5. Merge, dedupe, score, return ReviewResult
|
|
1278
|
-
*/
|
|
1279
|
-
|
|
1280
|
-
interface FullScanParams {
|
|
1281
|
-
/** Path to the project root to scan. */
|
|
1282
|
-
targetPath: string;
|
|
1283
|
-
/** Ruleset categories to enable. */
|
|
1284
|
-
enabledRulesets?: string[];
|
|
1285
|
-
/** Pluggable AI provider. */
|
|
1286
|
-
provider?: AIProvider;
|
|
1287
|
-
/** API key (creates Anthropic provider if no provider given). */
|
|
1288
|
-
apiKey?: string;
|
|
1289
|
-
/** Model override. */
|
|
1290
|
-
model?: string;
|
|
1291
|
-
/** Skip AI analysis, run static tools only. */
|
|
1292
|
-
staticOnly?: boolean;
|
|
1293
|
-
/** Max files to scan. Default: 500. */
|
|
1294
|
-
maxFiles?: number;
|
|
1295
|
-
/** Max individual file size in KB. Default: 100. */
|
|
1296
|
-
maxFileSizeKB?: number;
|
|
1297
|
-
/** Max tokens per AI chunk. Default: 12000. */
|
|
1298
|
-
maxChunkTokens?: number;
|
|
1299
|
-
/** AI concurrency limit. Defaults to AI_CONCURRENCY env var or 3. */
|
|
1300
|
-
aiConcurrency?: number;
|
|
1301
|
-
}
|
|
1302
|
-
declare function analyzeFullScan(params: FullScanParams): Promise<ReviewResult>;
|
|
1303
|
-
|
|
1304
|
-
/**
|
|
1305
|
-
* File discovery for full-codebase scanning.
|
|
1306
|
-
*
|
|
1307
|
-
* Two strategies:
|
|
1308
|
-
* 1. Git repo: use `git ls-files` (fast, respects .gitignore)
|
|
1309
|
-
* 2. Non-git: walk directories, skip common non-source dirs
|
|
1310
|
-
*/
|
|
1311
|
-
interface DiscoveredFile {
|
|
1312
|
-
relativePath: string;
|
|
1313
|
-
absolutePath: string;
|
|
1314
|
-
sizeBytes: number;
|
|
1315
|
-
language: string;
|
|
1316
|
-
}
|
|
1317
|
-
interface DiscoverOptions {
|
|
1318
|
-
maxFiles?: number;
|
|
1319
|
-
maxFileSizeKB?: number;
|
|
1320
|
-
/** Glob patterns to ignore (from .elytra.yml) */
|
|
1321
|
-
ignore?: string[];
|
|
1322
|
-
}
|
|
1323
|
-
/**
|
|
1324
|
-
* Discover all source files in a project.
|
|
1325
|
-
*
|
|
1326
|
-
* Uses `git ls-files` if available (fast, respects .gitignore), otherwise
|
|
1327
|
-
* walks the directory tree skipping common non-source directories.
|
|
1328
|
-
*/
|
|
1329
|
-
declare function discoverFiles(targetPath: string, opts?: DiscoverOptions): DiscoveredFile[];
|
|
1330
|
-
|
|
1331
|
-
/**
|
|
1332
|
-
* Agentic PoC generator.
|
|
1333
|
-
*
|
|
1334
|
-
* Given a Finding from our scanner and the vulnerable contract source,
|
|
1335
|
-
* asks Claude to write a Foundry exploit test, then tries to run it
|
|
1336
|
-
* against an Anvil fork to confirm the vulnerability is actually exploitable.
|
|
1337
|
-
*
|
|
1338
|
-
* Returns a PocResult indicating whether the finding was confirmed, along
|
|
1339
|
-
* with the generated test and execution output.
|
|
1340
|
-
*
|
|
1341
|
-
* Degrades gracefully when forge/anvil are not installed — the PoC code
|
|
1342
|
-
* is still generated, status is "generated" rather than "confirmed".
|
|
1343
|
-
*/
|
|
1344
|
-
|
|
1345
|
-
type PocStatus = "confirmed" | "not-exploitable" | "generated" | "error";
|
|
1346
|
-
interface PocResult {
|
|
1347
|
-
status: PocStatus;
|
|
1348
|
-
pocCode: string;
|
|
1349
|
-
output: string;
|
|
1350
|
-
rpcUrl?: string;
|
|
1351
|
-
}
|
|
1352
|
-
declare class PocGenerator {
|
|
1353
|
-
private provider;
|
|
1354
|
-
constructor(provider: AIProvider);
|
|
1355
|
-
generate(finding: Finding, contractSource: string, rpcUrl?: string): Promise<PocResult>;
|
|
1356
|
-
}
|
|
1357
|
-
|
|
1358
|
-
export { AIClient, type AICompleteParams, type AICompleteResult, type AIMessage, type AIProvider, type AnalyzeCodeParams, type AnalyzeFileParams, type AnalyzeParams, AnthropicProvider, type ApplyFixesResult, type AuditIssue, type AuditReport, CWE_OWASP_MAP, type Chain, type ChangeType, type CreateProviderOptions, type CweOwaspEntry, type DepInfo, type DepVulnerability, type DependencyReport, type DiffChange, type DiffChunk, type DiffFile, type DiffHunk, type DiscoverOptions, type DiscoveredFile, type Ecosystem, type ElytraConfig, type FileClassification, type FileFixInput, type FileFixResult, type FileStatus, type FileTransform, type Finding, FindingSchema, type Framework, type FullScanParams, type GitHubReviewComment, type HardenResult, type HardenSuggestion, type IssueCategory, type Language, MockProvider, OllamaProvider, OpenAIProvider, type ParsedDiff, type PatternRule, PocGenerator, type PocResult, type PocStatus, type ProjectFile, type ProjectSummary, type ReportOptions, type ReviewResult, ReviewResultSchema, type RewriteResult, type Rule, type SecurityScore, type SecurityScoreOutput, SecurityScoreSchema, type Severity, SeveritySchema, type StaticAnalysisOptions, type StaticAnalysisResult, type StaticFinding, type ToolRunner, type ToolRunnerOptions, type TransformResult, type UpgradeItem, type UpgradeOptions, type UpgradePlan, type UpgradeResult, type UpgradeType, ALL_RULES as _ALL_RULES, scanFile as _scanFile, analyze, analyzeDependencies, analyzeFullScan, apiRules, applyFixes, applyHardenFix, auditCodebase, authRules, bestPracticeRules, classifyFile, complexityRules, computeScore, createProvider, deadCodeRules, dedupeFindings, discoverFiles, filterByConfig, formatAsReviewComments, formatStaticFindingsForAI, gasRules, generalRules, generateFallbackPlan, generateMarkdownReport, generateUpgradePlan, getAllRules, getCweOwasp, getRulesForChains, getSystemPrompt, gitleaksRunner, ingestRepo, injectionRules, loadConfig, logger, namingRules, parseDiff, patternScannerRunner, readRepoFile, readRepoFiles, reconRules, rewriteFile, rewriteFiles, runHarden, runStaticAnalysis, runUpgrade, semgrepRunner, slitherRunner, solidityRules, splitIntoChunks, transformFiles, validateFixedSyntax };
|