【问题标题】:Querying a database for username and password查询数据库的用户名和密码
【发布时间】:2013-11-25 00:08:50
【问题描述】:

我对 C# 完全陌生。我正在验证用户名和密码,区分大小写 来自数据库 sql server 2008。这是我的登录代码;我该怎么办?

SqlConnection conn = new SqlConnection(@"Data Source=.\SQLEXPRESS;Initial Catalog=db_WiBo;Integrated Security=True");

SqlCommand cmd = new SqlCommand("SELECT * from tb_Account where Username= '"+textBox1.Text+"'  AND Password= '"+textBox2.Text+"' ", conn);

conn.Open();
SqlDataReader reader = cmd.ExecuteReader()

if (reader.HasRows)
{
   reader.Close();
   this.Hide();
}

提前致谢

【问题讨论】:

  • 您的SqlCommand 有一个SQL Injection vulnerability。您似乎也以纯文本形式存储密码,这不好。
  • 您应该做的第一件事是通过使用参数化查询来消除较大的 SQL 注入风险。第二件事可能是检查数据库字段/表上的排序规则以启用区分大小写...第三件事是在数据库中散列密码。
  • +哈希密码,不要存储...并使用好的哈希函数:throwingfire.com/storing-passwords-securely

标签: c# sql-server sqlcommand


【解决方案1】:

1) 您应该使用存储过程或参数化查询而不是 SQL 连接。您的代码中已经存在巨大的 SQL Server 注入安全漏洞。

您遇到了什么问题?代码看起来不错 - 如果没有检索到记录,您确定输入与数据库中的数据匹配吗?

代码只是执行查询,如果找到,则关闭阅读器并隐藏表单。

您也不应该在数据库中存储原始密码 - 另一个安全漏洞。相反,对它们进行散列/加密,并根据输入中的散列/加密值检查该值。 为了区分大小写,您可以使用排序规则

http://technet.microsoft.com/en-us/library/ms184391.aspx

http://blog.sqlauthority.com/2007/04/30/case-sensitive-sql-query-search/

【讨论】:

    【解决方案2】:

    一些事情:

    1. 您缺少一个“;”在SqlDataReader reader = cmd.ExecuteReader() 的末尾。
    2. 如前所述,请使用 Stored Procedure 来表示您正在执行的操作。
    3. 如前所述,请使用 parameterized queries,因为您接受来自文本框的输入。
    4. 使用using statement 管理您的连接和命令对象。
    5. 完成后不要忘记.Close()您的连接。
    6. 哦,我差点忘记了,hash 你的密码!

    这是上面的一个例子:

    using (SqlConnection conn = new SqlConnection(@"Data Source=.\SQLEXPRESS;Initial Catalog=db_WiBo;Integrated Security=True"))
    {
       using (SqlCommand cmd = new SqlCommand(@"SELECT * from tb_Account where Username= '@username'  AND Password= '@password' ", conn))
       {
          cmd.Parameters.Add("@username", textBox1.Text);
          cmd.Parameters.Add("@password", textBox2.Text);
          conn.Open();
    
          SqlDataReader reader = cmd.ExecuteReader();
          if (reader.HasRows)
          {
             reader.Close();
             this.Hide();
          }
          conn.Close();
       }
    }
    

    【讨论】:

      【解决方案3】:

      除了您的 SQL 注入问题之外,您还需要使用排序规则或强制转换为二进制。我发现另一个 SO 问题有很多有用的东西:
      How to do a case sensitive search in WHERE clause (I'm using SQL Server)?

      【讨论】:

        【解决方案4】:

        首先:不要为此使用字符串 concat。这可以很容易地用于代码注入。

        您可以改用存储过程,或 LinQ to SQL,甚至使用内置的成员资格提供程序

        【讨论】:

          【解决方案5】:

          尽管已经指出了与安全性相关的设计问题,但如果您的 SQL Server 实例的默认排序规则不区分大小写,则您需要选择合适的排序规则。 SQL Server 安装的默认排序规则是[通常,取决于服务器区域设置]SQL_Latin1_General_Cp1_CI_AS,意思是 Latin-1 代码页,不区分大小写,区分重音。

          创建数据库时,可以为该数据库指定默认排序规则。并且在创建表时,您可以为每个charvarcharncharnvarchar 列指定要使用的排序规则。

          您也可以通过适当的 DDL 语句更改这些。请注意,更改 collat​​ino 可能会影响数据完整性,导致主键和唯一索引等内容被破坏。

          创建一个表并为其列指定排序规则很容易:

          create table account
          (
            id       int         not null identity(1,1) primary key clustered ,
            user_id  varchar(32) collate SQL_Latin1_General_Cp1_CS_AS not null unique ,
            password varchar(32) collate SQL_Latin1_General_Cp1_CS_AS not null unique ,
            ...
          )
          

          您也可以使用alter tablealter database 来更改排序规则。

          可以在http://technet.microsoft.com/en-us/library/ms180175.aspxhttp://technet.microsoft.com/en-us/library/ms188046.aspx 找到支持的排序规则

          你应该

          • 请注意,在比较 2 列时,混合排序规则可能会导致问题,并且
          • 注意其他人提出的安全问题。

          【讨论】:

            猜你喜欢
            • 1970-01-01
            • 2010-12-12
            • 2018-02-13
            • 2016-02-05
            • 2012-08-29
            • 1970-01-01
            • 1970-01-01
            • 2016-12-04
            • 1970-01-01
            相关资源
            最近更新 更多