gpt4 book ai didi

sql-server - 如何清理(防止SQL注入(inject))SQL Server中的动态SQL?

转载 作者:行者123 更新时间:2023-12-02 10:36:42 24 4
gpt4 key购买 nike

我们有大量依赖动态 SQL 的 SQL Server 存储过程。

存储过程的参数在动态 SQL 语句中使用。

我们需要在这些存储过程中使用标准验证函数来验证这些参数并防止 SQL 注入(inject)。

假设我们有这些限制:

  1. 我们无法重写过程以不使用动态 SQL

  2. 我们不能使用 sp_OACreate 等来使用正则表达式进行验证。

  3. 我们无法修改调用存储过程以在参数传递到存储过程之前验证参数的应用程序。

是否有一组字符可以过滤掉以确保我们不会受到 SQL 注入(inject)的影响?

最佳答案

我相信您需要担心三种不同的情况:

  • 字符串(任何需要引号的内容):'''' + replace(@string, '''', '''''') + ''''
  • 名称(任何不允许使用引号的名称):quotename(@string)
  • 不能引用的内容:这需要白名单

注意:来自用户控制的字符串变量中的所有内容( charvarcharncharnvarchar 等)来源必须使用上述方法之一。这意味着,即使您希望是数字的东西,如果存储在字符串变量中,也会被引用。

有关更多详细信息,请参阅<罢工>Microsoft Magazine (废弃链接:2016-10-19)

这是使用所有三种方法的示例:

EXEC 'SELECT * FROM Employee WHERE Salary > ''' +
REPLACE(@salary, '''', '''''') + -- replacing quotes even for numeric data
''' ORDER BY ' + QUOTENAME(@sort_col) + ' ' + -- quoting a name
CASE @sort_dir WHEN 'DESC' THEN 'DESC' END -- whitelisting

另请注意,通过在 EXEC 中内联执行所有字符串操作声明不关心截断问题。如果将中间结果分配给变量,则必须确保变量足够大以保存结果。如果你这样做SET @result = QUOTENAME(@name)你应该定义 @result至少包含 258 (2 * 128 + 2) 个字符。如果你这样做SET @result = REPLACE(@str, '''', '''''')你应该定义 @result大小为 @str 的两倍(假设 @str 中的每个字符都可以是引号)。当然,保存最终 SQL 语句的字符串变量必须足够大,以容纳所有静态 SQL 以及所有结果变量。

关于sql-server - 如何清理(防止SQL注入(inject))SQL Server中的动态SQL?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/4102387/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com