Как отправить более 20 параметров в хранимую процедуру с помощью ODP.Net? - PullRequest
0 голосов
/ 28 апреля 2010

Переключение с драйвера Oracle Microsoft на ODP.NET версии 10.2.0.100. После изменения типов данных на OracleDBTypes в процедуре, которая работала безупречно с использованием System.Data.OracleClient, процедура завершается ошибкой, если мы пытаемся передать более 20 параметров. Возвращенная ошибка:

ORA-06550: строка 1, столбец 7: PLS-00306: неверный номер или типы аргументов при вызове ADD_TARP_EVENT. ORA-06550: строка 1, столбец 7: PL / SQL: оператор ignorede

Если уменьшить число параметров до менее 20, это сработает. Это известная проблема?

Вот код для создания параметров:

    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

А вот код для выполнения процедуры:

 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)

....

Ответы [ 3 ]

2 голосов
/ 28 апреля 2010

Меня удивило бы, что число 20 не так уж и велико, я думаю, что более вероятно, что вы перепутали какой-то параметр (достаточно легко сделать, когда их больше 20).

Но чтобы попробовать это, я предлагаю создать процедуру с 21 параметром, все из которых являются числами, а затем отправить 1 всем, чтобы вы могли убедиться, что это не просто неправильный тип.

0 голосов
/ 29 апреля 2010

Хранимая процедура «LOADER.ADD_TARP_EVENT» по умолчанию установила значения параметров процедуры в ноль, где это применимо на стороне сервера. Когда мы строили команду Oracle ADO, мы не заполняли параметры Null, поскольку в процедуре для них уже было установлено значение по умолчанию Null. Это прекрасно работает с ADO.NET. Очевидно, ODT требует, чтобы значения передавались как dbNull. Как только мы перешли в dbNull для значений, все работало как ожидалось.

0 голосов
/ 29 апреля 2010

Существует два способа вызова процедур оракула.Первый именуется нотацией

proc (p_1 => 'test', p2 => 1);

Второй позиционный

proc ('test', 1);

В именованной нотации вы можете поместить параметры в любом порядке и опустить все, которые определены с помощью DEFAULT.В позиционной нотации они должны быть в том порядке, в котором они определены, и только последние могут быть опущены.То есть, если вы задаете пять параметров, а процедура имеет шесть определенных, то предполагается, что недостающий является шестым.Опять же, шестой должен иметь по умолчанию.Выходной параметр не может иметь значение по умолчанию и должен быть указан.

Я не уверен, как ODP работает, чтобы выбрать, какой использовать (хотя это можно подтвердить, отслеживая сеанс с использованием DBMS_MONITOR и просматривая результирующий файл трассировки).

В любом случае, убедитесь, что имена параметров совпадают с именами в вашем коде.Oracle обрабатывает идентификаторы как заглавные, если они не заключены в кавычки.Кроме того, если какие-либо параметры не имеют значения DEFAULT, они ДОЛЖНЫ быть установлены в вызове (даже если установлено значение null).

...