OracleCommand.ExecuteNonQuery() lanzando una excepción

Gracias por tomarse el tiempo para mirar y ayudarme. Me estoy volviendo loco con lo que parece ser una operación de inserción muy fácil, pero parece que no puedo pasar esta parte. Esto es lo que tengo para el código:

 protected void InsertIntoMaterialDB()
    {
        ToroGeneral toro = new ToroGeneral();

        // Grab connection string.
        string conString = toro.GetOracle1ConnectionString();
        string insertQuery = "INSERT INTO MATERIALMOVEREQUEST (ORIGINATOR, REQUESTDATE, PARTNUMBER, REQUESTQTY, MOVEFROM, MOVETO, COMPLETEDBY, COMPLETION_DATE, COMMENTS, RESPONSETIME) "
                               + "values (:Originator, :RequestDate, :PartNumber, :RequestQty, :MoveFrom, :MoveTo, :CompletedBy, :CompletionDate, :ResponseTime, :Comments)";

        using(OracleConnection conn1 = new OracleConnection(conString))
        {    
             conn1.Open();
             OracleCommand cmd = conn1.CreateCommand();
             OracleTransaction myTrans;
             cmd.CommandText = insertQuery;
             myTrans = conn1.BeginTransaction(IsolationLevel.ReadCommitted);
             cmd.Transaction = myTrans;

             if (cmd.Connection.State == ConnectionState.Closed)
             {
                  cmd.Connection.Open();
             }

             DateTime rDate = DateTime.Parse(RequestDateTB.Text);
             DateTime cDate = DateTime.Parse(CompDateTB.Text);

             cmd.Parameters.AddWithValue("Originator", OracleType.VarChar).Value = OriginatorTB.Text;
             cmd.Parameters.AddWithValue("RequestDate", OracleType.DateTime).Value = rDate;
             cmd.Parameters.AddWithValue("PartNumber", OracleType.VarChar).Value = PartNumber.Text;
             cmd.Parameters.AddWithValue("RequestQty", OracleType.Number).Value = Convert.ToInt32(RequestQuantity.Text);
             cmd.Parameters.AddWithValue("MoveFrom", OracleType.VarChar).Value = MoveFromTB.Text;
             cmd.Parameters.AddWithValue("MoveTo", OracleType.VarChar).Value = MoveToTB.Text;
             cmd.Parameters.AddWithValue("CompletedBy", OracleType.VarChar).Value = CompletedByTB.Text;
             cmd.Parameters.AddWithValue("CompletionDate", OracleType.DateTime).Value = cDate;
             cmd.Parameters.AddWithValue("ResponseTime", OracleType.Number).Value = Convert.ToInt32(RespTimeTB.Text);
             cmd.Parameters.AddWithValue("Comments", OracleType.VarChar).Value = CommentsTB.Text;

             cmd.ExecuteNonQuery(); // THIS THROWS AN EXCEPTION.
             cmd.Transaction.Commit();
        }

    }

Pude hacer que todo funcionara excepto los dos campos de tipo 'FECHA' REQUESTDATE y COMPLETION_DATE. No sé qué estoy haciendo mal, excepto que cuando llega a la llamada ExecuteNonQuery(), arroja una excepción.

Si alguien tiene alguna sugerencia, sería muy apreciada.

preguntado el 12 de junio de 12 a las 18:06

¿Cuál es la excepción? Además, si ejecuta la consulta con las mismas entradas en Oracle, ¿se ejecuta eso? -

ORA-01740: faltan comillas dobles en el identificador EDITAR: Creo que me faltan "" o '' en mi instrucción INSERT ahora que lo pienso. -

ORA-01843: no es un mes válido cuando se apunta a: RequestDate -

3 Respuestas

Me he encontrado con un problema similar en el pasado. Utilice la función To_Date para convertir la cadena en una fecha que Oracle reconocerá.

INSERT INTO MATERIALMOVEREQUEST (ORIGINATOR, REQUESTDATE, PARTNUMBER, REQUESTQTY, MOVEFROM, MOVETO, COMPLETEDBY, COMPLETION_DATE, COMMENTS, RESPONSETIME) "
                           + "values (:Originator, To_Date(:RequestDate, 'YYYY-MM-DD-HH24:MI:SS'), :PartNumber, :RequestQty, :MoveFrom, :MoveTo, :CompletedBy, To_Date(:CompletionDate, 'YYYY-MM-DD-HH24:MI:SS'), :ResponseTime, :Comments)";

Luego, en sus parámetros, establezca el valor en una cadena.

cmd.Parameters.AddWithValue("RequestDate", OracleType.VarChar).Value = rDate.ToString("yyyy-MM-dd-hh:mm:ss");

Respondido el 13 de junio de 12 a las 21:06

Esto supone que la cuenta de usuario ha modificado la sesión en el nivel de la base de datos, lo que casi nunca ocurre en producción para los usuarios estándar. Tendría que decir que esta es una respuesta menos que deseable. - vende

Creo que un usuario que tiene derechos para manipular datos tiene la capacidad de causar mucho más daño que un usuario que tiene derechos de modificación de sesión en la base de datos. La alteración de la sesión dura solo mientras la conexión a la base de datos esté activa. Al conectarse a la base de datos a través de Benthic (o la herramienta de su elección), tiene la capacidad de establecer el formato de fecha, que utiliza el comando de modificación de sesión. - bwalk2895

asktom.oracle.com/pls/apex/… Este es solo un lugar que aconseja como tal. Hay muchos más..... - vende

La respuesta ha sido actualizada. Mirando hacia atrás, creo que esta es una solución más limpia de todos modos, menos tráfico a la base de datos. Es una peculiaridad extraña en el caso de Oracle en el que estoy trabajando y esto parece hacer que funcione. - bwalk2895

Para los campos de fecha que probablemente desee utilizar OracleType.DateTime y pase un valor DateTime que genere al analizar la cadena de entrada, por ejemplo:

AddWithValue("CompletedBy", OracleType.DateTime).Value = 
              DateTime.ParseExact(...CompletedByTB.Text...); 

Respondido el 12 de junio de 12 a las 18:06

Además de lo que Joe dijo anteriormente, noté un par de cosas: -

a) Está abriendo una transacción pero nunca revirtiéndola en caso de alguna excepción. Es posible que desee adjuntar esto con la instrucción try catch y revertir la transacción en caso de excepción y confirmar de lo contrario.

b) Siempre debe usar el bloque de uso alrededor de los objetos de conexión (acabo de editar su código en la pregunta). De esa manera, no tiene que cerrar y desechar la conexión explícitamente. Esto se debe a que todos los tipos de proveedores de conexión (incluido OracleConnection) implementan Desechable interfaz a través de su clase base "DbConnection".

Respondido el 12 de junio de 12 a las 18:06

Gracias por editar eso para mí. Tiene mucho sentido ahora que lo pienso. Probaré la solución de Joe y publicaré mis resultados. - se_brandon

"Es posible que desee adjuntar esto con la instrucción try catch y revertir la transacción en caso de excepción y confirmar de lo contrario" o, de manera más concisa, colocarlo en un bloque de uso (Dispose revertirá la transacción si no se ha confirmado). - Joe

No es la respuesta que estás buscando? Examinar otras preguntas etiquetadas or haz tu propia pregunta.