2010-07-08 98 views
13

在對錶進行某些更改後,數據庫中的某些觸發器失效。但似乎他們仍在工作。我遇到的唯一問題是,如果我使用SQL Developer,觸發器左側會出現紅色十字,表示它們無效。這是一個大問題嗎?觸發器在Oracle中無效

我知道我可以重新編譯觸發器來解決這個問題,但我不確定這是否值得關注。如果是這樣,我將需要回顧以前的數百項變更,並找出造成問題的原因。謝謝。

回答

16

每當我們將更改部署到數據庫對象時,依賴於它的任何代碼都將失效。這會影響觸發器,視圖和存儲過程。但是,下一次調用該代碼時,數據庫將自動重新編譯它。

所以我們不需要擔心這個,對吧?嗯,是的,達到一定程度。事情是,觸發器(或其他)的失效對我們來說是一個標誌,已經發生了可能影響觸發器操作的變化,這可能會產生副作用。最明顯的副作用是觸發器無法編譯。更巧妙地,觸發器編譯但在操作過程中失敗。

因此,在開發環境中強制重新編譯觸發器是一個好主意,以確保我們的更改不會從根本上破壞任何東西。但是當我們在生產中部署我們的變更時,我們可以跳過這一步,因爲我們確信所有事情都可以按需重新編譯。取決於我們的想法:)

Oracle提供了自動重新編譯模式中所有無效對象的機制。

  • 最直接的是使用DBMS_UTILITY.COMPILE_SCHEMA()。但是自從8i以來,這一直是個狡猾的行爲(因爲對Java存儲過程的支持引入了循環依賴的潛力),並且不再保證第一次成功地編譯所有對象。

  • 在9i中,Oracle給了我們一個腳本$ORACLE_HOME/rdbms/admin/utlrp.sql,它重新編譯了一些東西。不幸的是它需要SYSDBA訪問。

  • 在10g中他們添加了UTL_RECOMP包,它基本上完成了該腳本所做的一切。這是重新編譯大量對象的推薦方法。不幸的是,它也需要SYSDBA訪問。 Find out more

在Oracle 11g中引入了細粒度的依賴關係管理。這意味着對錶格的更改會以更精細的粒度(基本上是列級別而非表級別)進行評估,並且只有受更改直接影響的對象纔會受到影響。 Find out more

+0

謝謝,這個解釋看起來很不錯。我點擊上面的鏈接到10g的文檔,它說 您必須連接AS SYSDBA才能運行此腳本。 因此,看起來我必須以SYSDBA身份登錄。 – newguy 2010-07-08 03:42:09

+0

@Newguy - 哎呀,你是對的。 – APC 2010-07-08 03:52:33

0

根本不是一個大問題。

只需右鍵點擊它們重新編譯,你很好去...我從我自己的經驗寫這個。

如果您剛剛更改過的代碼有任何錯誤,它們將出現以便您可以修復它。編譯器會告訴你哪裏有問題(行號,變量名等),以防出錯。

+0

如果我什至不重新編譯觸發器怎麼辦?我打算將數據庫部署到十幾個客戶端的服務器,因此每次都要重新編譯會很麻煩。 – newguy 2010-07-08 02:04:47

+0

但我認爲重新編譯是必要的。它可以向你保證你的數據庫代碼沒有錯誤。耗時,但真的非常必要。當它們用紅色十字標記時,意味着觸發器引用的代碼被改變了。這是一個提醒,以便您可以採取措施重新編譯它以斷言沒有任何來自您的代碼更改的錯誤。 – 2010-07-08 02:14:14

+0

如果數以百計的觸發器,程序,功能和視圖無效,這是一個大問題。而花了我一個星期的時間來解決十分鐘重新編譯的後果。 – PhatHV 2016-04-11 07:38:47

0

如果觸發器正在工作,那麼當它觸發觸發器並在自動重新編譯後重試觸發器時,Oracle可能會捕獲ORA-04068錯誤。

+1

不,如果您嘗試執行任何標記爲「INVALID」的觸發器或存儲過程,Oracle將在執行之前首先嚐試重新編譯它。 ORA-04068與包狀態有關,與觸發器的狀態無關。 – 2010-07-08 04:56:26