【问题标题】:Inserting byte array into SQL Server将字节数组插入 SQL Server
【发布时间】:2016-07-27 04:12:18
【问题描述】:

我正在构造一个sql_insert_string 以在Microsoft.ApplicationBlocks.Data.SqlHelper 中使用,如下所示:

SqlHelper.ExecuteNonQuery(Transaction, CommandType.Text, sql_insert_string)

当我将鼠标悬停在 SQL 语句上时,它如下所示:

 string sql_insert_string = "Insert into images_table(image_id,     image_byte_array) values ('123', System.Byte[])

其中一个插入值是一个字节数组,如上所示。该变量在字节数组中具有值,例如 byte[6738] 。但是在sql_insert_string 被构造之后,它就变成了System.Byte[]image_byte_array 列类型为 varbinary(max)。数据库是 SQL Server 2008。因此数据库会抛出以下错误:

对象或列名丢失或为空。对于 SELECT INTO 语句,验证每一列都有一个名称。对于其他语句,请查找空别名。不允许使用定义为 \"\" 或 [] 的别名。将别名更改为有效名称。

【问题讨论】:

  • 您的 sql 字符串生成器只需在 byte[] 类型的变量上调用 ToString()。显示创建 sql 查询字符串的方法
  • 你不应该构造 SQL 语句 - 你应该使用参数来避免 SQL 注入攻击!
  • SqlParameter 不仅让你免于 SQL 注入,而且你不会有这样的问题,因为所有输入值都会被正确“转换”为 SqlParameters
  • 这不是您创建的正确 sql 语句。

标签: c# sql-server


【解决方案1】:

你可以像这样插入字节数组:

        private void FireSql(byte[] input)
        {
            const string sql_insert_string =
                "Insert into images_table(image_id, image_byte_array) values (@image_id, @image_byte_array)";

            SqlTransaction transaction = null; //wherever you get the transaction obj from.

            var imageIdParam = new SqlParameter("@image_id", SqlDbType.Int, 4)
            {
                Direction = ParameterDirection.Input,
                Value = 123
            }; //change the data type to whatever data type you are expecting

            var byteParam = new SqlParameter("@image_byte_array", SqlDbType.VarBinary)
            {
                Direction = ParameterDirection.Input,
                Size = input.Length,
                Value = input
            }; //change the data type to whatever data type you are expecting

            SqlHelper.ExecuteNonQuery(transaction, CommandType.Text, sql_insert_string, imageIdParam, byteParam);
        }

我建议查看像 Entity Framework(http://www.asp.net/entity-framework) 这样的 ORM (https://en.wikipedia.org/wiki/Object-relational_mapping) 来为您完成所有这些工作,同时更轻松地提高安全性和未来的更改。

【讨论】:

    【解决方案2】:

    您应该在构造 SQL 查询时使用 参数,这显然可以避免 SQL 注入攻击。您的查询是如何构建的还不清楚。 像这样的东西应该为你做。

    SqlParameter sParam = new SqlParameter("@image_byte_array", SqlDbType.VarBinary)
    {
     Value = image
    };
    SqlHelper.ExecuteNonQuery(Transaction, CommandType.Text, sql_insert_string, sParam)
    

    【讨论】:

      【解决方案3】:

      你可以使用

      string sql_insert_string = 
          String.Format("INSERT INTO images_table(image_id, image_byte_array) VALUES ('123', CAST('{0}' AS VARBINARY(MAX)))", System.Byte[].ToString());
      

      是的,正如@marc_s 评论的那样,您不应该将构建 SQL 语句作为安全问题。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2012-10-18
        • 2018-03-02
        • 1970-01-01
        • 1970-01-01
        • 2019-02-17
        • 2015-05-24
        • 2010-10-29
        • 1970-01-01
        相关资源
        最近更新 更多