Skip to content

Commit a21d6d0

Browse files
test(security): add PreparedStatementConsistencyTest from Cacti#769
Verifies that poller_thold.php, setup.php, thold.php, and thold_graph.php contain no single-line raw db_*() calls with interpolated variables. Signed-off-by: Thomas Vincent <thomasvincent@gmail.com>
1 parent 9cbd266 commit a21d6d0

1 file changed

Lines changed: 50 additions & 0 deletions

File tree

Lines changed: 50 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,50 @@
1+
<?php
2+
/*
3+
+-------------------------------------------------------------------------+
4+
| Copyright (C) 2004-2026 The Cacti Group |
5+
+-------------------------------------------------------------------------+
6+
| Cacti: The Complete RRDtool-based Graphing Solution |
7+
+-------------------------------------------------------------------------+
8+
*/
9+
10+
/*
11+
* Verify files in the hardening stack use prepared helpers when they execute
12+
* obviously variable-interpolated SQL on a single line.
13+
*/
14+
15+
it('does not introduce single-line interpolated db_* calls in hardened files', function () {
16+
$targetFiles = array(
17+
'poller_thold.php',
18+
'setup.php',
19+
'thold.php',
20+
'thold_graph.php',
21+
);
22+
23+
$rawInterpolatedPattern = '/\bdb_(?:execute|fetch_row|fetch_assoc|fetch_cell)\s*\(\s*(["\']).*\$[A-Za-z_{]/';
24+
$preparedPattern = '/\bdb_(?:execute|fetch_row|fetch_assoc|fetch_cell)_prepared\s*\(/';
25+
26+
foreach ($targetFiles as $relativeFile) {
27+
$path = realpath(__DIR__ . '/../../' . $relativeFile);
28+
expect($path)->not->toBeFalse("Failed to resolve target file path: {$relativeFile}");
29+
30+
$contents = file_get_contents($path);
31+
expect($contents)->not->toBeFalse("Failed to read target file: {$relativeFile}");
32+
33+
$lines = explode("\n", $contents);
34+
35+
foreach ($lines as $lineNumber => $line) {
36+
$trimmed = ltrim($line);
37+
38+
if (strpos($trimmed, '//') === 0 || strpos($trimmed, '*') === 0 || strpos($trimmed, '#') === 0) {
39+
continue;
40+
}
41+
42+
$hasInterpolatedRawCall = preg_match($rawInterpolatedPattern, $line) === 1;
43+
$hasPreparedCall = preg_match($preparedPattern, $line) === 1;
44+
45+
expect($hasInterpolatedRawCall && !$hasPreparedCall)->toBeFalse(
46+
sprintf('File %s contains an interpolated raw db_* call at line %d', $relativeFile, $lineNumber + 1)
47+
);
48+
}
49+
}
50+
});

0 commit comments

Comments
 (0)