使用 .Net 从 Oracle 获取插入记录的 ID 而不是 "TTCError"
Getting the ID of an inserted record instead of a "TTCError" from Oracle using .Net
我们正在更新较旧的应用程序以使用 “新” Oracle.ManagedDataAccess 而不是本地安装的 Oracle 客户端。但是从那以后像下面这样的简单语句。 ID 列填充了触发器和序列。
INSERT
INTO "SOME_TABLE" ("value1", "value2")
VALUES(:p, :p)
RETURNING "ID" INTO :LASTID
但这现在导致“TTC 错误”,没有内部异常,也没有异常中的任何其他细节。在例外情况下,堆栈跟踪只是对“OracleInternal.TTC.OraBufReader.ReadLengthAndData(Byte repOffset, Byte typeRep, Byte[]& dataBuffer, Int32& offset, Int32& bufLength, Boolean IgnoreData)
”的单次调用。
发生此异常时调试器中的调用堆栈为:
Oracle.ManagedDataAccess.dll!OracleInternal.TTC.OraBufReader.ReadLengthAndData(byte repOffset, byte typeRep, out byte[] dataBuffer, ref int offset, ref int bufLength, bool IgnoreData)
Oracle.ManagedDataAccess.dll!OracleInternal.TTC.MarshallingEngine.BufferToValue(byte repOffset, bool bIgnoreData)
Oracle.ManagedDataAccess.dll!OracleInternal.TTC.TTCExecuteSql.ReceiveExecuteResponse(ref OracleInternal.TTC.Accessors.Accessor[] defineAccessors, OracleInternal.TTC.Accessors.Accessor[] bindAccessors, bool bHasReturningParams, ref OracleInternal.Common.SQLMetaData sqlMetaData, OracleInternal.Common.SqlStatementType statementType, long noOfRowsFetchedLastTime, int noOfRowsToFetch, out int noOfRowsFetched, ref long queryId, int longFetchSize, long initialLOBFetchSize, long[] scnFromExecution, bool bAllInputBinds, int arrayBindCount, ref OracleInternal.ServiceObjects.DataUnmarshaller dataUnmarshaller, ref OracleInternal.TTC.TTCExecuteSql.MarshalBindParameterValueHelper marshalBindParamsHelper, out long[] rowsAffectedByArrayBind, bool bDefineDone, ref bool bMoreThanOneRowAffectedByDmlWithRetClause, ref System.Collections.Generic.List<OracleInternal.TTC.Accessors.TTCResultSet> implicitRSList, bool bLOBArrayFetchRequired)
Oracle.ManagedDataAccess.dll!OracleInternal.ServiceObjects.OracleCommandImpl.ExecuteNonQuery(string commandText, Oracle.ManagedDataAccess.Client.OracleParameterCollection paramColl, System.Data.CommandType commandType, OracleInternal.ServiceObjects.OracleConnectionImpl connectionImpl, int longFetchSize, long clientInitialLOBFS, OracleInternal.ServiceObjects.OracleDependencyImpl orclDependencyImpl, out long[] scnFromExecution, out Oracle.ManagedDataAccess.Client.OracleParameterCollection bindByPositionParamColl, ref bool bBindParamPresent, out Oracle.ManagedDataAccess.Client.OracleException exceptionForArrayBindDML, Oracle.ManagedDataAccess.Client.OracleConnection connection, ref Oracle.ManagedDataAccess.Client.OracleLogicalTransaction oracleLogicalTransaction, bool isFromEF)
Oracle.ManagedDataAccess.dll!Oracle.ManagedDataAccess.Client.OracleCommand.ExecuteNonQuery()
一位(很老的)post 评论说,在 table 上使用触发器时会发生这种情况,所以我让 DBA 创建了一个结构相同但结构不同的 table身份列。但这并没有改变任何东西,仍然是 信息性 消息“TTC 错误”。
我们正在使用 .Net Framework 4.6.2 和 Oracle.ManagedDataAccess v19.12.0。
数据库(从 v$version 读取)是:
Oracle Database 19c 企业版 19.0.0.0.0 版 - 生产
版本 19.11.0.0.0
编辑:
将库更新到 v19.13.0 并未解决此问题。
从来没有发现问题所在。我重写了这段代码,我改变的一件事是,我现在使用了命名参数……这个异常消失了。有点不知所措,但问题已经解决了。
我们正在更新较旧的应用程序以使用 “新” Oracle.ManagedDataAccess 而不是本地安装的 Oracle 客户端。但是从那以后像下面这样的简单语句。 ID 列填充了触发器和序列。
INSERT
INTO "SOME_TABLE" ("value1", "value2")
VALUES(:p, :p)
RETURNING "ID" INTO :LASTID
但这现在导致“TTC 错误”,没有内部异常,也没有异常中的任何其他细节。在例外情况下,堆栈跟踪只是对“OracleInternal.TTC.OraBufReader.ReadLengthAndData(Byte repOffset, Byte typeRep, Byte[]& dataBuffer, Int32& offset, Int32& bufLength, Boolean IgnoreData)
”的单次调用。
发生此异常时调试器中的调用堆栈为:
Oracle.ManagedDataAccess.dll!OracleInternal.TTC.OraBufReader.ReadLengthAndData(byte repOffset, byte typeRep, out byte[] dataBuffer, ref int offset, ref int bufLength, bool IgnoreData)
Oracle.ManagedDataAccess.dll!OracleInternal.TTC.MarshallingEngine.BufferToValue(byte repOffset, bool bIgnoreData)
Oracle.ManagedDataAccess.dll!OracleInternal.TTC.TTCExecuteSql.ReceiveExecuteResponse(ref OracleInternal.TTC.Accessors.Accessor[] defineAccessors, OracleInternal.TTC.Accessors.Accessor[] bindAccessors, bool bHasReturningParams, ref OracleInternal.Common.SQLMetaData sqlMetaData, OracleInternal.Common.SqlStatementType statementType, long noOfRowsFetchedLastTime, int noOfRowsToFetch, out int noOfRowsFetched, ref long queryId, int longFetchSize, long initialLOBFetchSize, long[] scnFromExecution, bool bAllInputBinds, int arrayBindCount, ref OracleInternal.ServiceObjects.DataUnmarshaller dataUnmarshaller, ref OracleInternal.TTC.TTCExecuteSql.MarshalBindParameterValueHelper marshalBindParamsHelper, out long[] rowsAffectedByArrayBind, bool bDefineDone, ref bool bMoreThanOneRowAffectedByDmlWithRetClause, ref System.Collections.Generic.List<OracleInternal.TTC.Accessors.TTCResultSet> implicitRSList, bool bLOBArrayFetchRequired)
Oracle.ManagedDataAccess.dll!OracleInternal.ServiceObjects.OracleCommandImpl.ExecuteNonQuery(string commandText, Oracle.ManagedDataAccess.Client.OracleParameterCollection paramColl, System.Data.CommandType commandType, OracleInternal.ServiceObjects.OracleConnectionImpl connectionImpl, int longFetchSize, long clientInitialLOBFS, OracleInternal.ServiceObjects.OracleDependencyImpl orclDependencyImpl, out long[] scnFromExecution, out Oracle.ManagedDataAccess.Client.OracleParameterCollection bindByPositionParamColl, ref bool bBindParamPresent, out Oracle.ManagedDataAccess.Client.OracleException exceptionForArrayBindDML, Oracle.ManagedDataAccess.Client.OracleConnection connection, ref Oracle.ManagedDataAccess.Client.OracleLogicalTransaction oracleLogicalTransaction, bool isFromEF)
Oracle.ManagedDataAccess.dll!Oracle.ManagedDataAccess.Client.OracleCommand.ExecuteNonQuery()
一位(很老的)post 评论说,在 table 上使用触发器时会发生这种情况,所以我让 DBA 创建了一个结构相同但结构不同的 table身份列。但这并没有改变任何东西,仍然是 信息性 消息“TTC 错误”。
我们正在使用 .Net Framework 4.6.2 和 Oracle.ManagedDataAccess v19.12.0。 数据库(从 v$version 读取)是: Oracle Database 19c 企业版 19.0.0.0.0 版 - 生产 版本 19.11.0.0.0
编辑: 将库更新到 v19.13.0 并未解决此问题。
从来没有发现问题所在。我重写了这段代码,我改变的一件事是,我现在使用了命名参数……这个异常消失了。有点不知所措,但问题已经解决了。