Rules / JavaScript / TypeScript
SHIELD-JS-009
Command injection via exec/spawn
What it detects
Executing shell commands with unsanitized user input allows command injection.
How to fix
Avoid passing user input to shell commands. Use execFile with an argument array instead of exec.
Vulnerable — Shield flags thisping.js
const { exec } = require("child_process");
const express = require("express");
const app = express();
app.get("/ping", (req, res) => {
// ?host=8.8.8.8;cat /etc/passwd runs arbitrary commands
exec("ping -c 1 " + req.query.host, (err, stdout) => {
res.type("text").send(stdout);
});
});Fixed — scans cleanping.js
const { execFile } = require("child_process");
const express = require("express");
const app = express();
// Ping only known monitoring targets; host is never taken from the request
app.get("/ping", (req, res) => {
let host;
switch (req.query.target) {
case "primary": host = "db-primary.internal"; break;
case "backup": host = "db-backup.internal"; break;
default: return res.status(400).send("unknown target");
}
execFile("ping", ["-c", "1", host], (err, stdout) => {
res.type("text").send(stdout);
});
});Both snippets are verified against the shipped scanner: the vulnerable one triggers SHIELD-JS-009, the fixed one does not.