1、觸發器的功能: a、實現比約束更為復雜的數據約束 b、可以檢查 SQL 所做的操作是否被允許 c、修改其他數據庫里表的數據 d、可以一次調用多個存儲過程 e、發送SQL Mail f、返回自定義錯誤信息 g、修改原來要操作的 SQL 語句 h、防止數據表結構更改或表被刪除 2、觸發器的種類主要分為DML 觸發器和DDL 觸發器兩種,其中DML觸發器又分為After 和 Instead Of 觸發器
使用 sp_settriggerorder 存儲過程進行觸發器排序,其參數均為字符串,參數一是觸發器名稱,參數二是激活觸發器的順序參數,可以為 FIRST,LAST和NONE,參數三是激活觸發器的動作,可以是 INSERT,UPDATE 和 DELETE
CREATE TRIGGER trigger_update_age_employee ON employee AFTER UPDATEAS PRINT '更新員工年齡'GOCREATE TRIGGER trigger_update_name_employee ON employee AFTER UPDATEAS PRINT '更新員工姓名'GOUPDATE employee SET age = 10 WHERE id=1 -- 進行觀察EXEC sp_settriggerorder 'trigger_update_age_employee','LAST',UPDATEGOUPDATE employee SET age = 10 WHERE id=11 -- 觸發器執行的順序改變了After 觸發器只能在數據表中使用,而 Instead Of 觸發器可以在數據表和視圖中使用。以下情況建議使用 Instead Of 觸發器: 1、數據庫的數據禁止修改,可以使用 Instead Of 觸發器來跳過 Update 修改記錄的 SQL 語句 2、有可能需要回滾修改的 SQL 語句,Instead Of 觸發器的回滾效率比 After 高。 3、在視圖中使用觸發器 4、用自己的方式修改數據,使用 Instead Of 觸發器來控制數據的修改方式和流程。
CREATE TRIGGER trigger_insert_employee ON employee INSTEAD OF INSERTAS PRINT 'employee 表插入數據'GO EXEC sp_help 'trigger_insert_employee' -- 查看觸發器信息EXEC sp_helptext 'trigger_insert_employee' -- 查看觸發器SQL文本修改觸發器的語法與修改存儲過程語法類似,只是將 CREATE 改變成 ALTER。觸發器重命名使用 sp_name 存儲過程
DDL 觸發器是SQL Server 2005 以后新增的觸發器類型,它在響應 DDL 語句時觸發,一般用于在數據庫中執行管理任務。
CREATE TRIGGER trigger_t1 ON ALL SERVER -- DDL 觸發器作用到當前服務器上所有數據庫,ON 可以指定某個數據庫對象 FOR DROP_TABLE,ALTER_TABLE --使用FOR或AFTER是一個意思,但DDL觸發器不支持INSTEAD OF觸發器。DROP_TABLE是激活 DDL 觸發器的事件AS PRINT '刪除表或修改表結構!'-- 創建數據庫 DDL 語句操作記錄表CREATE TABLE table_ddl_log( id INT NOT NULL IDENTITY(1,1) PRIMARY KEY, [event] NVARCHAR(100),-- 事件 [server] NVARCHAR(100), -- 服務器名 [database] NVARCHAR(100), -- 數據庫名 [schema] NVARCHAR(100),-- 架構名 [sql] NVARCHAR(MAX), -- SQL語句 [Operator] NVARCHAR(100), [date] datetime2 DEFAULT getdate())GO-- 創建 DDL 語句記錄觸發器ALTER TRIGGER trigger_ddl ON DATABASE -- 指定當前數據庫 FOR DDL_DATABASE_LEVEL_EVENTSAS DECLARE @log xml SET @log = EVENTDATA() INSERT ddl_log VALUES( @log.value('(/EVENT_INSTANCE/EventType)[1]','nvarchar(100)'), @log.value('(/EVENT_INSTANCE/ServerName)[1]','nvarchar(100)'), @log.value('(/EVENT_INSTANCE/DatabaseName)[1]','nvarchar(100)'), @log.value('(/EVENT_INSTANCE/SchemaName)[1]','nvarchar(100)'), @log.value('(/EVENT_INSTANCE/TSQLCommand)[1]','nvarchar(4000)'), CONVERT(nvarchar(100),CURRENT_USER), GETDATE() );GO1、在觸發器中使用 @@ROWCOUNT 獲取此次數據操作受影響行數; 2、在觸發器中使用 @@IDENTITY 獲取插入記錄的編號; 3、在UPDATE和INSERT觸發器里可以使用 Update(字段名) 來判斷某個字段是否被更改。
CREATE TRIGGER trigger_update_name_employee ON employee INSTEAD OF UPDATEAS SET NOCOUNT ON -- 不記錄行數提高性能,這是個運行時設置語句,不是編譯時語句 IF UPDATE(name) BEGIN PRINT '名字不能修改' RAISERROR('名字一旦確定不能修改',16,5) ENDGOUPDATE employee SET name = '張三' WHERE id = 1新聞熱點
疑難解答