在动态列名中阻止SQL注入

Mr *_*ubs 3 .net sql vb.net postgresql sql-injection

如果没有在我的系统的一部分中编写一些动态的sql条件(使用Postgres),我无法逃脱.

我的问题是如何最好地避免SQL注入与我目前使用的方法.

编辑(推理):许多表中有许多列(一个数字增长(仅)并在其他地方维护).我需要一种允许用户决定他们想要查询哪个(预定义)列的方法(如果需要,还可以应用字符串函数).查询本身太复杂,用户无法自己编写,也无法访问数据库.有1000个用户有不同的要求,我需要保持尽可能灵活 - 我不应该重新访问代码,除非主要查询需要更改 - 此外,没有办法知道用户需要什么条件使用.

对于某些大型SQL查询,我有对象(通过Web服务接收)生成条件(生成方法在下面 - 它还不完美).

_FieldName是用户可编辑的(参数的名字,但它并不需要定),我很担心它可能是一个攻击向量.我在字段名称周围加上双引号(请参阅带引号的标识符)以尝试清理字符串,这样它就永远不会成为关键字.我还可以根据字段列表查找字段名称,但很难及时维护.

不幸的是,用户必须输入条件标准,我相信必须有更多我可以添加到sanatize方法?引用列名称是否安全?(我的有限测试似乎是这么认为的).

一个示例构建条件是"AND upper(brandloaded.make)像'O%'和upper(brandloaded.make)不像'OTHERBRAND'"......

任何帮助或建议表示赞赏.

Public Function GetCondition() As String
   Dim sb As New Text.StringBuilder

   'put quote around the table name in an attempt to prevent some sql injection
   'http://www.postgresql.org/docs/8.2/static/sql-syntax-lexical.html
   sb.AppendFormat(" {0} ""{1}"" ", _LogicOperator.ToString, _FieldName)

   Select Case _ConditionOperator
      Case ConditionOperatorOptions.Equals
          sb.Append(" = ")

      ...

   End Select

   sb.AppendFormat(" {0} ", Me.UniqueParameterName) 'for parameter

   Return Me.Sanitize(sb)

End Function

Private Function Sanitize(ByVal sb As Text.StringBuilder) As String

   'compare against a similar blacklist mentioned here: http://forums.asp.net/t/1254125.aspx

    sb.Replace(";", "")
    sb.Replace("'", "")
    sb.Replace("\", "")
    sb.Replace(Chr(8), "")

    Return sb.ToString

End Function

Public ReadOnly Property UniqueParameterName() As String
     Get
         Return String.Concat(":" _UniqueIdentifier)
     End Get
End Property
Run Code Online (Sandbox Code Playgroud)

And*_*ton 6

您可以从数据库中获取列名称并进行比较以检查用户是否输入了有效的列名称.

  • @MrShoubs你显然会在一段时间内缓存你对模式的了解 (3认同)
  • @AndrewMorton:大多数数据库都不允许你使用占位符作为标识符,至少我没有使用过它们. (2认同)