SQL, NoSQL and Command Injection in Modern Stacks
ORMs and JSON filters, second-order and blind SQLi, MongoDB operators as query logic, shell versus argv injection, CRLF and expression language.
Injection did not go away with ORMs and JSON APIs. It moved into the places where structure is still assembled from input, which these notes try to name precisely.
NoSQL Injection in MongoDB
When a backend accepts user JSON directly inside a MongoDB filter, $ne and $regex stop being data and become operators. MongoDB queries use documents containing operators such as $ne, $gt, $regex and $where. Direct request-body deserialization may change query logic. Injection may cause authentication bypass, data extraction or JavaScript execution in older configurations using server-side JS. I compare string and object values in the same parameter and observe type-coercion errors before introducing operators. Schema validation and field-by-field query construction reduce exposure. Blocking $ with a regex often breaks legitimate input while leaving parser bypasses.
1
2
3
4
{
"username": {"$ne": null},
"password": {"$ne": null}
}
Modern SQL Injection
ORMs reduce manual concatenation, but a poorly built dynamic query is still user-controlled SQL. SQL injection appears when data enters query structure. ORMs protect parameterized values, while sort fields, raw queries and dynamic identifiers remain sensitive. JSON APIs hide injection inside filters, search DSLs and arrays. Stored procedures may also concatenate SQL internally. I identify DBMS, parameter context and query type before choosing boolean, error, union or time-based techniques. A WAF changes payload viability but does not fix data flow. Parameterization needs to happen where the final statement is built.
1
SELECT id,name FROM products WHERE category = ? ORDER BY user_sort
Second-Order SQL Injection
Input may be validated during registration and become SQL injection only when another process later trusts the stored value. Second-order SQLi separates source and sink in time. The payload enters as legitimate data and is later concatenated into another query. Admin panels, reports, migration jobs and batch processing are common consumers of stored values. I plant canary values, follow where they reappear and look for dynamic query construction in the second workflow. Escaping on input is fragile because the future context may differ. Parameterization needs to exist at the final sink.
Store a harmless quote-containing value in a lab record, then exercise the reporting and admin workflows that later consume it.
Blind SQL Injection
Blind SQLi becomes less mysterious when each request is treated as a yes-or-no question to the database. Boolean-based techniques observe content or status differences. Time-based techniques use controlled delay. Out-of-band methods use DNS or HTTP when the DBMS supports them. Efficient extraction uses binary search, length checks and careful parallelism instead of trying every character. I first identify a stable oracle and measure baseline behavior before automating any inference. Network jitter destroys poorly calibrated time-based tests. Repeated measurements and conservative delays produce stronger evidence.
1
' AND 1=(SELECT CASE WHEN (1=1) THEN (SELECT 1 FROM pg_sleep(3)) ELSE 1 END)--
Command Injection vs Argument Injection
Avoiding shell=True removes an entire injection class, but controlled arguments may still enable dangerous options in the called program. Command injection appears when a shell interprets metacharacters. Argument injection appears when input becomes valid argv with dangerous semantics for the target binary. Options such as curl --output or tool-specific flags show why argv separation does not end the analysis. I determine whether a shell exists, inspect the final command and then read the target program options for values beginning with hyphens or special syntax. Passing an argv array to execve is strong against shell injection. Also use -- where supported and validate the allowed argument domain.
1
subprocess.run(['git','show','--',user_value], check=True)
CRLF Injection and HTTP Response Splitting
When controlled input can insert \r\n, it stops changing one header and starts creating new headers or response sections. CRLF terminates lines in HTTP/1. Applications building headers manually may allow header injection or response splitting. Impact includes Set-Cookie injection, cache poisoning and redirect manipulation. Modern browsers limit some historical effects. I test single and double encoding only on parameters that clearly influence observable response headers. Modern frameworks reject newlines in header values. Proxies and normalization may decode at different layers, so the complete path matters.
1
%0d%0aX-Lab-Test:%20yes
Expression Language Injection
Expression languages were designed to access properties and functions dynamically. Untrusted input inside the expression gains exactly that power. Java EL, OGNL, SpEL and other expression languages appear in frameworks and templates. Each has its own syntax and object model. Injection may reach method invocation, class access or bean lookup when the context exposes powerful primitives. I identify the engine through errors and harmless expressions before using framework-specific syntax. Blocking ${ does not fix contexts using #{}, %{} or indirect parsing. Remediation is separating data from expression source.
1
2
3
${7*7}
#{7*7}
%{7*7}