這兩天在處理sqlserver通過連結的伺服器連oracle資料庫寫入資料到oracle資料庫,
在sqlserver的預存程序中,
begin tran
insert oracle.....
commit;
sqlserver 預存程序編譯通過,執行是報錯: OLE DB 提供者 "MSDAORA" 無法啟動分散式交易
後來在網上搜尋資料,有人指出是MSDTC服務設定的問題,
http://www.cnblogs.com/chnking/archive/2007/04/04/699891.html
按照他們的記錄修改msdtc服務的設定,還是沒有成功 。
後來看到通過執行oracle函數來處理事務
http://topic.csdn.net/t/20060531/12/4790992.html
這個確實可以,但在調用oracle函數時,又出現錯誤:
ORA-14551: cannot perform a DML operation inside a query
因為sqlserver執行oracle函數時的語句select * from openquery(ora,select funtest from dual)
是一個查詢語句,不能在函數中執行插入,提交,復原等動作。
又找到資料
http://www.cnblogs.com/pengyq/archive/2008/11/26/1341656.html
-----------------------
建立自由性交易, 使用名為autonomous_transaction的編譯指示(編譯命令,如, #include), 這個編譯命令要放在declare裡面.
Delcare or replace procedure procedure_name(params, types)
AS
PRAGMA AUTONOMOUS_TRANSACTION;
當程式執行的時候,pl/sql 會把autonomous_transaction當成獨立存在的地區來處理.
用途是用在記錄程式事件,不影響程式的進行.
---------------------------
在 oracle的函數中加入PRAGMA AUTONOMOUS_TRANSACTION; 終於是可以了。
=============================
最後的流程是:
oracle中的正式表:test
oracle中的暫存資料表:tmptest
oracle中的預存程序:sp_write_test (res out int),將資料從暫存資料表匯入到正是表,中間加上交易處理,成功返回1,失敗返回0
oracle中的函數:fun_write_tmptest return int,調用預存程序,並將預存程序的輸出參數res返回給調用者.
sqlserver的預存程序中先寫入到暫存資料表,暫存資料表全部寫完後,在調用函數 fun_write_tmptest將資料轉入到正式表,
select * from openquery(ora,'select fun_write_tmptest from dual');
保證正式表看到的資料是完整的。