143 lines
3.9 KiB
TypeScript
143 lines
3.9 KiB
TypeScript
/**
|
||
* Tool Sandbox PoC (Gen 2 - Production Tooling)
|
||
*
|
||
* This script proves that the execution environment can physically handle
|
||
* invoking actual production-grade tooling constraints (tree-sitter CLI
|
||
* and semgrep CLI) natively via system execution rather than Node imports.
|
||
*/
|
||
|
||
import {
|
||
dirname,
|
||
fromFileUrl,
|
||
join,
|
||
} from "https://deno.land/std@0.224.0/path/mod.ts";
|
||
import { execTool, requireTool } from "./sys_exec.ts";
|
||
|
||
const currentDir = dirname(fromFileUrl(import.meta.url));
|
||
const TEMP_FILE = join(currentDir, "dummy_target.js");
|
||
|
||
const DUMMY_CODE = `
|
||
function vulnerableQuery(userInput) {
|
||
const query = "SELECT * FROM users WHERE name = '" + userInput + "'";
|
||
db.execute(query);
|
||
}
|
||
`;
|
||
|
||
async function testTreeSitter() {
|
||
console.log("\n--- Testing Tree-sitter (CLI) ---");
|
||
const hasTreeSitter = await requireTool(
|
||
"tree-sitter",
|
||
"npm install -g tree-sitter-cli",
|
||
);
|
||
if (!hasTreeSitter) return false;
|
||
|
||
try {
|
||
await Deno.writeTextFile(TEMP_FILE, DUMMY_CODE);
|
||
|
||
// Provide code as a file, use normal tree-sitter parse output
|
||
const { code, stdout, stderr } = await execTool("tree-sitter", [
|
||
"parse",
|
||
TEMP_FILE,
|
||
"-q",
|
||
]);
|
||
|
||
if (code !== 0) {
|
||
console.error("❌ Tree-sitter CLI execution failed:", stderr || stdout);
|
||
return false;
|
||
}
|
||
|
||
// We don't have the nice object tree structure, but we can verify it executed successfully
|
||
// We would parse the sexp output from tree-sitter for full ast traversal in a real scenario
|
||
console.log("[Sandbox] Successfully executed native tree-sitter binary!");
|
||
return true;
|
||
} catch (error) {
|
||
console.error("❌ Tree-sitter CLI execution failed:", error);
|
||
return false;
|
||
} finally {
|
||
try {
|
||
await Deno.remove(TEMP_FILE);
|
||
} catch {
|
||
// ignore
|
||
}
|
||
}
|
||
}
|
||
|
||
async function testSemgrep() {
|
||
console.log("\n--- Testing Semgrep (Binary) ---");
|
||
const hasSemgrep = await requireTool(
|
||
"semgrep",
|
||
"pip3 install semgrep --break-system-packages",
|
||
);
|
||
if (!hasSemgrep) return false;
|
||
|
||
try {
|
||
// Write out dummy file for semgrep to scan
|
||
await Deno.writeTextFile(TEMP_FILE, DUMMY_CODE);
|
||
|
||
// Define a basic semgrep rule directly via CLI flag to detect our dummy issue
|
||
const { code, stdout, stderr } = await execTool("semgrep", [
|
||
"--quiet",
|
||
"--json",
|
||
"--lang",
|
||
"javascript",
|
||
"-e",
|
||
'"$SELECT ... " + $INPUT',
|
||
TEMP_FILE,
|
||
]);
|
||
|
||
if (code !== 0 && code !== 1) { // 1 means findings found, 0 means no findings. Other codes are errors.
|
||
console.error("❌ Semgrep execution returned error code:", code);
|
||
console.error(stderr);
|
||
return false;
|
||
}
|
||
|
||
const jsonResult = JSON.parse(stdout);
|
||
|
||
console.log("[Sandbox] Successfully executed native semgrep binary!");
|
||
console.log(
|
||
`[Sandbox] Vulnerabilities found: ${jsonResult.results.length}`,
|
||
);
|
||
if (jsonResult.results.length > 0) {
|
||
console.log(
|
||
`[Sandbox] Details: ${jsonResult.results[0].extra.message} (Line ${
|
||
jsonResult.results[0].start.line
|
||
})`,
|
||
);
|
||
}
|
||
|
||
return true;
|
||
} catch (error) {
|
||
console.error("❌ Semgrep binary execution failed:", error);
|
||
return false;
|
||
} finally {
|
||
try {
|
||
await Deno.remove(TEMP_FILE);
|
||
} catch {
|
||
// ignore
|
||
}
|
||
}
|
||
}
|
||
|
||
async function runSandbox() {
|
||
console.log("Starting Gen 2 Tool Sandbox (Production Dependencies)\n");
|
||
|
||
const tsSuccess = await testTreeSitter();
|
||
const sgSuccess = await testSemgrep();
|
||
|
||
// For PoC execution, we don't strictly fail if tools are missing, because
|
||
// the environment might be a basic docker. But we do want to record if it succeeded.
|
||
if (tsSuccess && sgSuccess) {
|
||
console.log(
|
||
"\n✅ Gen 2 Sandbox execution completed successfully. Physical tools verified.",
|
||
);
|
||
} else {
|
||
console.warn(
|
||
"\n⚠️ Gen 2 Sandbox finished with skipped/failed host dependencies. Assuming graceful pass for PoC.",
|
||
);
|
||
}
|
||
}
|
||
|
||
if (import.meta.main) {
|
||
runSandbox().catch(console.error);
|
||
}
|