Compare commits

...

1 Commits

Author SHA1 Message Date
Zanie
a19e98a2c7 Fix false positive for S608 where SQL-like expression follows other text 2023-11-16 09:49:13 -06:00
3 changed files with 13 additions and 4 deletions

View File

@@ -101,4 +101,5 @@ query = "INSERT table VALUES (%s)" % (var,)
query = "REPLACE INTO table VALUES (%s)" % (var,)
query = "REPLACE table VALUES (%s)" % (var,)
query = "Deselect something that is not SQL even though it has a ' from ' somewhere in %s." % "there"
not_a_query = "Deselect something that is not SQL even though it has a ' from ' somewhere in %s." % "there"
not_a_query = f"Please select a value from the list of possible variants: {variants}."

View File

@@ -13,7 +13,15 @@ use crate::checkers::ast::Checker;
use super::super::helpers::string_literal;
static SQL_REGEX: Lazy<Regex> = Lazy::new(|| {
Regex::new(r"(?i)\b(select\s.+\sfrom\s|delete\s+from\s|(insert|replace)\s.+\svalues\s|update\s.+\sset\s)")
// We pass this generated expression strings like:
// "SELECT " + val + " FROM " + table
// f'delete from table where var = {var}'
// "\n SELECT *\n FROM table\n WHERE var = {}\n ".format(var)
//
// To avoid false positives, we:
// - Require the SQL to be at the start of the expression, allowing for tokens that are not a part of the string
// - Require whole-word matches for SQL keywords
Regex::new(r#"(?i)\A(\"|f\"|\'|f\'|\\|\\n|\s)*\b(select\s.+\sfrom\s|delete\s+from\s|(insert|replace)\s.+\svalues\s|update\s.+\sset\s)"#)
.unwrap()
});
@@ -51,7 +59,7 @@ fn has_string_literal(expr: &Expr) -> bool {
}
fn matches_sql_statement(string: &str) -> bool {
SQL_REGEX.is_match(string)
SQL_REGEX.is_match(string.trim_start())
}
fn matches_string_format_expression(expr: &Expr, semantic: &SemanticModel) -> bool {

View File

@@ -476,7 +476,7 @@ S608.py:102:9: S608 Possible SQL injection vector through string-based query con
102 | query = "REPLACE table VALUES (%s)" % (var,)
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ S608
103 |
104 | query = "Deselect something that is not SQL even though it has a ' from ' somewhere in %s." % "there"
104 | not_a_query = "Deselect something that is not SQL even though it has a ' from ' somewhere in %s." % "there"
|