您的位置:首页 > 教程 > Mysql/MariaDB > MySQL数据库 触发器 trigger

MySQL数据库 触发器 trigger

2022-06-16 19:53:45 来源:易采站长站 作者:

MySQL数据库 触发器 trigger

目录
一、基本概念1、作用2、触发器的优缺点2.1、优点2.2、缺点二、创建触发器1、基本语法2、触发对象3、触发时机4、触发事件5、注意事项三、查看触发器四、触发触发器五、删除触发器六、触发器的应用1、完善2、优化

xcZ站长之家-易采站长站-Easck.Com

一、基本概念

触发器是一种特殊类型的存储过程,触发器通过事件进行触发而被执行xcZ站长之家-易采站长站-Easck.Com

触发器>

xcZ站长之家-易采站长站-Easck.Com

1、作用

    写入数据表前,强制检验或转换数据(保证数据安全)触发器发生错误时,异动的结果会被撤销(事务安全)部分数据库管理系统可以针对数据定义语言DDL使用触发器,称为DDL触发器可以依照特定的情况,替换异动的指令>

    xcZ站长之家-易采站长站-Easck.Com

    2、触发器的优缺点

    xcZ站长之家-易采站长站-Easck.Com

    2.1、优点

      触发器可通过数据库中的相关表实现级联更改(如果一张表的数据改变,可以利用触发器实现对其他表的操作,用户不知道)保证数据安全,进行安全校验

      xcZ站长之家-易采站长站-Easck.Com

      2.2、缺点

        对触发器过分依赖,势必影响数据库的结构,同时增加了维护的复杂度造成数据在程序层面不可控

        xcZ站长之家-易采站长站-Easck.Com

        二、创建触发器

        xcZ站长之家-易采站长站-Easck.Com

        1、基本语法

        create trigger 触发器名字 触发时机 触发事件 on 表 for each row
        begin
        end

        xcZ站长之家-易采站长站-Easck.Com

        2、触发对象

        on> 触发器绑定表中所有行,没一行发生指定改变的时候,就会触发触发器xcZ站长之家-易采站长站-Easck.Com

        xcZ站长之家-易采站长站-Easck.Com

        3、触发时机

        每张表对应的行都有不同的状态,当SQL指令发生的时候,都会令行中数据发生改变,每一行总会有两种状态:数据操作前和数据操作后xcZ站长之家-易采站长站-Easck.Com

          before:>after: 数据已经发生改变后的状态

          xcZ站长之家-易采站长站-Easck.Com

          4、触发事件

          mysql中触发器针对的目标是数据发生改变,对应的操作只有写操作(增删改)xcZ站长之家-易采站长站-Easck.Com

            inert>update 更新操作delete 删除操作

            xcZ站长之家-易采站长站-Easck.Com

            5、注意事项

            一张表中,每一个触发时机绑定的触发事件对应的触发器类型只能有一个xcZ站长之家-易采站长站-Easck.Com

            一张表表中只能有一个对应的after>

            最多只能有6个触发器xcZ站长之家-易采站长站-Easck.Com

            before insert
            after insert
            before update
            after update
            before delete
            after delete
            

            需求:xcZ站长之家-易采站长站-Easck.Com

            下单减库存xcZ站长之家-易采站长站-Easck.Com

            有两张表,一张是商品表,一张是订单表(保留商品ID)每次订单生成,商品表中对应的库存就应该发生变化xcZ站长之家-易采站长站-Easck.Com

            创建两张表:xcZ站长之家-易采站长站-Easck.Com

            create table my_item(
                id int primary key auto_increment,
                name varchar(20) not null,
                count int not null default 0
            ) comment '商品表';
            
            create table my_order(
                id int primary key auto_increment,
                item_id int not null,
                count int not null default 1
            ) comment '订单表';
            
            insert my_item (name, count) values ('手机', 100),('电脑', 100), ('包包', 100);
            
            mysql> select * from my_item;
            +----+--------+-------+
            | id | name   | count |
            +----+--------+-------+
            |  1 | 手机   |   100 |
            |  2 | 电脑   |   100 |
            |  3 | 包包   |   100 |
            +----+--------+-------+
            3 rows in set (0.00 sec)
            
            mysql> select * from my_order;
            Empty set (0.02 sec)

            创建触发器:xcZ站长之家-易采站长站-Easck.Com

            如果订单表发生数据插入,对应的商品就应该减少库存xcZ站长之家-易采站长站-Easck.Com

            delimiter $$
            create trigger after_insert_order_trigger after insert on my_order for each row
            begin
                -- 更新商品库存
                update my_item set count = count - 1 where id = 1;
            end
            $$
            delimiter ;
            

            xcZ站长之家-易采站长站-Easck.Com

            三、查看触发器

            -- 查看所有触发器
            show triggers\G
            *************************** 1. row ***************************
                         Trigger: after_insert_order_trigger
                           Event: INSERT
                           Table: my_order
                       Statement: begin
            
                update my_item set count = count - 1 where id = 1;
            end
                          Timing: AFTER
                         Created: 2022-04-16 10:00:19.09
                        sql_mode: ONLY_FULL_GROUP_BY,STRICT_TRANS_TABLES,NO_ZERO_IN_DATE,NO_ZERO_DATE,ERROR_FOR_DIVISION_BY_ZERO,NO_ENGINE_SUBSTITUTION
                         Definer: root@localhost
            character_set_client: utf8mb4
            collation_connection: utf8mb4_general_ci
              Database Collation: utf8mb4_general_ci
            1 row in set (0.00 sec)
            -- 查看创建语句
            show crate trigger 触发器名字;
            -- eg:
            show create trigger after_insert_order_trigger;

            xcZ站长之家-易采站长站-Easck.Com

            四、触发触发器

            让触发器执行,让触发器指定的表中,对应的时机发生对应的操作xcZ站长之家-易采站长站-Easck.Com

            insert into my_order (item_id, count) values(1, 1);
            
            mysql> select * from my_order;
            +----+---------+-------+
            | id | item_id | count |
            +----+---------+-------+
            |  1 |       1 |     1 |
            +----+---------+-------+
            1 row in set (0.00 sec)
            
            mysql> select * from my_item;
            +----+--------+-------+
            | id | name   | count |
            +----+--------+-------+
            |  1 | 手机   |    99 |
            |  2 | 电脑   |   100 |
            |  3 | 包包   |   100 |
            +----+--------+-------+
            3 rows in set (0.00 sec)

            xcZ站长之家-易采站长站-Easck.Com

            五、删除触发器

            drop trigger 触发器名字;
            -- eg
            drop trigger after_insert_order_trigger;

            xcZ站长之家-易采站长站-Easck.Com

            六、触发器的应用

            记录关键字>

            xcZ站长之家-易采站长站-Easck.Com

            1、完善

            商品自动扣除库存xcZ站长之家-易采站长站-Easck.Com

            触发器针对的是数据表中的每条记录,每行数据再操作前后都有一个对应的状态xcZ站长之家-易采站长站-Easck.Com

            触发器在执行之前就将对应的数据状态获取到了:xcZ站长之家-易采站长站-Easck.Com

              将没有操作之前的数据状态都保存到old关键字中操作后的状态都放在new

              触发器中,可以通过old和new来获取绑定表中对应的记录数据xcZ站长之家-易采站长站-Easck.Com

              基本语法:xcZ站长之家-易采站长站-Easck.Com

              关键字.字段名xcZ站长之家-易采站长站-Easck.Com

              old和new并不是所有触发器都有xcZ站长之家-易采站长站-Easck.Com

                insert>delete 清除数据,没有new

                商品自动扣减库存:xcZ站长之家-易采站长站-Easck.Com

                delimiter $$
                create trigger after_insert_order_trigger after insert on my_order for each row
                begin
                    -- 通过new关键字获取新数据的id 和数量
                    update my_item set count = count - new.count where id = new.item_id;
                end
                $$
                delimiter ;

                触发触发器:xcZ站长之家-易采站长站-Easck.Com

                mysql> select * from my_order;
                +----+---------+-------+
                | id | item_id | count |
                +----+---------+-------+
                |  1 |       1 |     1 |
                +----+---------+-------+
                mysql> select * from my_item;
                +----+--------+-------+
                | id | name   | count |
                +----+--------+-------+
                |  1 | 手机   |    99 |
                |  2 | 电脑   |   100 |
                |  3 | 包包   |   100 |
                +----+--------+-------+
                insert into my_order (item_id, count) values(2, 3);
                mysql> select * from my_order;
                +----+---------+-------+
                | id | item_id | count |
                +----+---------+-------+
                |  1 |       1 |     1 |
                |  2 |       2 |     3 |
                +----+---------+-------+
                mysql> select * from my_item;
                +----+--------+-------+
                | id | name   | count |
                +----+--------+-------+
                |  1 | 手机   |    99 |
                |  2 | 电脑   |    97 |
                |  3 | 包包   |   100 |
                +----+--------+-------+
                

                xcZ站长之家-易采站长站-Easck.Com

                2、优化

                如果库存数量没有商品订单多怎么办?xcZ站长之家-易采站长站-Easck.Com

                -- 删除原有触发器
                drop trigger after_insert_order_trigger;
                -- 新增判断库存触发器
                delimiter $$
                create trigger after_insert_order_trigger after insert on my_order for each row
                begin
                    -- 查询库存
                    select count from my_item where id = new.item_id into @count;
                
                    -- 判断
                    if new.count > @count then
                        -- 中断操作,暴力抛出异常
                        insert into xxx values ('xxx');
                
                    end if;
                    
                    -- 通过new关键字获取新数据的id 和数量
                    update my_item set count = count - new.count where id = new.item_id;
                end
                $$
                delimiter ;
                

                结果验证:xcZ站长之家-易采站长站-Easck.Com

                mysql> insert into my_order (item_id, count) values(3, 101);
                ERROR 1146 (42S02): Table 'mydatabase2.xxx' doesn't exist
                mysql> select * from my_order;
                +----+---------+-------+
                | id | item_id | count |
                +----+---------+-------+
                |  1 |       1 |     1 |
                |  2 |       2 |     3 |
                +----+---------+-------+
                2 rows in set (0.00 sec)
                
                mysql> select * from my_item;
                +----+--------+-------+
                | id | name   | count |
                +----+--------+-------+
                |  1 | 手机   |    99 |
                |  2 | 电脑   |    97 |
                |  3 | 包包   |   100 |
                +----+--------+-------+
                3 rows in set (0.00 sec)

                到此这篇关于MySQL数据库 触发器 trigger的文章就介绍到这了,更多相关MySQL trigger内容请搜索易采站长站以前的文章或继续浏览下面的相关文章希望大家以后多多支持易采站长站!xcZ站长之家-易采站长站-Easck.Com

                如有侵权,请联系QQ:279390809 电话:15144810328

相关文章

  • mysql 5.7.30安装配置方法图文教程

    mysql 5.7.30安装配置方法图文教程

    之前把服务器里面的MySQL卸了重装,安装mysql时未做总结,换新电脑,补上安装记录,安装的时候,找了些网友的安装记录,发现好多坑 截个图,作为笔记,也正好留给需要的朋友们。
    2019-01-03
  • MySQL5.6免安装版环境配置图文教程

    MySQL5.6免安装版环境配置图文教程

    MySQL是一个小巧玲珑但功能强大的数据库,目前十分流行。但是官网给出的安装包有两种格式,一个是msi格式,一个是zip格式的。很多人下了zip格式的解压发现没有setup.exe,面对一堆文
    2019-01-04
  • Linux下安装mysql-8.0.20的教程详解

    Linux下安装mysql-8.0.20的教程详解

    ** Linux下安装mysql-8.0.20 ** 环境介绍 操作系统:CentOS 7 mysql下载地址:https://dev.mysql.com/downloads/mysql/ 下载版本:mysql-8.0.20-linux-glibc2.12-x86_64.tar.xz 卸载mysql 查看是否安装过mysql,命令:fin
    2020-05-24
  • linux环境下安装mysql数据库的详细教程

    linux环境下安装mysql数据库的详细教程

    1.安装数据库 1)yum -y install mysql-server(简单) yum命令自动从网上寻找mysql服务资源,下载至本地并完成安装 2)也可以自己在网上下载mysql服务,通过xftp传输至Linux系统,自己安装(一般安
    2020-06-20
  • MySQL8.0.20安装教程及其安装问题详细教程

    MySQL8.0.20安装教程及其安装问题详细教程

    原文地址:https://blog.csdn.net/m0_46579864/article/details/105981304 官网下载MySQL的安装包 1.下载链接如下: MySQL8.0.20版本 https://dev.mysql.com/doc/relnotes/mysql/8.0/en/news-8-0-20.html 其他版本:MySQL8.0.16版本
    2020-05-10
  • MySQL对数据库操作(创建、选择、删除)

    MySQL对数据库操作(创建、选择、删除)

    MySQL 创建数据库 我们可以在登陆 MySQL 服务后,使用 create 命令创建数据库,语法如下: CREATE DATABASE 数据库名; 以下命令简单的演示了创建数据库的过程,数据名为 RUNOOB: [root@host]# mysql
    2020-07-01
  • Linux系统MySQL8.0.19快速安装配置教程图解

    Linux系统MySQL8.0.19快速安装配置教程图解

    一、环境介绍 Linux系统使用yum安装MySQL需要从网上下载MySQL的一系列组件,这个过程非常耗时且有下载中断的可能,如果想要快速安装MySQL,可以先在网上将MySQL的离线包下载下来传到系
    2020-02-27
  • mysql 加了 skip-name-resolve不能链接数据库问题的解决方法

    mysql 加了 skip-name-resolve不能链接数据库问题的解决方法

    mysql 加了 skip-name-resolve不能链接的问题, 要确认 MySql 是否采用过主机名的授权 在 MySql Server 的配置文件 My.ini 中,增加如下两行: [mysqld] skip-name-resolve 它将禁止 MySql Server 对外部连接进
    2019-01-04