2013-07-24 38 views
2

我有以下代码建立在C#(SQL注入攻击)动态查询

public DataSet GetProject(string projectID) 
{ 
    DataSet dataTable = new DataSet(); 
    DataAccess dataAccess = new DataAccess(); 
    OracleCommand commandOb = new OracleCommand(); 
    strQuery.Append("select projectName, managerName"); 
    strQuery.Append("from project "); 
    strQuery.Append("where projectID = '" + projectID + "'"); 

    cmd.CommandText = strQuery.ToString(); 
    dataTable = dataAccess.ExecuteDataAdapter(commandOb); 

    return dataTable; 
} 

这是建立查询并执行它的一个好方法是什么?这会对SQL注入攻击产生危害吗?

是否有建议的方法来动态构建查询。任何帮助,将不胜感激。

+1

从动态'走就走querys'尝试使用参数然后使用'string.Format(从ProjectID = {0}的项目中选择projectName,managerName“,projectID);' – MethodMan

+4

使用参数化查询或更好的方式,调用a存储过程... – user2480596

+0

'+ 1' StoredProcedure不能出错那 – MethodMan

回答

3

以这种方式构建查询确实会使其容易受到SQL注入攻击,除非您已手动转义输入(IE使'projectID'的值不可能通过使用数据库引擎特定的转义序列来更改查询结构)。但是,推荐的方法是使用参数化查询(有时称为“准备语句”)。通过参数化查询,您只需定义查询结构,然后分别提供输入值作为参数,从而防止通过SQL注入来更改查询的结构。

这里就是你们的榜样,改为使用参数:

public DataSet GetProject(string projectID) 
{ 
    DataSet dataTable = new DataSet(); 
    DataAccess dataAccess = new DataAccess(); 
    OracleCommand commandOb = new OracleCommand(); 
    strQuery = @"select projectName, managerName 
        from project 
        where projectID = :ProjectID" 

    cmd.CommandText = strQuery; 
    cmd.Parameters.AddWithValue("ProjectID", projectID); 
    dataTable = dataAccess.ExecuteDataAdapter(commandOb); 

    return dataTable; 
} 

参数:在查询“专案编号”将与“AddWithValue”的方法给定的值来代替。无论“projectID”变量中的值是什么,它都将作为WHERE子句的一部分进行评估。而之前,与['; DELETE FROM项目; - ]可能有不良改变您的查询内容如下影响:

select projectName, managerName 
    from project 
    where projectID = ''; DELETE FROM project;--' 
0

是的,查询很容易受到sql注射。如果projectID通过其他查询在您的应用程序中进行内部检索,则由于没有直接的用户输入而不易受到攻击。

但是,如果某些用户输入为:"=1' OR 'a'=a'",则将检索所有项目,以允许在未经适当授权的情况下访问数据。更糟的是,可以执行意外的命令,例如删除所有记录。

尽管如此,最好的做法是使用参数化查询或绑定参数以获得更好的性能和针对注入的安全性。参数化查询转义保留字符,但您仍然必须手写出所有查询。其他选择包括使用ORM等等。 http://www.troyhunt.com/2010/05/owasp-top-10-for-net-developers-part-1.html

using (var cn = new OracleConnection(connString)) 
{ 
    var sql = "select projectName, managerName from project where projectID = :p1"; 
    using (var cmd = new OracleCommand(sql, cn)) 
    { 
    cmd.BindByName = true; 
    cmd.Parameters.Add(new OracleParameter(":p1", OracleDbType.Varchar2, projectID, 
              ParameterDirection.Input)); 
    using (var adapter = new OracleDataAdapter(cmd)) 
    { 
     cn.Open(); 
     var dataSet = new DataSet(); 
     adapter.Fill(dataSet); 
     return dataSet; 
    } 
    } 
} 

注:

更多的信息和sql注射有用.net特定的博客系列,更见https://www.owasp.org/这是odp.net