我有一些用我的C#代码编写的SQL查询。表名使用枚举传递给构造函数。然后它分配给一个全局变量并附加到字符串,
const string ADD_SQL = "INSERT INTO {0} (ColumnOne) VALUES (@valueOne)";
const string CLEAR_SQL = "DELETE FROM {0}";
var commandText = string.Format(ADD_SQL , _tableName);
但是当我运行Veracode工具时,它会显示此查询在执行时有可能出现SQL注入。
command.ExecuteNonQuery();
从代码中避免这种SQL注入方案的任何可能的解决方案。需要对上面的const.I尝试添加标记(@tablename)并尝试。但它没有成功。
const string ADD_SQL = "INSERT INTO @tablename (Data) VALUES (@valueOne)";
var commandText = ADD_MESSAGE_SQL.Replace("@tablename", _tableName);
要避免这种情况的其他任何可能的解决方案吗?
答案 0 :(得分:0)
Veracode很可能不喜欢像当前语句那样放置SQL查询,而是希望使用它编写此代码的规定方式。并且在plnkr中可见,它希望您使用预准备语句来创建参数化查询。
现在可以选择。我对此的看法是存储过程会更好,但是如果你必须保留documentation in the Repair section,那么就不要试图让一个查询对所有场景和表格都过于通用。
答案 1 :(得分:0)
如果您的字符串来自用户输入,则将字符串连接到SQL语句中会有风险 虽然你所描述的情况并非如此,但我猜测Veracode工具不知道字符串的来源,它只是看到字符串连接并发出警告。
更好的方法是为每个表编写完整的SQL语句(通常我更喜欢使用存储过程,但这是另一个主题[您可以搜索存储过程与内联SQL])并使用参数作为值(标识符不能正如您已经发现的那样,在SQL中进行参数化。
所以而不是
const string ADD_SQL = "INSERT INTO {0} (ColumnOne) VALUES (@valueOne)";
const string CLEAR_SQL = "DELETE FROM {0}";
并在运行时添加表名,这是一个更好的解决方案:
const string ADD_tableName = "INSERT INTO TableName (ColumnOne) VALUES(@ValueOne)"
const string CLEAR_tableName = "DELETE FROM TableName";
还有更好的解决方案,但这是您提供的代码最简单的解决方法。