Oracle
 sql >> Datenbank >  >> RDS >> Oracle

Die Oracle-Prozedur gibt keine Ergebnisse zurück, wenn sie von einer Skriptaufgabe auf SSIS ausgeführt wird

Verwenden Sie zunächst nicht OleDb , Zeitraum. Microsoft fordert Sie auf, einen herstellerspezifischen Anbieter zu verwenden. Verwenden Sie ODP.NET von Oracle.

Zweitens müssen Sie zum Abrufen des Recordsets von Oracle SP refCursor zurückgeben .

Bearbeiten: Zu diesem Zeitpunkt wissen wir, dass Ihre Parameter Tabellen sind. Um dies zu verarbeiten, müssen Sie p.CollectionType = OracleCollectionType.PLSQLAssociativeArray hinzufügen zu Ihren Parametern

Ihr Code ist im Wesentlichen dieser:

Declare 
    obus_grp_id PKG_HOBS.Tnumber; -- numeric table value
    ostat_c PKG_HOBS.Tnumber;     -- numeric table value
    ostat_msg_x PKG_HOBS.Tmsg_500; -- string table value
BEGIN  
    PKG_HOBS.PRC_HOBS_GET_CLIENTID(obus_grp_id, ostat_c, ostat_msg_x);
END;

Ich sehe, dass Sie einen anonymen Block ausführen - Sie müssen dies nicht tun, da dies die Dinge für Sie komplizierter macht. Was Sie tun müssen, ist vb.net zu verwenden, um das Paket direkt auszuführen.

Fazit: Ihr aktueller ORACLE-Code tut nichts, um Ergebnisse an .NET auszugeben. Entfernen Sie die anonyme Sperre und Sie sind im Geschäft.

Hier ist der Code zur Verarbeitung Ihres Verfahrenstyps (lesen Sie in den Kommentaren)

Dim cmd As New OracleCommand("PKG_HOBS.PRC_HOBS_GET_CLIENTID", conn)
cmd.CommandType = CommandType.StoredProcedure

Dim p1 As New OracleParameter(":p1", OracleDbType.Int64, ParameterDirection.Output)
p1.CollectionType = OracleCollectionType.PLSQLAssociativeArray
p1.Size = 100  ' Declare more than you expect
' This line below is not needed for numeric types (date too???)
' p1.ArrayBindSize = New Integer(99) {} 
cmd.Parameters.Add(p1)

' Add parameter 2 here - same as 1

Dim p3 As New OracleParameter(":p3", OracleDbType.Varchar2, ParameterDirection.Output)
p3.CollectionType = OracleCollectionType.PLSQLAssociativeArray
p3.Size = 100 ' Declare more than you expect
' for string data types you need to allocate space for each element
p3.ArrayBindSize = Enumerable.Repeat(500, 100).ToArray() ' get 100 elements of 500 - size of returning string
' I don't know why you have problems referencing System.Linq but if you do...
'Dim intA() As Integer = New Integer(99) {} 
'For i as integer = 0 to intA.Length -1
'    intA(i) = 500
'Next

cmd.Parameters.Add(p3)
conn.Open()
cmd.ExecuteNonQuery()

' Ora number is not compatible to .net types. for example integer is something 
' between number(9) and (10). So, if number(10) is the type - you get Long in 
' return. Therefore use "Convert" 

' Also, you return arrays, so you need to process them as arrays - NOTE CHANGES


Dim oraNumbers() As OracleDecimal = CType(p1.Value, OracleDecimal())
Dim myP1Values(oraNumbers.Length - 1) As Long
For i as Integer = 0 To oraNumbers.Length - 1
    myP1Values(i) = Convert.ToInt64(oraNumbers(i).Value)
Next

oraNumbers = CType(p2.Value, OracleDecimal())
Dim myP2Values(oraNumbers.Length - 1) As Long
For i as Integer = 0 To oraNumbers.Length - 1
    myP2Values(i) = Convert.ToInt64(oraNumbers(i).Value)
Next    

Dim oraStrings() As OracleString= CType(p3.Value, OracleString())
Dim myP3Values(oraStrings.Length - 1) As String
For i as Integer = 0 To oraStrings.Length - 1
    myP3Values(i) = oraStrings(i).Value
Next

Und das ist der wichtigste Teil

Der wichtigste Teil ist, wie Sie Ihren deklarierten Typ füllen. Nehmen wir

TYPE Tnumber IS TABLE OF NUMBER INDEX BY BINARY_INTEGER;
v_num Tnumber;

v_num(1) := 1234567890;
v_num(2) := 2345678901;
v_num(3) := 3456789012;

Das (oben) wird funktionieren. Aber das wird fehlschlagen:

v_num(0) := 1234567890;
v_num(1) := 2345678901;
v_num(2) := 3456789012;

Und schließlich funktioniert dies mit einer Bedingung

v_num(2) := 1234567890;
v_num(3) := 2345678901;
v_num(4) := 3456789012;

Hier erhalten wir 4 Mitglieder in p1.Value aber unter dem Index 0 Sie werden oracle null haben . Sie müssten sich also hier damit befassen (wenn Sie eine solche Bedingung haben)

' instead of this 
myP2Values(i) = Convert.ToInt64(oraNumbers(i).Value)
' you will need first to check 
If oraNumbers(i).IsNull Then 
. . . . 

Also, die Hauptsache hier ist, WAS ist der Index Ihrer pl/sql-Tabelle?! Es muss mit etwas größer als 0 beginnen , und vorzugsweise von 1 . Und wenn Sie einen Index mit übersprungenen Zahlen haben, dh 2,4,6,8 , alle diese Leerzeichen sind Teil des zurückgegebenen Orakel-Arrays und es wird oracle null geben in ihnen

Hier ist eine Referenz