[英]How do you Send More that 20 Parameters to a Stored Procedure Using ODP.Net?
Switching from Microsofts Oracle Driver to ODP.NET version 10.2.0.100. 从Microsoft的Oracle驱动程序切换到ODP.NET版本10.2.0.100。 After changing the data types to OracleDBTypes in a procedure, that worked perficetly using System.Data.OracleClient, the procedure fails if we try and pass in more that 20 parameters.
在使用System.Data.OracleClient正常运行的过程中将数据类型更改为OracleDBTypes之后,如果尝试传递20个以上的参数,则过程将失败。 The error returned is:
返回的错误是:
ORA-06550: line 1, column 7: PLS-00306: wrong number or types of arguments in call to 'ADD_TARP_EVENT' ORA-06550: line 1, column 7: PL/SQL: Statement ignorede
ORA-06550:第1行,第7列:PLS-00306:调用“ ADD_TARP_EVENT”时参数的数量或类型错误ORA-06550:第1行,第7列:PL / SQL:语句被忽略
If we reduce the number of parameters to less than 20 it works. 如果我们将参数数量减少到少于20个,它将起作用。 Is this a known issue?
这是一个已知的问题?
Here the code for creating the parameters: 下面是用于创建参数的代码:
Shared Function CreateTarpEventCommand(ByVal aTarpEvent As TARPEventType) As OracleCommand
Dim cmd As New OracleCommand
With aTarpEvent
cmd.Parameters.Add(New OracleParameter("I_facID_C", OracleDbType.Char)).Value = .FacilityShortName
cmd.Parameters.Add(New OracleParameter("I_facName_VC", OracleDbType.Varchar2)).Value = .FacilityLongName
cmd.Parameters.Add(New OracleParameter("I_client_VC", OracleDbType.Varchar2)).Value = .ComputerNameTarpIsRunningOn
cmd.Parameters.Add(New OracleParameter("I_TARP_Version_VC", OracleDbType.Varchar2)).Value = .TarpVersionNumber
cmd.Parameters.Add(New OracleParameter("I_NAS_Type_VC", OracleDbType.Varchar2)).Value = .FacilityNASSystemType
cmd.Parameters.Add(New OracleParameter("I_Aircraft1_Callsign_VC", OracleDbType.Varchar2)).Value = .Aircraft1Callsign
If .Aircraft1Type Is Nothing Then
cmd.Parameters.Add(New OracleParameter("I_Aircraft1_Type_VC", OracleDbType.Varchar2)).Value = .Aircraft1Type
End If
If .Aircraft1Category Is Nothing Then
cmd.Parameters.Add(New OracleParameter("I_Aircraft1_Cat_VC", OracleDbType.Varchar2)).Value = .Aircraft1Category
End If
cmd.Parameters.Add(New OracleParameter("I_Aircraft2_Callsign_VC", OracleDbType.Varchar2)).Value = .Aircraft2Callsign
If .Aircraft2Type Is Nothing Then
cmd.Parameters.Add(New OracleParameter("I_Aircraft2_Type_VC", OracleDbType.Varchar2)).Value = .Aircraft2Type
End If
If .Aircraft2Category Is Nothing Then
cmd.Parameters.Add(New OracleParameter("I_Aircraft2_Cat_VC", OracleDbType.Varchar2)).Value = .Aircraft2Category
End If
If .SensorShortName Is Nothing Then
cmd.Parameters.Add(New OracleParameter("I_Sensor_Name_VC", OracleDbType.Varchar2)).Value = .SensorShortName
End If
If .TarpConfigurationName Is Nothing Then
cmd.Parameters.Add(New OracleParameter("I_TARP_Config_Name_VC", OracleDbType.Varchar2)).Value = .TarpConfigurationName
End If
If .EntryCreatorID Is Nothing Then
cmd.Parameters.Add(New OracleParameter("I_Create_VC", OracleDbType.Varchar2)).Value = .EntryCreatorID
End If
If .LogAction Is Nothing Then
cmd.Parameters.Add(New OracleParameter("I_Log_Action_VC", OracleDbType.Varchar2)).Value = .LogAction
End If
cmd.Parameters.Add(New OracleParameter("I_TARP_Mode_VC", OracleDbType.Varchar2)).Value = .TarpOperatingMode
cmd.Parameters.Add(New OracleParameter("I_Min_Loss_N", OracleDbType.Decimal)).Value = .ClosestMeasureOfLoSS
If .MapName Is Nothing Then
cmd.Parameters.Add(New OracleParameter("I_MAP_NAME_VC", OracleDbType.Varchar2)).Value = .MapName
End If
If .TarpConfigurationFileHash Is Nothing Then
cmd.Parameters.Add(New OracleParameter("I_CONFIG_HASH_VC", OracleDbType.Varchar2)).Value = .TarpConfigurationFileHash
End If
Dim aDate As OracleDate = CType(.LossEventsMessages(0).LossEventTime, System.DateTime)
cmd.Parameters.Add(New OracleParameter("I_FIRST_LOSS_EVENT_DATE", OracleDbType.Date)).Value = aDate
cmd.Parameters.Add(New OracleParameter("I_FIRST_LOSS_EVENT_MS_N", OracleDbType.Int32)).Value = .LossEventsMessages(0).LossEventMilliSeconds
If .ZippedMapFiles Is Nothing Then
cmd.Parameters.Add(New OracleParameter("I_Map_File_BL", OracleDbType.Blob)).Value = .ZippedMapFiles
End If
cmd.Parameters.Add(New OracleParameter("I_TARP_Package_BL", OracleDbType.Blob)).Value = .ZippedTarpPackageWithoutMaps
cmd.Parameters.Add(New OracleParameter("rs_RESULTS", OracleDbType.RefCursor)).Direction = ParameterDirection.Output
End With
Return cmd
End Function
And here is the code for executing the procedure: 这是执行该过程的代码:
Dim workingDataSet As New DataSet
Dim oracleConnection As New OracleConnection
Dim cmd As New OracleCommand
Dim oracleDataAdapter As New OracleDataAdapter
Try
Using oracleConnection
oracleConnection.ConnectionString = System.Configuration.ConfigurationManager.AppSettings("MasterConnectionODT")
cmd = HelperDB.CreateTarpEventCommand(TarpEvent)
cmd.Connection = oracleConnection
cmd.CommandText = "LOADER.ADD_TARP_EVENT"
cmd.CommandType = CommandType.StoredProcedure
Using oracleConnection
oracleConnection.Open()
Dim aTransation As OracleTransaction = oracleConnection.BeginTransaction(IsolationLevel.ReadCommitted)
Try
Using oracleDataAdapter
oracleDataAdapter = New OracleDataAdapter(cmd)
oracleDataAdapter.TableMappings.Add("Results", "rs_Max")
oracleDataAdapter.Fill(workingDataSet)
.... ....
It would surprise me since 20 isn't such a high number, I'd think it's more likely that you're getting some parameter mixed up (easy enough to do when it's over 20 of them). 因为20的数字不是一个很高的数字,这会让我感到惊讶,我认为您更有可能混入一些参数(当超过20个时,很容易做到)。
But to try it out I suggest creating a procedure with 21 parameters, all being Numbers and then sending in 1 to all of them, that way you could make sure that it's not just a mistype. 但是要尝试一下,我建议创建一个包含21个参数的过程,所有参数均为数字,然后将1发送给所有参数,这样就可以确保它不仅是一个错误的类型。
There are two ways of calling oracle procedures. 有两种方法可以调用oracle过程。 The first is named notation
第一个是命名法
proc (p_1 => 'test', p2 => 1);
The second is positional 第二个是位置
proc ('test', 1);
In named notation, you can put the parameters in any order and omit any that are defined with a DEFAULT. 在命名符号中,您可以按任何顺序放置参数,并忽略使用DEFAULT定义的任何参数。 In positional notation, they must be in the order they are defined in and only the last ones can be omitted.
在位置表示法中,它们必须按照定义的顺序,并且只能省略最后一个。 That is, if you supply five parameters and the procedure has six defined, then it assumes the missing one is the sixth.
也就是说,如果您提供五个参数,并且该过程定义了六个,则假定缺少的一个是第六个。 Again, the sixth must have a DEFAULT.
同样,第六个必须具有默认值。 An output parameter cannot have a default and must be supplied.
输出参数不能具有默认值,必须提供。
I'm not sure how ODP works to choose which to use (though it could be confirmed by tracing the session using DBMS_MONITOR and looking at the resultant trace file). 我不确定ODP如何选择使用哪个(尽管可以通过使用DBMS_MONITOR跟踪会话并查看生成的跟踪文件来确认)。
Anyway, check that the names of the parameters match those in your code. 无论如何,请检查参数名称是否与代码中的名称匹配。 Oracle treats identifiers as uppercase unless quoted.
除非加引号,否则Oracle将标识符视为大写。 Also, if any parameters do not have a DEFAULT, they MUST be set in the call (even if set to null).
另外,如果任何参数没有默认值,则必须在调用中进行设置(即使设置为null)。
The stored procedure "LOADER.ADD_TARP_EVENT" defaulted the procedure parameter values to Null where applicable on the server side. 存储过程“ LOADER.ADD_TARP_EVENT”在服务器端适用的情况下,将过程参数值默认为Null。 When we built the ADO Oracle Command we did not populate the Null parameters, as they were already set to default to Null in the procedure.
在构建ADO Oracle Command时,我们没有填充Null参数,因为在该过程中已经将它们设置为默认值。 This worked great with ADO.NET.
这对于ADO.NET效果很好。 ODT aparently requires that the values be passed in as dbNull.
ODT显然要求将值作为dbNull传入。 Once we passed in dbNull for the values all worked as expected.
一旦我们为所有值传递dbNull,它们都将按预期工作。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.