@pensar/apex 0.0.111 → 0.0.112
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/README.md +2 -3
- package/bin/pensar.js +31 -276
- package/build/agent-5qdmmchx.js +206 -0
- package/build/agent-s2z0dasf.js +16 -0
- package/build/auth-jvq72ekc.js +263 -0
- package/build/authentication-nya4td5k.js +310 -0
- package/build/blackboxAgent-qa9ze2hn.js +17 -0
- package/build/blackboxPentest-85hwznet.js +41 -0
- package/build/cli-15vxn9zj.js +1358 -0
- package/build/cli-2ckm5es2.js +50 -0
- package/build/cli-49cd9yfk.js +4475 -0
- package/build/cli-5d6cs4dq.js +53 -0
- package/build/cli-6gtnyaqf.js +109 -0
- package/build/cli-7ckctq7a.js +45 -0
- package/build/cli-8rxa073f.js +104 -0
- package/build/cli-bp6d08sg.js +110 -0
- package/build/cli-e20q3hqz.js +307 -0
- package/build/cli-f9shhcxf.js +1498 -0
- package/build/cli-hmrzx8am.js +507 -0
- package/build/cli-j66pect7.js +202 -0
- package/build/cli-jb0gcnrs.js +60 -0
- package/build/cli-jh38b6zv.js +1074 -0
- package/build/cli-kqtgcdzn.js +54784 -0
- package/build/cli-r8r90gka.js +96700 -0
- package/build/cli-va4y0089.js +395 -0
- package/build/cli-w04ggbe4.js +104 -0
- package/build/cli-x1msjf55.js +103 -0
- package/build/cli-yj3dy0vg.js +180 -0
- package/build/cli.js +509 -0
- package/build/doctor-b7612pzw.js +117 -0
- package/build/fixes-1r6v7kh2.js +49 -0
- package/build/index-5ke2yd32.js +17 -0
- package/build/index-9ze42wn7.js +68412 -0
- package/build/index-rd11fk7h.js +1257 -0
- package/build/index-tke6896d.js +1097 -0
- package/build/index-vwvh1rdw.js +535 -0
- package/build/issues-kx721wja.js +94 -0
- package/build/logs-hav7d0nm.js +77 -0
- package/build/main-2483qzbq.js +397 -0
- package/build/multipart-parser-r38qdp5v.js +350 -0
- package/build/pentest-zzebnfa0.js +25 -0
- package/build/pentests-s9fwd71b.js +70 -0
- package/build/projects-tr719twv.js +35 -0
- package/build/targetedPentest-w2c85whf.js +32 -0
- package/build/token-6x6aavpc.js +58 -0
- package/build/token-util-na95bqjj.js +6 -0
- package/build/uninstall-2j0pymb0.js +231 -0
- package/build/utils-jky0th19.js +107 -0
- package/package.json +3 -4
- package/build/auth.js +0 -625
- package/build/highlights-eq9cgrbb.scm +0 -604
- package/build/highlights-ghv9g403.scm +0 -205
- package/build/highlights-hk7bwhj4.scm +0 -284
- package/build/highlights-r812a2qc.scm +0 -150
- package/build/highlights-x6tmsnaa.scm +0 -115
- package/build/index.js +0 -292069
- package/build/injections-73j83es3.scm +0 -27
- package/build/tree-sitter-javascript-nd0q4pe9.wasm +0 -0
- package/build/tree-sitter-markdown-411r6y9b.wasm +0 -0
- package/build/tree-sitter-markdown_inline-j5349f42.wasm +0 -0
- package/build/tree-sitter-typescript-zxjzwt75.wasm +0 -0
- package/build/tree-sitter-zig-e78zbjpm.wasm +0 -0
- package/src/core/installation/index.ts +0 -223
- package/src/core/installation/installation.test.ts +0 -454
package/README.md
CHANGED
|
@@ -20,12 +20,10 @@ Want to run from the cloud or integrate it with your CI/CD? See <a href="https:/
|
|
|
20
20
|
<img src="screenshot.png" alt="Pensar Apex Screenshot" width="800">
|
|
21
21
|
</p> -->
|
|
22
22
|
|
|
23
|
-
|
|
24
23
|
## Use Cases
|
|
25
24
|
|
|
26
25
|
Apex enables both developers and security professionals to run autonomous and assisted penetration testing directly from the terminal.
|
|
27
26
|
|
|
28
|
-
|
|
29
27
|
### Developers: Run a Pentest in Minutes
|
|
30
28
|
|
|
31
29
|
Apex makes it easy for developers to run a real penetration test without needing deep offensive security expertise.
|
|
@@ -39,6 +37,7 @@ This allows teams to quickly identify security issues before they reach producti
|
|
|
39
37
|
```
|
|
40
38
|
|
|
41
39
|
Examples:
|
|
40
|
+
|
|
42
41
|
- Test a staging environment before deploying
|
|
43
42
|
- Scan a newly launched domain or API
|
|
44
43
|
- Run quick security checks during development
|
|
@@ -54,12 +53,12 @@ Security professionals can use Apex as an **agentic offensive security harness**
|
|
|
54
53
|
|
|
55
54
|
The `/operator` mode allows engineers to work interactively with the Offensive Security Agent, guiding investigations and chaining tools dynamically.
|
|
56
55
|
|
|
57
|
-
|
|
58
56
|
```bash
|
|
59
57
|
/operator
|
|
60
58
|
```
|
|
61
59
|
|
|
62
60
|
Examples:
|
|
61
|
+
|
|
63
62
|
- Deep investigation of suspicious endpoints
|
|
64
63
|
- Manual exploitation of discovered vulnerabilities
|
|
65
64
|
- Tool orchestration across recon and exploitation phases
|
package/bin/pensar.js
CHANGED
|
@@ -1,282 +1,37 @@
|
|
|
1
|
-
#!/usr/bin/env
|
|
1
|
+
#!/usr/bin/env node
|
|
2
2
|
|
|
3
|
-
/**
|
|
4
|
-
* Pensar - AI-Powered Penetration Testing CLI
|
|
5
|
-
*
|
|
6
|
-
* This is the main entry point for the Pensar CLI tool.
|
|
7
|
-
* It supports:
|
|
8
|
-
* - Default (no args): Launches the OpenTUI-based terminal interface
|
|
9
|
-
* - benchmark command: Runs the benchmark CLI
|
|
10
|
-
*/
|
|
11
|
-
|
|
12
|
-
import { fileURLToPath } from "url";
|
|
13
3
|
import { dirname, join } from "path";
|
|
14
|
-
|
|
15
|
-
// Import package.json directly so Bun can embed it at compile time
|
|
16
|
-
import packageJson from "../package.json";
|
|
17
|
-
import { getCurrentVersion, upgrade } from "../src/core/installation/index.ts";
|
|
4
|
+
import { fileURLToPath } from "url";
|
|
18
5
|
|
|
19
6
|
const __filename = fileURLToPath(import.meta.url);
|
|
20
7
|
const __dirname = dirname(__filename);
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
}
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
process.argv = [process.argv[0], quicktestPath, ...args.slice(1)];
|
|
48
|
-
|
|
49
|
-
// Import and run quicktest
|
|
50
|
-
await import(quicktestPath);
|
|
51
|
-
} else if (command === "pentest") {
|
|
52
|
-
// Run pentest CLI
|
|
53
|
-
const pentestPath = join(__dirname, "..", "build", "pentest.js");
|
|
54
|
-
|
|
55
|
-
// Remove "pentest" from args and pass the rest to pentest script
|
|
56
|
-
process.argv = [process.argv[0], pentestPath, ...args.slice(1)];
|
|
57
|
-
|
|
58
|
-
// Import and run pentest
|
|
59
|
-
await import(pentestPath);
|
|
60
|
-
} else if (command === "auth") {
|
|
61
|
-
// Run auth CLI
|
|
62
|
-
const authPath = join(__dirname, "..", "build", "auth.js");
|
|
63
|
-
|
|
64
|
-
// Remove "auth" from args and pass the rest to auth script
|
|
65
|
-
process.argv = [process.argv[0], authPath, ...args.slice(1)];
|
|
66
|
-
|
|
67
|
-
// Import and run auth
|
|
68
|
-
await import(authPath);
|
|
69
|
-
} else if (command === "uninstall") {
|
|
70
|
-
// Run uninstall CLI
|
|
71
|
-
const uninstallPath = join(__dirname, "..", "build", "uninstall.js");
|
|
72
|
-
|
|
73
|
-
process.argv = [process.argv[0], uninstallPath, ...args.slice(1)];
|
|
74
|
-
|
|
75
|
-
await import(uninstallPath);
|
|
76
|
-
} else if (command === "projects") {
|
|
77
|
-
const p = join(__dirname, "..", "build", "projects.js");
|
|
78
|
-
process.argv = [process.argv[0], p, ...args.slice(1)];
|
|
79
|
-
await import(p);
|
|
80
|
-
} else if (command === "pentests") {
|
|
81
|
-
const p = join(__dirname, "..", "build", "pentests.js");
|
|
82
|
-
process.argv = [process.argv[0], p, ...args.slice(1)];
|
|
83
|
-
await import(p);
|
|
84
|
-
} else if (command === "issues") {
|
|
85
|
-
const p = join(__dirname, "..", "build", "issues.js");
|
|
86
|
-
process.argv = [process.argv[0], p, ...args.slice(1)];
|
|
87
|
-
await import(p);
|
|
88
|
-
} else if (command === "fixes") {
|
|
89
|
-
const p = join(__dirname, "..", "build", "fixes.js");
|
|
90
|
-
process.argv = [process.argv[0], p, ...args.slice(1)];
|
|
91
|
-
await import(p);
|
|
92
|
-
} else if (command === "logs") {
|
|
93
|
-
const p = join(__dirname, "..", "build", "logs.js");
|
|
94
|
-
process.argv = [process.argv[0], p, ...args.slice(1)];
|
|
95
|
-
await import(p);
|
|
96
|
-
} else if (command === "upgrade" || command === "update") {
|
|
97
|
-
const currentVersion = getCurrentVersion();
|
|
98
|
-
console.log(`Current version: v${currentVersion}`);
|
|
99
|
-
console.log("Checking for updates...");
|
|
100
|
-
|
|
101
|
-
const result = await upgrade({ interactive: true });
|
|
102
|
-
console.log();
|
|
103
|
-
console.log(result.message);
|
|
104
|
-
|
|
105
|
-
process.exit(result.success ? 0 : 1);
|
|
106
|
-
} else if (
|
|
107
|
-
command === "version" ||
|
|
108
|
-
command === "--version" ||
|
|
109
|
-
command === "-v"
|
|
110
|
-
) {
|
|
111
|
-
// Show version
|
|
112
|
-
console.log(`v${version}`);
|
|
113
|
-
} else if (command === "help" || command === "--help" || command === "-h") {
|
|
114
|
-
// Show help
|
|
115
|
-
console.log("Pensar - AI-Powered Penetration Testing CLI");
|
|
116
|
-
console.log();
|
|
117
|
-
console.log("Usage:");
|
|
118
|
-
console.log(" pensar Launch the TUI (Terminal User Interface)");
|
|
119
|
-
console.log(" pensar uninstall Uninstall Pensar (keeps sessions, memories, skills)");
|
|
120
|
-
console.log(" pensar upgrade Update pensar to the latest version");
|
|
121
|
-
console.log(" pensar help Show this help message");
|
|
122
|
-
console.log(" pensar version Show version number");
|
|
123
|
-
console.log(" pensar benchmark Run the benchmark CLI");
|
|
124
|
-
console.log(" pensar quicktest Run a quick penetration test");
|
|
125
|
-
console.log(" pensar pentest Run a comprehensive penetration test");
|
|
126
|
-
console.log(
|
|
127
|
-
" pensar swarm Run parallel pentests on multiple targets"
|
|
128
|
-
);
|
|
129
|
-
console.log(
|
|
130
|
-
" pensar auth Connect to Pensar Console for managed inference"
|
|
131
|
-
);
|
|
132
|
-
console.log(
|
|
133
|
-
" pensar projects List workspace projects"
|
|
134
|
-
);
|
|
135
|
-
console.log(
|
|
136
|
-
" pensar pentests List and manage pentests"
|
|
137
|
-
);
|
|
138
|
-
console.log(
|
|
139
|
-
" pensar issues List and manage security issues"
|
|
140
|
-
);
|
|
141
|
-
console.log(
|
|
142
|
-
" pensar fixes View security fixes"
|
|
143
|
-
);
|
|
144
|
-
console.log(
|
|
145
|
-
" pensar logs View agent execution logs"
|
|
146
|
-
);
|
|
147
|
-
console.log();
|
|
148
|
-
console.log("Options:");
|
|
149
|
-
console.log(" -h, --help Show this help message");
|
|
150
|
-
console.log(" -v, --version Show version number");
|
|
151
|
-
console.log();
|
|
152
|
-
console.log("Benchmark Usage:");
|
|
153
|
-
console.log(" pensar benchmark <repo-path> [options] [branch1 branch2 ...]");
|
|
154
|
-
console.log();
|
|
155
|
-
console.log("Benchmark Options:");
|
|
156
|
-
console.log(" --all-branches Test all branches in the repository");
|
|
157
|
-
console.log(" --limit <number> Limit the number of branches to test");
|
|
158
|
-
console.log(" --skip <number> Skip the first N branches");
|
|
159
|
-
console.log(
|
|
160
|
-
" --model <model> Specify the AI model to use (default: claude-sonnet-4-5)"
|
|
161
|
-
);
|
|
162
|
-
console.log();
|
|
163
|
-
console.log("Quicktest Usage:");
|
|
164
|
-
console.log(
|
|
165
|
-
" pensar quicktest --target <target> --objective <objective> [options]"
|
|
166
|
-
);
|
|
167
|
-
console.log();
|
|
168
|
-
console.log("Quicktest Options:");
|
|
169
|
-
console.log(
|
|
170
|
-
" --target <target> Target URL or IP address to test (required)"
|
|
171
|
-
);
|
|
172
|
-
console.log(
|
|
173
|
-
" --objective <objective> Objective or goal of the pentest (required)"
|
|
174
|
-
);
|
|
175
|
-
console.log(
|
|
176
|
-
" --model <model> AI model to use (default: claude-sonnet-4-5)"
|
|
177
|
-
);
|
|
178
|
-
console.log(
|
|
179
|
-
" --headers <mode> Header mode: none, default, custom (default: default)"
|
|
180
|
-
);
|
|
181
|
-
console.log(
|
|
182
|
-
" --header <name:value> Add custom header (requires --headers custom)"
|
|
183
|
-
);
|
|
184
|
-
console.log();
|
|
185
|
-
console.log("Pentest Usage:");
|
|
186
|
-
console.log(" pensar pentest --target <target> [options]");
|
|
187
|
-
console.log();
|
|
188
|
-
console.log("Pentest Options:");
|
|
189
|
-
console.log(
|
|
190
|
-
" --target <target> Target domain or organization (required)"
|
|
191
|
-
);
|
|
192
|
-
console.log(
|
|
193
|
-
" --model <model> AI model to use (default: claude-sonnet-4-5)"
|
|
194
|
-
);
|
|
195
|
-
console.log(
|
|
196
|
-
" --headers <mode> Header mode: none, default, custom (default: default)"
|
|
197
|
-
);
|
|
198
|
-
console.log(
|
|
199
|
-
" --header <name:value> Add custom header (requires --headers custom)"
|
|
200
|
-
);
|
|
201
|
-
console.log();
|
|
202
|
-
console.log("Swarm Usage:");
|
|
203
|
-
console.log(" pensar swarm <targets> [options]");
|
|
204
|
-
console.log();
|
|
205
|
-
console.log("Swarm Arguments:");
|
|
206
|
-
console.log(" <targets> JSON string or path to JSON file");
|
|
207
|
-
console.log();
|
|
208
|
-
console.log("Swarm Options:");
|
|
209
|
-
console.log(
|
|
210
|
-
" --model <model> AI model to use (default: claude-sonnet-4-5)"
|
|
211
|
-
);
|
|
212
|
-
console.log(
|
|
213
|
-
" --headers <mode> Header mode: none, default, custom (default: default)"
|
|
214
|
-
);
|
|
215
|
-
console.log(
|
|
216
|
-
" --header <name:value> Add custom header (requires --headers custom)"
|
|
217
|
-
);
|
|
218
|
-
console.log();
|
|
219
|
-
console.log("Auth Usage:");
|
|
220
|
-
console.log(
|
|
221
|
-
" pensar auth Login to Pensar Console (or show status if connected)"
|
|
222
|
-
);
|
|
223
|
-
console.log(" pensar auth login Login to Pensar Console");
|
|
224
|
-
console.log(" pensar auth logout Disconnect from Pensar Console");
|
|
225
|
-
console.log(" pensar auth status Show connection status");
|
|
226
|
-
console.log();
|
|
227
|
-
console.log("Uninstall Usage:");
|
|
228
|
-
console.log(
|
|
229
|
-
" pensar uninstall Fully uninstall Pensar"
|
|
230
|
-
);
|
|
231
|
-
console.log(
|
|
232
|
-
" pensar uninstall --force Skip confirmation prompt"
|
|
233
|
-
);
|
|
234
|
-
console.log();
|
|
235
|
-
console.log("Header Modes (for quicktest, pentest, swarm):");
|
|
236
|
-
console.log(" none No custom headers added to requests");
|
|
237
|
-
console.log(
|
|
238
|
-
" default Add 'User-Agent: pensar-apex' to all offensive requests"
|
|
239
|
-
);
|
|
240
|
-
console.log(
|
|
241
|
-
" custom Use custom headers defined with --header flag"
|
|
242
|
-
);
|
|
243
|
-
console.log();
|
|
244
|
-
console.log("Examples:");
|
|
245
|
-
console.log(" pensar");
|
|
246
|
-
console.log(" pensar benchmark /path/to/vulnerable-app");
|
|
247
|
-
console.log(" pensar benchmark /path/to/app main develop");
|
|
248
|
-
console.log(" pensar benchmark /path/to/app --all-branches --limit 3");
|
|
249
|
-
console.log(
|
|
250
|
-
" pensar quicktest --target http://localhost:3000 --objective 'Find SQL injection'"
|
|
251
|
-
);
|
|
252
|
-
console.log(
|
|
253
|
-
" pensar quicktest --target api.example.com --objective 'API testing' --headers custom --header 'User-Agent: pensar_client123'"
|
|
254
|
-
);
|
|
255
|
-
console.log(" pensar pentest --target example.com");
|
|
256
|
-
console.log(
|
|
257
|
-
" pensar pentest --target example.com --headers custom --header 'User-Agent: pensar_client123'"
|
|
258
|
-
);
|
|
259
|
-
console.log(" pensar swarm targets.json");
|
|
260
|
-
console.log(" pensar swarm targets.json --headers none");
|
|
261
|
-
console.log(" pensar auth");
|
|
262
|
-
console.log(" pensar auth status");
|
|
263
|
-
console.log(" pensar auth logout");
|
|
264
|
-
console.log();
|
|
265
|
-
console.log("Console API:");
|
|
266
|
-
console.log(" pensar projects");
|
|
267
|
-
console.log(" pensar pentests <projectId>");
|
|
268
|
-
console.log(" pensar issues <projectId>");
|
|
269
|
-
console.log(" pensar issues get <issueId>");
|
|
270
|
-
console.log(" pensar fixes <issueId>");
|
|
271
|
-
console.log(" pensar logs <issueId>");
|
|
272
|
-
} else if (args.length === 0) {
|
|
273
|
-
// No command specified, run the TUI
|
|
274
|
-
const appPath = join(__dirname, "..", "build", "index.js");
|
|
275
|
-
await import(appPath);
|
|
276
|
-
} else {
|
|
277
|
-
// Unknown command
|
|
278
|
-
console.error(`Error: Unknown command '${command}'`);
|
|
279
|
-
console.error();
|
|
280
|
-
console.error("Run 'pensar --help' for usage information");
|
|
281
|
-
process.exit(1);
|
|
8
|
+
const cliPath = join(__dirname, "..", "build", "cli.js");
|
|
9
|
+
|
|
10
|
+
// Under Node, try to re-exec under Bun if no subcommand given (TUI needs Bun)
|
|
11
|
+
if (typeof globalThis.Bun === "undefined") {
|
|
12
|
+
const args = process.argv.slice(2);
|
|
13
|
+
if (args.length === 0) {
|
|
14
|
+
// No subcommand = TUI mode — try re-exec under Bun
|
|
15
|
+
const { execFileSync } = await import("child_process");
|
|
16
|
+
try {
|
|
17
|
+
execFileSync("bun", [__filename], { stdio: "inherit" });
|
|
18
|
+
process.exit(0);
|
|
19
|
+
} catch (err) {
|
|
20
|
+
if (err && typeof err === "object" && "code" in err && err.code === "ENOENT") {
|
|
21
|
+
console.error(
|
|
22
|
+
"TUI mode requires Bun. Install Bun (https://bun.sh) or use a standalone binary release for interactive mode.",
|
|
23
|
+
);
|
|
24
|
+
console.error("All other commands work with Node — run 'pensar --help'.");
|
|
25
|
+
process.exit(1);
|
|
26
|
+
}
|
|
27
|
+
if (err && typeof err === "object" && "status" in err) {
|
|
28
|
+
process.exit(err.status ?? 1);
|
|
29
|
+
}
|
|
30
|
+
process.exit(1);
|
|
31
|
+
}
|
|
32
|
+
}
|
|
33
|
+
process.env.PENSAR_NO_TUI = "1";
|
|
282
34
|
}
|
|
35
|
+
|
|
36
|
+
process.argv = [process.argv[0], cliPath, ...process.argv.slice(2)];
|
|
37
|
+
await import(cliPath);
|
|
@@ -0,0 +1,206 @@
|
|
|
1
|
+
import {
|
|
2
|
+
WhiteboxAttackSurfaceResultSchema
|
|
3
|
+
} from "./cli-2ckm5es2.js";
|
|
4
|
+
import {
|
|
5
|
+
OffensiveSecurityAgent
|
|
6
|
+
} from "./cli-r8r90gka.js";
|
|
7
|
+
import"./cli-jh38b6zv.js";
|
|
8
|
+
import {
|
|
9
|
+
hasToolCall,
|
|
10
|
+
tool
|
|
11
|
+
} from "./cli-kqtgcdzn.js";
|
|
12
|
+
import"./cli-j66pect7.js";
|
|
13
|
+
import"./cli-bp6d08sg.js";
|
|
14
|
+
import"./cli-jb0gcnrs.js";
|
|
15
|
+
import"./cli-yj3dy0vg.js";
|
|
16
|
+
import"./cli-15vxn9zj.js";
|
|
17
|
+
import"./cli-7ckctq7a.js";
|
|
18
|
+
import"./cli-8rxa073f.js";
|
|
19
|
+
|
|
20
|
+
// src/core/agents/specialized/whiteboxAttackSurface/prompts.ts
|
|
21
|
+
var WHITEBOX_ATTACK_SURFACE_SYSTEM_PROMPT = `You are an expert source-code analyst and orchestrator. Your mission is to comprehensively map the attack surface of a codebase by analyzing its source code directly.
|
|
22
|
+
|
|
23
|
+
You operate completely autonomously. Do not ask for permission or wait for user input.
|
|
24
|
+
|
|
25
|
+
# Your Goal
|
|
26
|
+
|
|
27
|
+
Given a codebase path, you must:
|
|
28
|
+
1. Identify the repository structure (monorepo vs single app, package manager, etc.)
|
|
29
|
+
2. Discover every application/service defined in the repo
|
|
30
|
+
3. For each app, enumerate ALL web pages and ALL API endpoints defined in the source code
|
|
31
|
+
4. For each endpoint, generate specific pentest objectives
|
|
32
|
+
|
|
33
|
+
# Tools at Your Disposal
|
|
34
|
+
|
|
35
|
+
## list_files
|
|
36
|
+
List directories to understand project structure. Start here.
|
|
37
|
+
|
|
38
|
+
## read_file
|
|
39
|
+
Read config files, entry points, route definitions, etc.
|
|
40
|
+
|
|
41
|
+
## grep
|
|
42
|
+
Your primary search tool. Use it to find route definitions, middleware, controllers, etc.
|
|
43
|
+
|
|
44
|
+
## document_asset
|
|
45
|
+
**Use this to document every significant asset you discover.** Each call persists a JSON record to the session's assets directory. Document:
|
|
46
|
+
- Each application/service you identify (assetType: "web_application" or "api")
|
|
47
|
+
- Notable subdomains or infrastructure you encounter (assetType: "subdomain", "infrastructure_service")
|
|
48
|
+
- Key API endpoint groups or admin panels (assetType: "endpoint", "admin_panel")
|
|
49
|
+
|
|
50
|
+
Call this throughout your analysis as you discover assets — don't wait until the end. Include relevant details like the technology stack, URL, authentication requirements, and risk level.
|
|
51
|
+
|
|
52
|
+
## spawn_coding_agent
|
|
53
|
+
**This is your key tool for scaling out analysis.** Spawn coding sub-agents to analyze individual apps in parallel for higher fidelity. Each sub-agent has full filesystem access (read_file, list_files, grep, execute_command).
|
|
54
|
+
|
|
55
|
+
## submit_results
|
|
56
|
+
Call this LAST with your complete structured results. This ends your run.
|
|
57
|
+
|
|
58
|
+
# Methodology
|
|
59
|
+
|
|
60
|
+
## Phase 1: REPO IDENTIFICATION (do this yourself — it's fast)
|
|
61
|
+
1. List the root directory
|
|
62
|
+
2. Read the top-level config files to determine:
|
|
63
|
+
- Package manager (package.json → npm/yarn/pnpm, requirements.txt → pip, Cargo.toml → cargo, go.mod → go, etc.)
|
|
64
|
+
- Repo structure (workspaces field in package.json → monorepo, multiple service dirs → multi-package, etc.)
|
|
65
|
+
3. Identify all apps/services — look for:
|
|
66
|
+
- Monorepo workspace packages with their own entry points
|
|
67
|
+
- Separate service directories with their own configs
|
|
68
|
+
- A single app at the root
|
|
69
|
+
|
|
70
|
+
## Phase 2: APP ANALYSIS (delegate to coding agents)
|
|
71
|
+
For each app you identified, spawn a coding agent with a detailed objective. The objective should instruct the agent to:
|
|
72
|
+
|
|
73
|
+
1. **Identify the framework** — read the app's config/entry point to determine the web framework
|
|
74
|
+
2. **Find ALL web pages** — search for page/view/route definitions:
|
|
75
|
+
- React/Next.js: pages/ or app/ directory, route components
|
|
76
|
+
- Express: res.render(), res.sendFile(), static file serving
|
|
77
|
+
- Django: urls.py patterns pointing to template views
|
|
78
|
+
- Rails: routes.rb entries pointing to controller actions that render views
|
|
79
|
+
- Vue/Nuxt: pages/ directory, router definitions
|
|
80
|
+
- etc.
|
|
81
|
+
3. **Find ALL API endpoints** — search for route/endpoint definitions:
|
|
82
|
+
- Express: app.get(), app.post(), router.get(), router.post(), etc.
|
|
83
|
+
- Next.js: app/api/ or pages/api/ route handlers
|
|
84
|
+
- Django: urls.py patterns pointing to API views, DRF viewsets/routers
|
|
85
|
+
- FastAPI: @app.get(), @app.post() decorators
|
|
86
|
+
- Rails: routes.rb API namespaces, controller actions
|
|
87
|
+
- Spring: @GetMapping, @PostMapping, @RequestMapping
|
|
88
|
+
- etc.
|
|
89
|
+
4. **For each endpoint, determine**:
|
|
90
|
+
- HTTP method and route path
|
|
91
|
+
- Handler function/component name
|
|
92
|
+
- File location and line number
|
|
93
|
+
- Whether auth appears to be required (middleware, decorators, guards)
|
|
94
|
+
- Brief description of what it does
|
|
95
|
+
5. **For each endpoint, generate pentest objectives** — specific, actionable testing goals like:
|
|
96
|
+
- "Test for SQL injection in the 'search' query parameter"
|
|
97
|
+
- "Test for IDOR by accessing /api/orders/{id} with other users' order IDs"
|
|
98
|
+
- "Test for XSS in the user profile name field"
|
|
99
|
+
- "Test for privilege escalation by accessing admin-only endpoint as regular user"
|
|
100
|
+
- "Test for CSRF on the password change endpoint"
|
|
101
|
+
- "Test for path traversal in the file download parameter"
|
|
102
|
+
|
|
103
|
+
**IMPORTANT:** Tell each coding agent to output its findings in a STRUCTURED FORMAT that you can parse. Instruct it to use clear delimiters or a consistent format for each endpoint (method, path, handler, file, line, auth, description, pentest objectives).
|
|
104
|
+
|
|
105
|
+
## Phase 3: COLLECT AND SUBMIT (do this yourself)
|
|
106
|
+
1. Parse the output from all coding agents
|
|
107
|
+
2. Assemble the complete structured result
|
|
108
|
+
3. Call \`submit_results\` with the full data
|
|
109
|
+
|
|
110
|
+
# Guidelines
|
|
111
|
+
- Be thorough — every endpoint matters. Don't skip files or directories.
|
|
112
|
+
- Delegate aggressively — spawn coding agents for each app to get high-fidelity results.
|
|
113
|
+
- Give coding agents VERY detailed objectives — they work best with specific instructions about what to search for and how to report it.
|
|
114
|
+
- Don't duplicate work — let the coding agents do the deep file-by-file analysis.
|
|
115
|
+
- When in doubt about repo structure, read more config files before deciding.
|
|
116
|
+
`;
|
|
117
|
+
|
|
118
|
+
// src/core/agents/specialized/whiteboxAttackSurface/agent.ts
|
|
119
|
+
class WhiteboxAttackSurfaceAgent extends OffensiveSecurityAgent {
|
|
120
|
+
constructor(opts) {
|
|
121
|
+
const {
|
|
122
|
+
model,
|
|
123
|
+
codebasePath,
|
|
124
|
+
session,
|
|
125
|
+
authConfig,
|
|
126
|
+
onStepFinish,
|
|
127
|
+
abortSignal,
|
|
128
|
+
callbacks,
|
|
129
|
+
attackSurfaceRegistry
|
|
130
|
+
} = opts;
|
|
131
|
+
let capturedResult = null;
|
|
132
|
+
const submitResultsTool = tool({
|
|
133
|
+
description: `Submit the final whitebox attack surface analysis results.
|
|
134
|
+
|
|
135
|
+
Call this ONCE at the end with your complete structured findings.
|
|
136
|
+
This ends the agent run — make sure all data is included.`,
|
|
137
|
+
inputSchema: WhiteboxAttackSurfaceResultSchema,
|
|
138
|
+
execute: async (results) => {
|
|
139
|
+
capturedResult = results;
|
|
140
|
+
return { success: true, message: "Results submitted." };
|
|
141
|
+
}
|
|
142
|
+
});
|
|
143
|
+
super({
|
|
144
|
+
system: WHITEBOX_ATTACK_SURFACE_SYSTEM_PROMPT,
|
|
145
|
+
prompt: buildPrompt(codebasePath),
|
|
146
|
+
model,
|
|
147
|
+
session,
|
|
148
|
+
authConfig,
|
|
149
|
+
onStepFinish,
|
|
150
|
+
abortSignal,
|
|
151
|
+
attackSurfaceRegistry,
|
|
152
|
+
callbacks,
|
|
153
|
+
subagentCallbacks: callbacks?.subagentCallbacks,
|
|
154
|
+
activeTools: [
|
|
155
|
+
"read_file",
|
|
156
|
+
"list_files",
|
|
157
|
+
"grep",
|
|
158
|
+
"document_asset",
|
|
159
|
+
"spawn_coding_agent",
|
|
160
|
+
"submit_results"
|
|
161
|
+
],
|
|
162
|
+
extraTools: {
|
|
163
|
+
submit_results: submitResultsTool
|
|
164
|
+
},
|
|
165
|
+
stopWhen: hasToolCall("submit_results"),
|
|
166
|
+
resolveResult: () => {
|
|
167
|
+
if (capturedResult) {
|
|
168
|
+
return capturedResult;
|
|
169
|
+
}
|
|
170
|
+
return {
|
|
171
|
+
repoType: "unknown",
|
|
172
|
+
packageManager: "unknown",
|
|
173
|
+
apps: [],
|
|
174
|
+
summary: {
|
|
175
|
+
totalApps: 0,
|
|
176
|
+
totalPages: 0,
|
|
177
|
+
totalApiEndpoints: 0,
|
|
178
|
+
totalPentestObjectives: 0
|
|
179
|
+
}
|
|
180
|
+
};
|
|
181
|
+
}
|
|
182
|
+
});
|
|
183
|
+
}
|
|
184
|
+
}
|
|
185
|
+
function buildPrompt(codebasePath) {
|
|
186
|
+
return `# Whitebox Attack Surface Analysis
|
|
187
|
+
|
|
188
|
+
## Codebase
|
|
189
|
+
- **Path:** ${codebasePath}
|
|
190
|
+
|
|
191
|
+
## Task
|
|
192
|
+
Analyze this codebase and produce a complete attack surface map:
|
|
193
|
+
1. Identify the repo type and package manager
|
|
194
|
+
2. Discover all apps/services
|
|
195
|
+
3. For each app, find all web pages and API endpoints
|
|
196
|
+
4. For each endpoint, generate pentest objectives
|
|
197
|
+
|
|
198
|
+
Use \`spawn_coding_agent\` to delegate app-level analysis for higher fidelity.
|
|
199
|
+
|
|
200
|
+
When finished, call \`submit_results\` with the complete structured output.
|
|
201
|
+
|
|
202
|
+
Begin now.`;
|
|
203
|
+
}
|
|
204
|
+
export {
|
|
205
|
+
WhiteboxAttackSurfaceAgent
|
|
206
|
+
};
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
import {
|
|
2
|
+
CodeAgent
|
|
3
|
+
} from "./cli-w04ggbe4.js";
|
|
4
|
+
import"./cli-r8r90gka.js";
|
|
5
|
+
import"./cli-jh38b6zv.js";
|
|
6
|
+
import"./cli-kqtgcdzn.js";
|
|
7
|
+
import"./cli-j66pect7.js";
|
|
8
|
+
import"./cli-bp6d08sg.js";
|
|
9
|
+
import"./cli-jb0gcnrs.js";
|
|
10
|
+
import"./cli-yj3dy0vg.js";
|
|
11
|
+
import"./cli-15vxn9zj.js";
|
|
12
|
+
import"./cli-7ckctq7a.js";
|
|
13
|
+
import"./cli-8rxa073f.js";
|
|
14
|
+
export {
|
|
15
|
+
CodeAgent
|
|
16
|
+
};
|