2015-10-25 2 views
2

У меня есть пользовательский тип, который выглядит как этотODP.net передать UDT в таблице хранимой процедуры в C#

create or replace TYPE order_type AS OBJECT 
(
    order_type VARCHAR2 (50), 
    quantity VARCHAR2 (50), 
    price NUMBER, 

); 

таблица определяется как ниже

create or replace TYPE order_tabtype AS TABLE OF order_type; 

хранимой процедура

PROCEDURE create_order (acc_number VARCHAR2, 
          order_items devs.order_tabtype, 
          confirmation_num OUT VARCHAR2) 
    IS 

Как мне подготовить классы C#, чтобы заставить мой вызов хранимой процедуры работать. Большинство примеров, которые я упоминал, либо передают UDT как массив, либо существует только таблица типа по умолчанию. Но мне нужно передать пользовательский тип как таблицу.

+1

Для работы с пользовательскими типами в общем, есть автоматический мастер генерации коды входит в Oracle Developer Tools для Visual Studio. См. Эту ссылку для получения дополнительной информации: https://apexapps.oracle.com/pls/apex/f?p=44785:24:103077088849673:::24:P24_CONTENT_ID,P24_PROD_SECTION_GRP_ID,P24_PREV_PAGE:10199,,24 Также вы не можете привязываться к Таблицы PL/SQL из ODP.NET хотя (order_tabtype). Таким образом, вы не должны использовать тип TABLE в качестве входного параметра (исключением является «Index-by Tables», также известный как ассоциативные массивы, но они являются скалярными типами и не применяются здесь) –

ответ

3

Вот простой пример, который я использую для UDT в демонстрации ODP.NET. Здесь проходят в трех случаях UDT в таблице в качестве переменного связывания:

void Main() 
{ 
    using (var connection = new OracleConnection("DATA SOURCE=hq_pdb_tcp;PASSWORD=oracle;USER ID=HUSQVIK")) 
    { 
     connection.Open(); 

     using (var command = connection.CreateCommand()) 
     { 
      command.CommandText = "DECLARE x SYS.ODCISECOBJTABLE := :p; BEGIN :r := x.COUNT; END;"; 

      var parameter = command.CreateParameter(); 
      parameter.Direction = ParameterDirection.Input; 
      parameter.ParameterName = "p"; 
      parameter.OracleDbType = OracleDbType.Array; 
      parameter.UdtTypeName = "SYS.ODCISECOBJTABLE"; 
      parameter.Value = 
       new OdciSecObjTable 
       { 
        Values = new OdciSecObj[] 
        { 
         new OdciSecObj { POBJSCHEMA = "V1", POBJNAME = "V2", OBJSCHEMA = "V3", OBJNAME = "V4" }, 
         new OdciSecObj { POBJSCHEMA = "V5", POBJNAME = "V6", OBJSCHEMA = "V7", OBJNAME = "V8" }, 
         new OdciSecObj { POBJSCHEMA = "V9", POBJNAME = "V10", OBJSCHEMA = "V11", OBJNAME = "V12" } 
        } 
       }; 

      command.Parameters.Add(parameter); 

      var resultParameter = command.CreateParameter(); 
      resultParameter.Direction = ParameterDirection.Output; 
      resultParameter.ParameterName = "r"; 
      resultParameter.OracleDbType = OracleDbType.Decimal; 

      command.Parameters.Add(resultParameter); 

      command.ExecuteNonQuery(); 
      Console.WriteLine(((OracleDecimal)resultParameter.Value).Value); 
     } 
    } 
} 

[OracleCustomTypeMapping("SYS.ODCISECOBJTABLE")] 
public class OdciSecObjTable : CustomCollectionTypeBase<OdciSecObjTable, OdciSecObj> 
{ 
} 

[OracleCustomTypeMapping("SYS.ODCISECOBJ")] 
public class OdciSecObj : CustomTypeBase<OdciSecObj> 
{ 
    [OracleObjectMapping("POBJSCHEMA")] 
    public string POBJSCHEMA; 
    [OracleObjectMapping("POBJNAME")] 
    public string POBJNAME; 
    [OracleObjectMapping("OBJSCHEMA")] 
    public string OBJSCHEMA; 
    [OracleObjectMapping("OBJNAME")] 
    public string OBJNAME; 

    public override void FromCustomObject(OracleConnection connection, IntPtr pointerUdt) 
    { 
     OracleUdt.SetValue(connection, pointerUdt, "POBJSCHEMA", POBJSCHEMA); 
     OracleUdt.SetValue(connection, pointerUdt, "POBJNAME", POBJNAME); 
     OracleUdt.SetValue(connection, pointerUdt, "OBJSCHEMA", OBJSCHEMA); 
     OracleUdt.SetValue(connection, pointerUdt, "OBJNAME", OBJNAME); 
    } 

    public override void ToCustomObject(OracleConnection connection, IntPtr pointerUdt) 
    { 
     POBJSCHEMA = (string)OracleUdt.GetValue(connection, pointerUdt, "POBJSCHEMA"); 
     POBJNAME = (string)OracleUdt.GetValue(connection, pointerUdt, "POBJNAME"); 
     OBJSCHEMA = (string)OracleUdt.GetValue(connection, pointerUdt, "OBJSCHEMA"); 
     OBJNAME = (string)OracleUdt.GetValue(connection, pointerUdt, "OBJNAME"); 
    } 
} 

public abstract class CustomCollectionTypeBase<TType, TValue> : CustomTypeBase<TType>, IOracleArrayTypeFactory where TType : CustomTypeBase<TType>, new() 
{ 
    [OracleArrayMapping()] 
    public TValue[] Values; 

    public override void FromCustomObject(OracleConnection connection, IntPtr pointerUdt) 
    { 
     OracleUdt.SetValue(connection, pointerUdt, 0, Values); 
    } 

    public override void ToCustomObject(OracleConnection connection, IntPtr pointerUdt) 
    { 
     Values = (TValue[])OracleUdt.GetValue(connection, pointerUdt, 0); 
    } 

    public Array CreateArray(int elementCount) 
    { 
     return new TValue[elementCount]; 
    } 

    public Array CreateStatusArray(int elementCount) 
    { 
     return new OracleUdtStatus[elementCount]; 
    } 
} 

public abstract class CustomTypeBase<T> : IOracleCustomType, IOracleCustomTypeFactory, INullable where T : CustomTypeBase<T>, new() 
{ 
    private bool _isNull; 

    public IOracleCustomType CreateObject() 
    { 
     return new T(); 
    } 

    public abstract void FromCustomObject(OracleConnection connection, IntPtr pointerUdt); 

    public abstract void ToCustomObject(OracleConnection connection, IntPtr pointerUdt); 

    public bool IsNull 
    { 
     get { return this._isNull; } 
    } 

    public static T Null 
    { 
     get { return new T { _isNull = true }; } 
    } 
} 
Смежные вопросы