SQL+Informix:在进行插入时如何添加blob?(使用.NET(C#)SDK)

本文关键字:blob 使用 NET SDK 添加 插入 SQL+Informix 何添加 | 更新日期: 2023-09-27 17:58:30

我正在使用Informix和。NET SDK(C#):

基本上,在执行标准的insert-sql语句时,有没有任何方法可以插入blob?

INSERT INTO mytable (name, theblob) VALUES ('foo', ? what goes here ?);

哦,我的数据是以byte[]数组的形式存在的。

SQL+Informix:在进行插入时如何添加blob?(使用.NET(C#)SDK)

几个注意事项:

1) 您应该使用参数化查询

//Assuming you already have a connection somewhere that is opened.
var sql = "INSERT INTO mytable (name, theblob) VALUES (?, ?);";
using (var command = new IfxCommand(sql, connection))
{
    command.Parameters.Add(new IfxParameter()).Value = "foo";
    command.Parameters.Add(new IfxParameter()).Value = ifxBlob;
}


需要注意的几点是:Informix在客户端SDK 3.5.xC7(到目前为止)方面有一个错误。您可以在插入期间轻松地传入byte数组,但如果传入byte[]数组,则在进行更新时会出现609错误。相反,您必须使用IfxBlob对象。

public IfxBlob CreateIfxBlob(byte[] data)
{
    //Get the connection however you like and make sure it's open...
    //Obviously you should make this method handle exceptions and the such.
    IfxBlob blob = connection.GetIfxBlob();
    blob.Open(IfxSmartLOBOpenMode.ReadWrite);
    blob.Write(data);
    blob.Close();
    return blob;
}

您必须在更新过程中传递IfxBlob,所以您也可以在插入过程中传递。

此外,请记住,如果您试图设置null,则会出现错误。相反,如果值为null,则传入DBNull。价值

public Object AsDBValue(Object value) //Or this Object value if you want it as an extension
{
    if (value == null)
        return DBNull.Value;
    //Other checks
    if (value is Enum)
        return Convert.ChangeType(value, value.GetType().GetEnumUnderlyingType());
    //Is Blob?
    if (value is byte[])
        return GetIfxBlob(value as byte[]);
    return value;
}

不要指定参数类型

//These will lead to errors unless you typecast the parameters in the query.
new IfxParameter { IfxType = IfxType.Blob };
new IfxParameter { DbType = DbType.Binary };

如果你做了其中任何一个,你必须做以下事情:

  • 当Blob值不为空时"INSERT INTO mytable (name, theblob) VALUES (?, ?::blob);";
  • Blob值为空时"INSERT INTO mytable (name, theblob) VALUES (?, ?::byte);";

您可以看到,由于类型和值的不同,进行不同的查询将是一件令人头疼的事情。只是不要指定DbType或IfxType,而是让Informix。NET提供程序为您映射正确的类型(即使它不能在Update上正确映射byte[]数组)。

希望这对你来说是可行的,因为我经历了同样的痛苦,试图弄清楚这一点,并发现了我认为Informix中的一个错误。NET提供程序(版本:3.5.xC7).

最好使用参数化查询。例如:

using(System.Data.SqlClient.SqlCommand cmd = new System.Data.SqlClient.SqlCommand("INSERT INTO mytable (name, theblob) VALUES ('foo', @binaryValue)", conn))
{
  cmd.Parameters.Add("@binaryValue", System.Data.SqlDbType.Text, 8000).Value = arraytoinsert;
  cmd.ExecuteNonQuery();
}

我假设您的列类型是Text。上述方法的原始来源于本帖。

我阅读了您的两条消息,这是帮助我的解决方案:

 byte[] data = File.ReadAllBytes(PathFile);
 StringBuilder sql = new StringBuilder();
sql.Append(" UPDATE  updater SET report = ?  where path = " + "''" + Path + "'' and status = 1;");
IfxCommand cmd = new IfxCommand(sql.ToString(), i_connect);
cmd.Parameters.Add("@binaryValue", IfxType.Byte).Value = data;
int res = cmd.ExecuteNonQuery();

PathFile-是一个File.txt

我的informix表:

   CREATE TABLE updater
 (
    nzp_up SERIAL PRIMARY KEY,
    version VARCHAR(50),
    status INT,
    path VARCHAR(200),
    key VARCHAR(100),
    soup VARCHAR(20),
    report TEXT
 );

这篇文章对解决我的问题非常有用,所以我想分享我的解决方案,它可能会帮助其他人。这是完整的代码:

        try
        {
            //pFoto is a byte[] loaded in another method.
            if (pFoto != null && pFoto.Length > 0)
            {
                StringBuilder sentenciaSQL = new StringBuilder();
                sentenciaSQL.Append("INSERT INTO bd_imagenes:imagenes ");
                sentenciaSQL.Append("(identificador, cod_imagen, fecha_desde, fecha_hasta, fecha_grabacion, usuario, sec_transaccion, imagen) ");
                sentenciaSQL.Append("VALUES (?, 'FP', current, null, current, ?, 0, ?);");
                using (IfxConnection conIFX = new IfxConnection("Database=bd_imagenes; Server=xxxxxxxx; uid=xxxxxxx; password=xxxxxxxx; Enlist=true; Client_Locale=en_US.CP1252;Db_Locale=en_US.819"))
                {
                    conIFX.Open(); //<- Abro la conexion.
                    //Aqui convierto la foto en un BLOB:                        
                    IfxBlob blob = conIFX.GetIfxBlob();
                    blob.Open(IfxSmartLOBOpenMode.ReadWrite);
                    blob.Write(pFoto);
                    blob.Close(); 
                    //Creo el Comando con la SQL:
                    using (IfxCommand cmd = new IfxCommand(sentenciaSQL.ToString(), conIFX))
                    {
                        //Agrego los parámetros en el mismo orden que la SQL:
                        cmd.Parameters.Add(new IfxParameter()).Value = pCedula;
                        cmd.Parameters.Add(new IfxParameter()).Value = SecurityHandler.Auditoria.NombreUsuario;
                        cmd.Parameters.Add(new IfxParameter()).Value = blob;
                        //Ejecuto la Consulta:
                        Resultado = cmd.ExecuteNonQuery();
                    }
                    conIFX.Close();  
                }
                if (Resultado != 0) { retorno = true; }
            }
        }
        catch (IfxException ae)
        {
            if (exepcionesValidacion == null) { exepcionesValidacion = new ArrayList(); }
            exepcionesValidacion.Add(Util.CrearExcepcion(ae.Message, "ERROR_INESPERADO", ae.StackTrace));
        }
        catch (Exception ex)
        {
            if (exepcionesValidacion == null) { exepcionesValidacion = new ArrayList(); }
            exepcionesValidacion.Add(Util.CrearExcepcion(ex.Message, "ERROR_INESPERADO", ex.StackTrace));
        }
        return retorno;
    }