日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 运维知识 > 数据库 >内容正文

数据库

Oracle 原理:DML触发器和数据库触发器

發布時間:2024/10/14 数据库 78 豆豆
生活随笔 收集整理的這篇文章主要介紹了 Oracle 原理:DML触发器和数据库触发器 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

一、DML觸發器

觸發器的作用即當某個事件發生時會自動執行執行程序段里的內容。

觸發器可以作用于表或者視圖,可以指定在insert 或update 或delete? 操作前、操作時、操作后 執行特定的程序段。

CREATE [OR REPLACE] TRIGGER triggername BEFORE/INSTEAD OF/AFTER ---選擇事件觸發(前,時,后)執行 PL/SQL代碼塊[INSERT [OR] UPDATE [OR] DELETE] ---當執行 插入 、更新、刪除前觸發ON tblname_or_viewname ---確認作用的表或者視圖[Referencing {OLD [AS] old / NEW [AS] new }] [FOR EACH ROW] --指定行級觸發器,不指定就是表級觸發器[WHEN (condition)] --當符合condition的條件滿足時觸發 DECLARE-- local variables here BEGIN;--PL/SQL blockEND triggername ;

在sqlserver 中 Deleted 是一張臨時表存即將被更新刪除的老信息,對應Oracle 中的 :old? ,Inserted 是一張臨時表用來存即將插入更新的新信息,對應Oracle 中的 :new。 :new 和:old 表示即將操作的一行數據而不是代表整個數據集,所以,在用這兩個的時候通常要加上[FOR EACH ROW] 來指明行觸發器。 其中 對于update的操作實際上是先把數據放入:old再刪除再把新數據放入:new插入到數據庫中。

由于:old是存的是老數據是即將被刪除或更改的,所以更新old沒意義。after 已經完成的操作后再觸發,所以此時對新數據new進行操作是無意義的。當為after時,無法修改? ? ?:new的記錄。

對于多表視圖,是可以改變鍵保留表中的內容的。也可以對單表視圖j進行DML操作

表級觸發器在當對表或視圖事件觸發時,只執行1次。而行級觸發器在對表或視圖事件觸發時,每影響1行數據就會執行1次程序塊內容

在DML觸發器中 不能使用rollback ,commit 還有DDL語句。

新建練習表 department_tbl:

新建如下觸發器,比較效果

create view VW_department_tbl as select * from department_tbl; --------insert視圖VW_department_tbl時,給每行數據Leaders 默認值'BOSS'---- create or replace trigger departInsertDefault2Instead of insert --替換原有的insert語句,且Instead Of 只能作用于視圖, WHEN不能用于 INSTEAD OFon VW_department_tblFOR EACH ROW declare beginif :new.leaders is null theninsert into department_tbl values(:new.department,:new.all_salary,'BOSS');else insert into department_tbl values(:new.department,:new.all_salary,:new.leaders);end if; end departInsertDefault2 ; drop trigger departInsertDefault2; ----------------------------------- --------insert表department_tbl時,給每行數據Leaders 默認值'BOSS'---- create or replace trigger departInsertDefault1before insert on department_tbl FOR EACH ROWWHEN (new.leaders is null )declarebegin :new.leaders :='BOSS'; end departInsertDefault1 ; drop trigger departInsertDefault1;

對觸發器2執行

對觸發器1執行

新建觸發器3,

create or replace procedure dep_insert(dep in department_tbl.department%type ,sal in department_tbl.all_salary%type) is PRAGMA AUTONOMOUS_TRANSACTION; --自主事物處理 begininsert into department_tbl values(dep,sal,'BOSS');--update department_tbl set leaders='BOSS' where leaders is null and department = dep; --取不到還未提交的數據 commit; end dep_insert; / create or replace trigger departInsertDefault3after insert --after 無法修改基表的數據,需要自主事物處理的存儲過程配合,且新數據屬于未提交狀態on department_tblFOR EACH ROWWHEN (new.leaders is null)declarev_data department_tbl%rowtype; begin --update department_tbl set leaders='BOSS' where leaders is null and department = :new.department; --無法執行dep_insert( :new.department,:new.all_salary);end departInsertDefault3 ; drop trigger departInsertDefault3;

執行

總之,如果要修改數據建議用 before? ,after適用于數據校驗,而Instead of只能作用于視圖。

update 示例:

create or replace trigger departInsertDefault4before update on department_tblFOR EACH ROWwhen (old.department = new.department) declare begin :new.all_salary := :new.all_salary+:old.all_salary; end departInsertDefault4 ; / --drop trigger departInsertDefault4;truncate table department_tbl; insert into department_tbl(department,all_salary) values('部門1',2000); insert into department_tbl(department,all_salary,leaders) values('部門1',2000,'BOSS'); insert into department_tbl(department,all_salary,leaders) values('部門2',3000,'雇傭者1'); update department_tbl set department = '部門999' where Leaders is not null; update department_tbl set Leaders = 'boss' where Leaders is not null; commit; select * from department_tbl;

最后執行結果:

二、模式(DDL)觸發器

Create table obj_tbl( obj_name varchar2(30), obj_type varchar2(20), obj_date Date )create or replace trigger obj_trigger after Create --alter drop on SCHEMA BEGINinsert into obj_tbl values( ora_dict_obj_name,ora_dict_obj_type,SYSDATE); END; /

ora_client_ip_address用于返回客戶端的IP地址
ora_database_name用于返回當前數據庫名
ora_des_encrypted_password用于返回DES加密后的用戶口令
ora_dict_obj_name用于返回DDL操作所對應的數據庫對象名
ora_dict_obj_name_list(name_list_ OUT ora_name_list_t)用于返回字事件中被修改的對象名列表
ora_dict_obj_owner用于返回DDL操作所對應的對象的所有者名。
ora_dict_obj_ower_list(ower_list OUT ora_name_list_t)用于返回在事件中被修改對象的所有者列表
ora_dict_obj_type用于返回DDL操作所對應的數據庫對象的類型。
ora_grantee(user_list OUT ora_name_list_t)用于返回授權時事件授權者。
ora_instance_num用于返回歷程號。
ora_is_alter_column(column_name IN VARCHAR2)用于檢測特定列是否被修改
ora_is_creating_nested_table用于檢測是否正在建立嵌套表
ora_is_drop_column(column_name IN VARCHAR2)用于檢測特定列是否被刪除
ora_is_servererror(error_number)用于檢測是否返回了特定Oracle錯誤。
ora_login_user用于返回登錄用戶名
ora_sysevent?用于返回觸發 觸發器的系統時間名。

?

?

三、數據庫級觸發器

?

----數據庫啟動觸發器----- create or replace trigger db_trigger after startup on database begin insert into obj_tbl values( ora_sysevent,null,SYSDATE); end; / ----數據庫用戶登錄觸發器----- create or replace trigger user_trigger after logon on database begin insert into obj_tbl values( ora_login_user,ora_client_ip_address,SYSDATE); end; /

四、對觸發器的操作

alter tigger? ? tiggername? ?ENABLE/DISABLE? ? 打開關閉觸發器?

select * from dba_triggers/user_triggers? ?查詢觸發器信息

總結

以上是生活随笔為你收集整理的Oracle 原理:DML触发器和数据库触发器的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。