Command Injection in Express with Basic Auth
Command Injection in Express with Basic Auth — how this specific combination creates or exposes the vulnerability
Command Injection occurs when an attacker can cause an application to execute arbitrary system commands. In Express.js, this often arises when user-controlled input is passed to shell utilities such as exec, execSync, or child processes without proper validation or escaping. When Basic Authentication is used, the presence of static credentials does not introduce the vulnerability by itself, but it can change how an exploit is attempted and what impact it may have.
Consider an endpoint that accepts a filename query parameter and runs a system command to inspect the file. If the application uses Basic Auth, an authenticated user (or an attacker who obtained credentials via phishing or a leak) may attempt to inject shell metacharacters to read sensitive files, change system behavior, or chain commands. For example, using &&, ||, or backticks can enable command chaining or substitution. An attacker might send a request like /report?file=report.txt;cat%20/etc/passwd and, if the server constructs a shell command such as exec(`cat ${filename}`), the injected segment runs with the same privileges as the Node.js process.
In a black-box scan, middleBrick tests unauthenticated attack surfaces where possible, but if Basic Auth is required, scanning can include credentials to exercise authenticated paths. The 12 security checks, including Input Validation and Unsafe Consumption, will flag instances where user input reaches OS commands without sanitization, escaping, or use of non-shell APIs. Because the OpenAPI/Swagger spec is analyzed with full $ref resolution, middleBrick cross-references runtime behavior with declared parameters to highlight routes where command-like patterns appear, such as dynamic paths or script names that incorporate user data.
Real-world impact aligns with common attack patterns like CVE-2021-23337-style injection chains, where improper input handling leads to unauthorized file access or code execution. Even without direct root access, leaked environment variables or configuration files can aid further exploitation. The LLM/AI Security checks do not apply here, as this scenario involves server-side command execution rather than LLM endpoints or prompt manipulation.
Because middleBrick reports findings with severity and remediation guidance rather than fixing issues, it will identify the vulnerable parameter and suggest safer alternatives. Developers should treat any user-controlled data flowing into shell commands as hostile, regardless of whether authentication is enforced.
Basic Auth-Specific Remediation in Express — concrete code fixes
Remediation focuses on avoiding shell invocation and validating input. The safest approach is to use language-native operations instead of spawning a shell. For file operations, use Node.js filesystem APIs directly and validate filenames against a strict allowlist or a safe pattern. If system utilities are unavoidable, use parameterized APIs or explicit argument arrays to prevent the shell from interpreting metacharacters.
Below are concrete Express examples. The vulnerable pattern demonstrates the risk, followed by a remediated version that avoids shell execution.
// Vulnerable example: user input reaches exec via template literal
const express = require('express');
const { exec } = require('child_process');
const app = express();
const authUser = 'admin'; // Basic Auth user
const authPass = 'secret'; // Basic Auth pass (insecure hardcoded example)
// Basic Auth middleware (simplified)
app.use((req, res, next) => {
const auth = req.headers.authorization;
if (auth) {
const [user, pass] = Buffer.from(auth.split(' ')[1], 'base64').toString().split(':');
if (user === authUser && pass === authPass) return next();
}
res.set('WWW-Authenticate', 'Basic');
res.status(401).send('Authentication required');
});
// Vulnerable route
app.get('/report', (req, res) => {
const filename = req.query.file;
exec(`cat ${filename}`, (err, stdout) => {
if (err) return res.status(500).send('Error');
res.send(stdout);
});
});
In this example, an attacker who knows the Basic Auth credentials can inject shell commands via the file parameter, leading to unauthorized data exposure (e.g., /report?file=report.txt;cat%20/etc/passwd).
Remediated version using safe filesystem operations and input validation:
const express = require('express');
const fs = require('fs');
const path = require('path');
const app = express();
const authUser = 'admin';
const authPass = 'secret';
app.use((req, res, next) => {
const auth = req.headers.authorization;
if (auth) {
const [user, pass] = Buffer.from(auth.split(' ')[1], 'base64').toString().split(':');
if (user === authUser && pass === authPass) return next();
}
res.set('WWW-Authenticate', 'Basic');
res.status(401).send('Authentication required');
});
// Safe route: no shell, strict path handling
app.get('/report', (req, res) => {
const requested = req.query.file;
if (!requested || !/^[a-zA-Z0-9_.-]+\.txt$/.test(requested)) {
return res.status(400).send('Invalid filename');
}
const filePath = path.join('/safe/reports', requested);
fs.readFile(filePath, 'utf8', (err, data) => {
if (err) return res.status(404).send('Not found');
res.send(data);
});
});
Key changes include removing shell usage, validating the filename with a regex, and using path.join to avoid directory traversal. If system commands are required, prefer spawn with an argument array and avoid the shell by setting shell: false explicitly.
middleBrick’s scans will highlight the vulnerable route and recommend these practices. The Dashboard can track remediation progress over time, the CLI can output JSON for scripting, and the GitHub Action can enforce a minimum score before merges. These integrations help maintain secure configurations without relying on the scanner to fix issues automatically.
Related CWEs: inputValidation
| CWE ID | Name | Severity |
|---|---|---|
| CWE-20 | Improper Input Validation | HIGH |
| CWE-22 | Path Traversal | HIGH |
| CWE-74 | Injection | CRITICAL |
| CWE-77 | Command Injection | CRITICAL |
| CWE-78 | OS Command Injection | CRITICAL |
| CWE-79 | Cross-site Scripting (XSS) | HIGH |
| CWE-89 | SQL Injection | CRITICAL |
| CWE-90 | LDAP Injection | HIGH |
| CWE-91 | XML Injection | HIGH |
| CWE-94 | Code Injection | CRITICAL |