MySQL觸發器

觸發器:當一張表發生了某件事(插入、刪除、更新操作),然後自動觸發了預先編寫好的若干條SQL語句。

一、創建觸發器
(1)創建只有一個執行語句的觸發器
(2)創建有多個執行語句的觸發器
二、查看觸發器
(1)show triggers語句查看觸發器信息
(2)在triggers表中查看觸發器信息

三、使用觸發器
四、刪除觸發器


一、創建觸發器
(1)創建只有一個執行語句的觸發器

創建一個觸發器的語法如下:

create trigger trigger_name trigger_time trigger_event
on tbl_name for each row trigger_stmt
  • trigger_name標識觸發器名稱,用戶自行指定。
  • trigger_time標識觸發時機,可以指定爲before或after。
  • trigger_event標識觸發事件,包括insert、update和delete。
  • tbl_name標識建立觸發器的表名,即在哪張表上建立觸發器。
  • trigger_stmt是觸發器執行語句。

【例1】創建一個單執行語句的觸發器,SQL語句如下:

mysql> create table account (acct_num int,amount decimal(10,2));
Query OK, 0 rows affected (0.12 sec)

mysql> create trigger ins_sum before insert on account
    -> for each row set @sum = @sum + NEW.amount;
Query OK, 0 rows affected (0.07 sec)

mysql> set @sum = 0;
Query OK, 0 rows affected (0.05 sec)

mysql> insert into account values(1,1.00),(2,2.00);
Query OK, 2 rows affected (0.06 sec)
Records: 2  Duplicates: 0  Warnings: 0

mysql> select @sum;
+------+
| @sum |
+------+
| 3.00 |
+------+
1 row in set (0.00 sec)

首先創建一個account表,表中有兩個字段acct_num和amount,接着創建一個名爲ins_sum的觸發器,觸發的條件是向數據表account插入數據之前,對新插入的amount字段值進行求和計算。

(2)創建有多個執行語句的觸發器

創建多個執行語句的觸發器的語法如下:

create trigger trigger_name trigger_time trigger_event
on tbl_name for each row
begin
語句執行列表
end 
  • trigger_name標識觸發器的名稱,用戶自行指定
  • trigger_time標識觸發時機,可以指定爲before或after
  • trigger_event標識觸發事件,包括insert、update和delete
  • table_name標識建立觸發器的表名,即在哪張表上建立觸發器
  • 觸發器程序可以使用begin和end作爲開始和結束,中間包含多條語句

【例2】創建一個包含多個執行語句的觸發器,sql語句如下:

mysql> create table test1(a1 int);
Query OK, 0 rows affected (0.10 sec)

mysql> create table test2(a2 int);
Query OK, 0 rows affected (0.10 sec)

mysql> create table test3(a3 int not null auto_increment primary key);
Query OK, 0 rows affected (0.08 sec)

mysql> create table test4(
    -> a4 int not null auto_increment primary key,
    -> b4 int default 0
    -> );
Query OK, 0 rows affected (0.10 sec)

delimiter //
mysql> create trigger testref before insert on test1
    -> for each row begin
    -> insert into test2 set a2 = NEW.a1;
    -> delete from test3 where a3 = NEW.a1;
    -> update test4 set b4 = b4 + 1 where a4 = NEW.a1;
    -> end
    -> //
Query OK, 0 rows affected (0.07 sec)

mysql> delimiter ;
mysql> insert into test3(a3) values
    -> (null),(null),(null),(null),(null),
    -> (null),(null),(null),(null),(null);
Query OK, 10 rows affected (0.06 sec)
Records: 10  Duplicates: 0  Warnings: 0

mysql> insert into test4 (a4) values
    -> (0),(0),(0),(0),(0),(0),(0),(0),(0),(0);
Query OK, 10 rows affected (0.06 sec)
Records: 10  Duplicates: 0  Warnings: 0

上面的代碼創建了一個名爲testref的觸發器,這個觸發器的條件是在向表test1插入數據前執行觸發器的語句,具體執行代碼如下:

mysql> insert into test1 values
    -> (1),(3),(1),(7),(1),(8),(4),(4);
Query OK, 8 rows affected (0.07 sec)
Records: 8  Duplicates: 0  Warnings: 0

4個表的數據如下:

mysql> select * from test1;
+------+
| a1   |
+------+
|    1 |
|    3 |
|    1 |
|    7 |
|    1 |
|    8 |
|    4 |
|    4 |
+------+
8 rows in set (0.00 sec)

mysql> select * from test2;
+------+
| a2   |
+------+
|    1 |
|    3 |
|    1 |
|    7 |
|    1 |
|    8 |
|    4 |
|    4 |
+------+
8 rows in set (0.00 sec)

mysql> select * from test3;
+----+
| a3 |
+----+
|  2 |
|  5 |
|  6 |
|  9 |
| 10 |
+----+
5 rows in set (0.00 sec)

mysql> select * from test4;
+----+------+
| a4 | b4   |
+----+------+
|  1 |    3 |
|  2 |    0 |
|  3 |    1 |
|  4 |    2 |
|  5 |    0 |
|  6 |    0 |
|  7 |    1 |
|  8 |    1 |
|  9 |    0 |
| 10 |    0 |
+----+------+
10 rows in set (0.00 sec)

執行結果顯示,在向test1插入記錄的時候,test2、test3、test4都發生了變化。從這個例子看insert觸發了觸發器,向test2中插入了test1中的值,刪除了test3中相同的內容,同時更新了test4中的b4,即與插入的值相同的個數。

二、查看觸發器
(1)show triggers語句查看觸發器信息

【例3】通過show triggers命令查看一個觸發器,代碼如下:

mysql> create table myevent
    -> (
    -> id int(11) default null,
    -> evt_name char(20) default null
    -> );
Query OK, 0 rows affected (0.11 sec)

mysql> create trigger trig_update after update on account
    -> for each row insert into myevent values(1,'after update');
Query OK, 0 rows affected (0.04 sec)

使用show triggers命令查看觸發器:

mysql> show triggers \G
*************************** 1. row ***************************
             Trigger: ins_sum
               Event: INSERT
               Table: account
           Statement: set @sum = @sum + NEW.amount
              Timing: BEFORE
             Created: 2019-09-08 13:37:29.40
            sql_mode: STRICT_TRANS_TABLES,NO_ENGINE_SUBSTITUTION
             Definer: root@localhost
character_set_client: gbk
collation_connection: gbk_chinese_ci
  Database Collation: utf8mb4_0900_ai_ci
*************************** 2. row ***************************
             Trigger: trig_update
               Event: UPDATE
               Table: account
           Statement: insert into myevent values(1,'after update')
              Timing: AFTER
             Created: 2019-09-08 14:27:16.39
            sql_mode: STRICT_TRANS_TABLES,NO_ENGINE_SUBSTITUTION
             Definer: root@localhost
character_set_client: gbk
collation_connection: gbk_chinese_ci
  Database Collation: utf8mb4_0900_ai_ci
*************************** 3. row ***************************
             Trigger: testref
               Event: INSERT
               Table: test1
           Statement: begin
insert into test2 set a2 = NEW.a1;
delete from test3 where a3 = NEW.a1;
update test4 set b4 = b4 + 1 where a4 = NEW.a1;
end
              Timing: BEFORE
             Created: 2019-09-08 14:12:34.15
            sql_mode: STRICT_TRANS_TABLES,NO_ENGINE_SUBSTITUTION
             Definer: root@localhost
character_set_client: gbk
collation_connection: gbk_chinese_ci
  Database Collation: utf8mb4_0900_ai_ci
3 rows in set (0.00 sec)
  • Trigger表示觸發器的名稱
  • Event表示激活觸發器的事件
  • Table表示激活觸發器的操作對象表
  • Timing表示觸發器觸發的時間
  • Statement表示觸發器執行的操作
(2)在triggers表中查看觸發器信息

在MySQL中所有觸發器的定義都存在information_schema數據庫的triggers表格中,可以通過查詢命令select來查看,具體語法如下:

mysql> select * from information_schema.triggers where trigger_name = 'trig_update' \G
*************************** 1. row ***************************
           TRIGGER_CATALOG: def
            TRIGGER_SCHEMA: test
              TRIGGER_NAME: trig_update
        EVENT_MANIPULATION: UPDATE
      EVENT_OBJECT_CATALOG: def
       EVENT_OBJECT_SCHEMA: test
        EVENT_OBJECT_TABLE: account
              ACTION_ORDER: 1
          ACTION_CONDITION: NULL
          ACTION_STATEMENT: insert into myevent values(1,'after update')
        ACTION_ORIENTATION: ROW
             ACTION_TIMING: AFTER
ACTION_REFERENCE_OLD_TABLE: NULL
ACTION_REFERENCE_NEW_TABLE: NULL
  ACTION_REFERENCE_OLD_ROW: OLD
  ACTION_REFERENCE_NEW_ROW: NEW
                   CREATED: 2019-09-08 14:27:16.39
                  SQL_MODE: STRICT_TRANS_TABLES,NO_ENGINE_SUBSTITUTION
                   DEFINER: root@localhost
      CHARACTER_SET_CLIENT: gbk
      COLLATION_CONNECTION: gbk_chinese_ci
        DATABASE_COLLATION: utf8mb4_0900_ai_ci
1 row in set (0.03 sec)
  • trigger_schema表示觸發器 所在的數據庫
  • trigger_name後面是觸發器的名稱
  • event_object_table表示在哪個數據表上觸發
  • action_statement表示觸發器觸發的時候執行的具體操作
  • action_orientation是row表示在每條記錄上都觸發
  • ation_timing表示觸發的時刻是after,剩下的是和系統相關的信息

也可以不指定觸發器名稱,這樣查看所有的觸發器,命令如下:

select * from information_schema.triggers \G
三、使用觸發器

觸發程序與表相關,當對錶執行insert、delete或update語句時,將激活觸發程序,可以將觸發程序設置爲在執行語句之前或之後激活。例如,可以在從表中刪除每一行之前或在更新每一行之後激活觸發程序。

【例4】創建一個在account表插入記錄之後更新myevent數據表的觸發器,sql語句如下:

mysql> create trigger trig_insert after insert on account
    -> for each row insert into myevent values(2,'after insert');
Query OK, 0 rows affected (0.02 sec)

mysql> insert into account values (1,1.00),(2,2.00);
Query OK, 2 rows affected (0.03 sec)
Records: 2  Duplicates: 0  Warnings: 0

mysql> select * from myevent;
+------+--------------+
| id   | evt_name     |
+------+--------------+
|    2 | after insert |
|    2 | after insert |
+------+--------------+
2 rows in set (0.00 sec)

從執行的結果來看,是創建了一個名稱爲trig_insert的觸發器,是在向account插入記錄之後進行觸發的,執行的操作是向表myevent插入一條記錄。

四、刪除觸發器

使用drop trigger語句可以刪除MySQL中已經定義的觸發器,刪除觸發器語法格式如下:

drop trigger [schema_name.] trigger_name
  • schema_name表示數據庫名稱,可選。如果省略了,將會從當前數據庫中捨棄觸發程序
  • trigger_name是要刪除的觸發器的名稱

【例5】刪除一個觸發器,sql語句如下:

mysql> drop trigger ins_sum;
Query OK, 0 rows affected (0.06 sec)

觸發器ins刪除成功。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章