2009-06-09 35 views
2

有誰知道使用cx_Oracle在Oracle中使用用戶定義類型的更簡單方法嗎?cx_Oracle和用戶定義類型

舉例來說,如果我有這兩種類型:

CREATE type my_type as object(
component varchar2(30) 
,key varchar2(100) 
,value varchar2(4000)) 
/
CREATE type my_type_tab as table of my_type 
/

然後一個程序包my_package如下:

PROCEDURE my_procedure (param in my_type_tab); 

要在PL/SQL執行的程序,我可以做些什麼像這樣:

declare 
    l_parms my_type_tab; 
    l_cnt  pls_integer; 
begin 
    l_parms := my_type_tab(); 
    l_parms.extend; 
    l_cnt := l_parms.count; 
    l_parms(l_cnt) := my_type('foo','bar','hello'); 
    l_parms.extend; 
    l_cnt := l_parms.count; 
    l_parms(l_cnt) := my_type('faz','baz','world'); 
    my_package.my_procedure(l_parms); 
end; 

但是,我想知道如何在Python中做到這一點,simila R鍵此代碼:

import cx_Oracle 
orcl = cx_Oracle.connect('foo:[email protected]:5555/blah' + instance) 
curs = orcl.cursor() 
params = ??? 
curs.execute('begin my_package.my_procedure(:params)', params=params) 

如果該參數是一個字符串,我可以這樣做如上,但因爲它是一個用戶定義類型,我不知道如何調用它,而不訴諸純PL/SQL代碼。

編輯:對不起,我應該說我正在尋找方法來做更多的Python代碼而不是PL/SQL。

回答

0

您是否試圖更有效地填充對象表?

如果你可以做一個選擇,看看大宗收進第

-1

我不太清楚你硬編碼的意思,但你可以建立一個動態數組像這樣:

SQL> desc my_procedure 
Parameter Type  Mode Default? 
--------- ----------- ---- -------- 
P_IN  MY_TYPE_TAB IN 

SQL> declare 
    2  l_tab my_type_tab; 
    3 begin 
    4  select my_type(owner, table_name, column_name) 
    5  bulk collect into l_tab 
    6  from all_tab_columns 
    7  where rownum <= 10; 
    8  my_procedure (l_tab); 
    9 end; 
10/

PL/SQL procedure successfully completed 

這已經過Oracle 11.1.0.6的測試。

3

儘管cx_Oracle可以選擇用戶定義的類型,但它不支持將用戶定義的類型作爲綁定變量傳遞。因此,例如,下面的工作:

cursor.execute("select my_type('foo', 'bar', 'hello') from dual") 
val, = cursor.fetchone() 
print val.COMPONENT, val.KEY, val.VALUE 

但是你不能做的是建立一個Python對象,在把它作爲輸入參數,然後有cx_Oracle「翻譯」的Python對象到Oracle類型。所以我會說你將不得不在PL/SQL塊中構造你的輸入參數。

可以在Python列表傳遞,所以下面應該工作:

components=["foo", "faz"] 
values=["bar", "baz"] 
keys=["hello", "world"] 
cursor.execute(""" 
declare 
    type udt_StringList is table of varchar2(4000) index by binary_integer; 
    l_components udt_StringList := :p_components; 
    l_keys udt_StringList := :p_keys; 
    l_values udt_StringList := :p_values; 
    l_parms my_type_tab; 
begin 
    l_parms.extend(l_components.count); 
    for i in 1..l_components.count loop 
    l_parms(i) := my_type(l_components(i), l_keys(i), l_values(i)); 
    end loop; 

    my_package.my_procedure(l_parms); 
end;""", p_components=components, p_values=values, p_keys=keys)