数据据库八之 视图、触发器、事务

【零】数据准备

【1】创建表

(1)部门表
  • d_id是部门的编号
  • d_name是部门的名字
# 确保表不存在
drop table if exists department;
# 创建表
create table department(
d_id int auto_increment primary key,
d_name varchar(6)
)auto_increment = 501 ;
(2)创建员工表
  • id是员工的编号
  • name是员工的姓名
  • money是员工的金额,默认1000
  • sex是员工性别默认男性
  • department_id是所在部门的编号
# 确保表不存在
drop table if exists employee;
# 创建表
create table employee(
id int auto_increment primary key,
name varchar(10),
password varchar(20),
money int default 1000,
sex enum('female', 'male') default 'male',
department_id int
);

【2】插入数据

(1)部门信息
  • 只插入3个部门信息
insert department (d_name) values("销售部"), ("技术部"), ("售后部");
+-----+-----------+
| id  | name      |
+-----+-----------+
| 501 | 销售部    |
| 502 | 技术部    |
| 503 | 售后部    |
+-----+-----------+
(2)员工信息
  • 共5名员工
insert employee (name, sex, password, department_id)values
('John', 'male', '111',  501),
('Jane', 'female', '222', 503),
('Mike', 'male', '333',  502),
('Tom', 'male', 'aaa', 503),
('Amy', 'female', '999', 501);
+----+------+----------+-------+--------+---------------+
| id | name | password | money | sex    | department_id |
+----+------+----------+-------+--------+---------------+
|  1 | John | 111      |  1000 | male   |           501 |
|  2 | Jane | 222      |  1000 | female |           503 |
|  3 | Mike | 333      |  1000 | male   |           502 |
|  4 | Tom  | aaa      |  1000 | male   |           503 |
|  5 | Amy  | 999      |  1000 | female |           501 |
+----+------+----------+-------+--------+---------------+

【一】视图

【1】说明

(1)什么是视图
  • 视图是数据库中的一种虚拟表,其内容是一个或多个基本表的查询结果。
  • 与基本表不同,视图不存储实际数据,而是根据查询语句在使用时进行实时计算
  • 视图可以通过定义查询语句来简化复杂的查询、隐藏敏感数据、实现数据安全性和完整性约束等。
  • 用户可以对视图执行与表相同的查询操作但是多用于查询,其他容易出错
  • 视图可以是虚拟的,每次查询都会计算最新的结果,也可以是物化的,用于提高查询性能。
  • 虚拟视图适用于经常变动的数据,而物化视图适用于查询频繁但数据变动较少的情况。
  • 通过使用视图,用户可以以灵活且安全的方式访问和操作数据库中的数据,无需直接访问底层的基本表
(2)作用
  • 简化复杂查询:通过在视图中定义复杂的查询逻辑,包括连接多个表、过滤条件、聚合函数等,使用户能够以更简洁明了的方式进行数据检索。

  • 数据安全性:通过限制用户对数据的访问权限,视图可以用于隐藏敏感数据或只提供部分数据给特定的用户。通过定义视图并设置相应的权限,可以保护数据的安全性,防止未经授权的用户访问敏感信息。

  • 数据完整性:视图可以用于实现数据完整性约束,即对数据的有效性进行验证。通过定义视图并添加计算列、过滤条件等约束,可以确保所返回的数据满足一定的条件,提高数据的准确性和一致性。

  • 逻辑数据独立性:通过解耦应用程序与底层数据表结构,视图使得应用程序不需要了解底层表结构的细节。这样,当底层数据库发生变化时,只需调整底层视图的定义而无需修改应用程序,提高系统的可维护性和扩展性。

  • 性能优化:物化视图作为一种缓存机制,将视图的查询结果存储在磁盘上,提高查询性能。特别在基本表数据频繁变动时,物化视图可以减少查询的计算开销和响应时间,从而提升系统的性能。

【2】使用

  • 联合多个表的时候,字段名不能重复
(1)创建视图
  • 创建视图的模板
create view 视图名 as
select 字段名,...
from 表名
join 表名 on 条件
where 条件
  • 创建视图
create view emp_dep as
select * from employee
left join department
on employee.department_id = department.d_id;
  • 查看文件结构
    • 只有frm文件,没有ibd文件
    • 只有表结构,没有数据记录

请添加图片描述

(2)修改数据
  • 先查看原本视图内容
select * from emp_dep;
+----+------+--------+---------------+------+-----------+
| id | name | sex    | department_id | d_id | d_name    |
+----+------+--------+---------------+------+-----------+
|  1 | John | male   |           501 |  501 | 销售部    |
|  5 | Amy  | female |           501 |  501 | 销售部    |
|  3 | Mike | male   |           502 |  502 | 技术部    |
|  2 | Jane | female |           503 |  503 | 售后部    |
|  4 | Tom  | male   |           503 |  503 | 售后部    |
+----+------+--------+---------------+------+-----------+
  • 员工表插入记录,并查看视图是否修改(修改了)
insert employee (name, sex, department_id)
values('lulu', 'female', 502);
select * from emp_dep;
+----+------+--------+---------------+------+-----------+
| id | name | sex    | department_id | d_id | d_name    |
+----+------+--------+---------------+------+-----------+
|  1 | John | male   |           501 |  501 | 销售部    |
|  5 | Amy  | female |           501 |  501 | 销售部    |
|  3 | Mike | male   |           502 |  502 | 技术部    |
|  6 | lulu | female |           502 |  502 | 技术部    |
|  2 | Jane | female |           503 |  503 | 售后部    |
|  4 | Tom  | male   |           503 |  503 | 售后部    |
+----+------+--------+---------------+------+-----------+
  • 视图表删除数据记录,查看视图表是否修改(不能)
delete from emp_dep
where id = 6;
ERROR 1288 (HY000): The target table emp_dep of the DELETE is not updatable
  • 视图表修改数据记录,查看视图表是否修改(不能)
update emp_dep
set department_id = 502
where name = tom;
ERROR 1288 (HY000): The target table emp_dep of the UPDATE is not updatable
  • 小结
    • 视图表多用于查询
    • 若要修改,在原表进行修改
(3)删除视图
  • 查看方法:
    • 和查看表一样
show tables;
+---------------+
| Tables_in_db4 |
+---------------+
| department    |
| emp_dep       |
| employee      |
+---------------+
desc emp_dep;
+---------------+-----------------------+------+-----+---------+-------+
| Field         | Type                  | Null | Key | Default | Extra |
+---------------+-----------------------+------+-----+---------+-------+
| id            | int(11)               | NO   |     | 0       |       |
| name          | varchar(10)           | YES  |     | NULL    |       |
| sex           | enum('female','male') | YES  |     | male    |       |
| department_id | int(11)               | YES  |     | NULL    |       |
| d_id          | int(11)               | YES  |     | 0       |       |
| d_name        | varchar(6)            | YES  |     | NULL    |       |
+---------------+-----------------------+------+-----+---------+-------+
  • 删除视图
    • 关键字稍微不同
drop view id exists 触发器名;
drop view emp_dep;

【二】触发器

【1】说明

(1)什么是触发器
  • 触发器是数据库管理系统中的一种特殊对象,用于在数据库表发生特定的数据变化时自动触发相关的操作或逻辑
  • 触发器通常与数据库表关联,监视表的增删改操作,当满足指定条件时,触发器会执行相应的响应行为。
(2)主要作用
  • 自动执行操作: 触发器可以在表的数据发生变化时自动执行相关的操作,如插入、更新、删除或查询数据等。
  • 维护数据一致性: 触发器可以用作一种约束,用于保证数据的完整性和一致性。通过在触发器中定义逻辑,可以确保数据库中的数据始终符合特定的规则或条件。
  • 实现业务规则: 触发器可以用于实现特定的业务规则。例如,当某个表的特定列达到某个阈值时,触发器可以自动执行相应的业务逻辑。
  • 记录操作历史: 触发器可以用于记录数据的修改历史,例如在表的某个字段发生变化时,触发器可以将变化记录到一个历史表中。
(3)使用场景
  • 使用触发器可以实现很多功能
    • 比如数据验证、数据补全、数据同步、日志记录等。
  • 在增删改的前后都可以使用触发器,故有六种使用情况
    • 增前、增后
    • 删前、删后
    • 改前、改后

【2】使用

(0)修改默认语句结束符
  • sql语句默认结束符是
  • 但是在接下来的语句中会有出现
  • 所以我们需要学会修改默认语句结束符
# 修改为 $$
delimiter $$
# 修改回来 ;
delimiter ;
(1)创建触发器
  • 模板
delimiter $$
create trigger 触发器名
{before | after} {insert | update | delete} on 表名
for each row
begin
	--触发器执行的语句
	--new
	--old
end $$	
delimiter ;
  • 触发器的名字需要让人很容易的理解其含义
# 例如
tri_表名_after_insert
  • NEW
    • NEW 用于引用触发器中正在处理的行的新值。在 BEFORE INSERTBEFORE UPDATE 触发器中,NEW 包含即将插入或更新到表中的数据。在 AFTER INSERTAFTER UPDATEAFTER DELETE 触发器中,NEW 包含已经插入、更新或删除的数据。
    • BEFORE INSERTAFTER INSERT 触发器中,NEW 是唯一的,并包含即将或已经插入到表中的数据。
  • OLD
    • OLD 用于引用触发器中正在处理的行的旧值。在 BEFORE UPDATEAFTER UPDATE 触发器中,OLD 包含即将或已经被更新的行的旧值。在 BEFORE DELETEAFTER DELETE 触发器中,OLD 包含即将或已经被删除的行的旧值。
    • BEFORE UPDATEAFTER UPDATE 触发器中,OLD 包含被更新的数据的旧值。在 BEFORE DELETEAFTER DELETE 触发器中,OLD 包含被删除的数据的旧值。
(2)删除触发器
  • 删除语句很简单
    • 和视图的删除差不多
drop trigger if exists 触发器名
(2)例一:部门检查
  • 要求:在插入数据之前进行部门id校验
delimiter $$
create trigger tri_employee_before_insert before insert on employee
for each row
begin
	if new.department_id not in (select d_id from department) then
		signal sqlstate '45000'
		set message_text = "部门id不存在";
    end if;
end $$
delimiter ;
  • 检查检查(正确)
insert employee (name, sex, department_id) values('liuliu', 'male', 505);
ERROR 1644 (45000): 部门id不存在
minsert employee (name, sex, department_id) values('liuliu', 'male', 501);
Query OK, 1 row affected (0.00 sec)
(3)例二:密码安全性提醒
  • 要求:每次在修改密码以后进行判断
    • 如果密码是全新的密码,不做提醒
    • 如果密码和之前的密码一样,提醒安全性较低
drop trigger if exists tri_employee_after_update;
delimiter $$
create trigger tri_employee_after_update after update on employee
for each row
begin
	if old.password = new.password then
		signal sqlstate '01000'
		set message_text = '修改成功,但密码安全性较低,和之前一样';
		# 不允许返回值
		# select '修改成功,但密码安全性较低,和之前一样';
	end if;	
end $$
delimiter ;
  • 检查检查
# 查看id为2的员工密码
select password 
from employee
where id=2;
+----------+
| password |
+----------+
| 222      |
+----------+
# 修改的密码和之前一样
update employee
set password = '222'
where id = 2;
Query OK, 0 rows affected (0.00 sec)
Rows matched: 1  Changed: 0  Warnings: 0
  • 很遗憾,不会触发
    • 但是可以修改错误代码围为45000
    • 验证逻辑是没有问题
    • 只不过这种应用并不适合
    • 有待更改完善或者使用新的例子
(4)一些模板
  • 插入数据之前,自动生成唯一标识符
CREATE TRIGGER generate_uuid_trigger BEFORE INSERT ON table_name
FOR EACH ROW
BEGIN
    SET NEW.uuid = UUID();
END
  • 更新数据时,更新最后修改时间
CREATE TRIGGER update_last_modified_trigger BEFORE UPDATE ON table_name
FOR EACH ROW
BEGIN
    SET NEW.last_modified = NOW();
END
  • 删除数据时,将记录添加到历史记录表
CREATE TRIGGER archive_deleted_record_trigger AFTER DELETE ON table_name
FOR EACH ROW
BEGIN
    INSERT INTO history_table (id, deleted_at)
    VALUES (OLD.id, NOW());
END
  • 插入数据进行某个条件检查,不满足抛出异常
CREATE TRIGGER check_condition_trigger BEFORE INSERT ON table_name
FOR EACH ROW
BEGIN
    IF NEW.column_name < 10 THEN
        SIGNAL SQLSTATE '45000' SET MESSAGE_TEXT = 'Value must be greater than 10';
    END IF;
END
  • 日志模板
# 主要是为了区分错误执行语句和全局结束语句
create trigger tri_after_insert_cmd after insert on cmd 
for each row
begin
	if NEW.success = "no" then
		insert into errlog(err_cmd,err_time)
	values(NEW.cmd,NEW.sub_time);
		end if;
end

【三】事务

【1】说明

(1)什么是事务
  • 事务是数据库管理系统中的一个概念,它表示一系列相关的数据库操作,这些操作要么全部成功执行要么全部失败回滚,保证数据库的一致性和完整性。
(2)事务的四大特性
  • 原子性(Atomicity): 事务被视为一个原子操作,不可再分割。要么所有的操作都成功执行,要么所有的操作都会被回滚到事务开始前的状态,确保数据的一致性。
  • 一致性(Consistency): 事务执行前后,数据库应保持一致的状态。在事务开始之前和结束之后,数据库必须满足所有的完整性约束,如数据类型、关系等。
  • 隔离性(Isolation): 事务的执行结果对其他并发执行的事务是隔离的。即一个事务的执行不应受到其他事务的干扰,各个事务之间应该相互独立工作,从而避免数据的不一致性。
  • 持久性(Durability): **一旦事务被提交,其结果应该永久保存在数据库中,并且可以被系统故障恢复。**即使系统发生宕机或崩溃,事务提交后的更改也应该是永久性的。
(3)简单示例
  • 用户提交订单的操作流程可以总结为以下步骤:

    1. 检查库存: 系统检查所需商品的库存是否足够。
    2. 库存充足: 如果库存足够,系统继续执行后续步骤;如果库存不足,系统提示用户库存不足,无法完成订单。
    3. 扣减库存: 系统减少所购商品对应的库存数量。
    4. 生成订单: 系统生成一个新的订单,包括订单号、商品信息、购买数量、价格等相关信息。
    5. 计算总价: 系统根据订单中的商品信息和购买数量计算订单的总价格。
    6. 更新用户账户: 根据用户选择的支付方式,在扣除相应金额后,系统更新用户账户余额或积分。
    7. 生成支付信息: 系统生成相应的支付信息,以便用户完成支付。
    8. 通知物流部门: 系统通知物流部门准备配送相关商品。
    9. 发送订单确认邮件/短信: 系统向用户发送订单确认的邮件或短信,包括订单详细信息、配送信息等。
    10. 监控商品配送: 系统跟踪订单的配送情况,并向用户提供订单状态更新。
    11. 完成订单: 当用户收到商品并确认满意后,订单状态会被更新为“已完成”。
  • 这个流程确保了在用户提交订单后,系统进行了必要的检查、处理、通知和更新操作,以提供完整的购物体验。

【2】使用

(1)创建事务
  • 模板
# 开启事务
start transaction;

# 执行事务操作
......
......

# 提交事务或者回滚事务
# 此时会结束事务
commit; | rollback;
(2)示例:转钱
  • 任务

    • 初始每个人都是1000元

    • 让我们来试试一号给二号转100元试试

  • 开启事务

start transaction;
  • 1号员工扣钱、2号员工加钱
update employee 
set money = money - 100
where id = 1;
update employee 
set money = money + 100
where id = 2;
  • 查看此时他们的金额
select id, money
from employee
where id in (1, 2);
+----+-------+
| id | money |
+----+-------+
|  1 |   900 |
|  2 |  1100 |
+----+-------+
  • 回滚试试,看看会发生什么
    • 金额变回来了
rollback;
select id, money
from employee
where id in (1, 2);
+----+-------+
| id | money |
+----+-------+
|  1 |  1000 |
|  2 |  1000 |
+----+-------+
  • 再次转钱
update employee 
set money = money - 100
where id = 1;
update employee 
set money = money + 100
where id = 2;
  • 提交事务
commit;
  • 尝试回滚并查看数据
    • 虽然回滚没有报错
    • 但是数据并不会发生回滚了
    • 因为事务在commit以后已经结束了
rollback;
select id, money
from employee
where id in (1, 2);
+----+-------+
| id | money |
+----+-------+
|  1 |   900 |
|  2 |  1100 |
+----+-------+

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/358200.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

【linux|java应用报错】Cannot allocate memory

启动一个java应用报Cannot allocate memory&#xff0c;并且会生产一个hs_ess_pid.log文件。 文件内容为&#xff1a; #内存不足&#xff0c;Java运行时环境无法继续。 #本机内存分配&#xff08;mmap&#xff09;无法映射4294967296字节以提交保留内存。 【排查】 1、尝试使…

Mysql-事务(隔离级别,事务底层原理,MVCC)

什么是事务&#xff1f;有哪些特性&#xff1f; 事务&#xff1a;事务指的是逻辑上的一组操作&#xff0c;组成这组操作的各个单元要么全都成功&#xff0c;要么全都失败。 事务特性&#xff1a; 原子性&#xff08;Atomicity&#xff09;&#xff1a; 原子性是指事务是一个不…

Python tkinter (11) —— Frame控件

本文主要是Python tkinter Frame框架控件介绍及使用简单示例。 tkinter系列文章 python tkinter窗口简单实现 Python tkinter (1) —— Label标签 Python tkinter (2) —— Button标签 Python tkinter (3) —— Entry标签 Python tkinter (4) —— Text控件 Python tkint…

大健康行业千城万企信用建设工作启动大会在京召开

9月19日&#xff0c;为响应商务部、中宣部、国家发改委等13个部门共同举办的“诚信兴商宣传月”活动&#xff0c;中国国际电子商务中心所属北京国富泰信用管理有限公司联合北京华商国医堂集团及旗下东方岐黄商学院&#xff0c;北京华商国医堂中医药研究院举办的共筑信用月&…

Mov转MP4怎么转换?如何播放mov视频?

MOV文件格式的使用场景 MOV文件格式以其支持多种媒体数据类型的特性而闻名&#xff0c;包括视频、音频、文本、动画等。它常用于存储包含视频剪辑、电影、音频轨道等多媒体元素的文件。由于其在质量和编辑方面的优越性&#xff0c;MOV文件在电影制作、广告宣传、多媒体演示等领…

阿里二面:SpringBoot同时可以处理多少个请求?直接懵了。。。

SpringBoot以其简洁高效的开发方式和强大的内嵌容器特性&#xff0c;为开发者提供了构建高性能后端服务的便利。然而&#xff0c;当面临高并发场景时&#xff0c;理解并合理配置Spring Boot应用以达到最佳的并发处理能力至关重要。在Spring Boot中&#xff0c;应用程序对HTTP请…

Docker最新超详细版教程通俗易懂(基础版)

Docker概述 概念&#xff1a;容器虚拟化技术&#xff0c;系统平滑移植&#xff0c;解决了运⾏环境和配置问题的软件容 器&#xff0c;⽅便做持续集成并有助于整体发布的容器虚拟化技术 意义&#xff1a;Docker的出现使得Docker得以打破过去程序即应⽤的观念&#xff0c;透过…

Flink中的时间语义和TTL

时间语义 事件时间&#xff08;Event Time&#xff09; 事件时间是数据生成的时间&#xff0c;是数据流中每个元素或者每个事件自带的时间属性&#xff0c;一般是事件发生的时间&#xff0c;在实际项目中作为前端的一个属性嵌入。在理想情况下&#xff0c;数据应当按照事件时…

TeX:一款功能强大的Telegram安全监控与管理工具

关于TeX TeX是一款功能强大的Telegram安全监控与管理工具&#xff0c;该工具专为Telegram设计&#xff0c;可以实现针对Telegram的安全监控与管理。 TeX旨在帮助安全研究人员、调查人员和执法人员收集和处理针对网络犯罪分子的取证信息&#xff0c;其中包括网络犯罪、欺诈攻击…

vue3-深入组件-透传属性

透传属性 &#xff08;透传 attribute&#xff09; 什么是透传属性&#xff08;透传 attribute&#xff09;? 传递给一个组件&#xff0c;却没有被该组件声明为 props 或 emits 的 attribute 或者是事件监听器&#xff0c;例如 class style id 等。 属性继承 当一个组件以单…

STM32 1-5

目录 STM32简介 点亮PC13LED GPIO LED闪烁 LED流水灯 按键控制LED 光敏传感器控制蜂鸣器 OLED调试工具 OLED显示 EXTI外部中断 对射式红外传感器计次 旋转编码器计次 继续 STM32简介 点亮PC13LED main.c #include "stm32f10x.h" // D…

【linux】复制cp和硬连接、软连接的区别? innode 关系?

1.命令&#xff1a; cp -r [源文件或目录] [目的目录] #复制 ln -s [被链接的文件] [链接的目录/名称] #软连接 ln [被链接的文件] [链接的目录/名称] #硬连接 注&#xff1a;cp -r 会把所有source当作普通文件&#xff08;regular文件&#xff09;&#x…

代码随想录算法训练营第35天 | 860.柠檬水找零 406.根据身高重建队列 452.用最少数量的箭引爆气球

柠檬水找零 局部最优&#xff1a;收到20元时优先找零10元5元&#xff0c;不够再找零3个5元&#xff0c;因为5元可以找零20和10&#xff0c;更有用。全局最优&#xff1a;完成所有的找零。 class Solution { public:bool lemonadeChange(vector<int>& bills) {int fi…

Flink问题解决及性能调优-【Flink rocksDB读写state大对象导致背压问题调优】

RocksDB是Flink中用于持久化状态的默认后端&#xff0c;它提供了高性能和可靠的状态存储。然而&#xff0c;当处理大型状态并频繁读写时&#xff0c;可能会导致背压问题&#xff0c;因为RocksDB需要从磁盘读取和写入数据&#xff0c;而这可能成为瓶颈。 遇到的问题 Flink开发…

多线程编程3——线程的状态

一、状态是线程的状态 状态是PCB中与调度相关的属性&#xff0c;线程是CPU调度执行的基本单位。所以&#xff0c;状态是线程的属性。谈到状态&#xff0c;考虑的都是线程的状态&#xff0c;不是进程&#xff01;&#xff01;&#xff01; 二、在Java中&#xff0c;线程的状态…

作业车间调度问题:P还是NP

获取更多资讯&#xff0c;赶快关注上面的公众号吧&#xff01; 文章目录 基本概念多项式时间指数时间 P问题&#xff08;多项式问题&#xff09;NP问题&#xff08;非确定性多项式问题&#xff09;暴力穷举法动态规划 P与NP关系&#xff1a;作业车间调度问题是典型的NP难问题 …

将vite项目(vue/react)使用vite-plugin-pwa配置为pwa应用,只需要3分钟即可

将项目配置为pwa模式&#xff0c;就可以在浏览器里面看到安装应用的选项&#xff0c;并且可以将web网页像app一样添加到手机桌面或者pad桌面上&#xff0c;或者是电脑桌面上&#xff0c;这样带来的体验就像真的在一个app上运行一样。为了实现这个目的&#xff0c;我们可以为vue…

vue3-hand-mobile

当我写完手势移动事件后&#xff0c;我又通过svg的方法添加了一段文字和polygon。当我在这个蓝色的polygon上滑动手势的时候&#xff0c;会报错。 可能这个bug只是我个人的代码导致的。但是我觉得vue3-hand-mobile插件的这一段代码写的有问题。 我通过circular-json库修复了这…

vite+vue3+ts项目上线docker 配置反向代理API

这次重点的坑是反向代理。 1。项目中配置代理&#xff0c;为了跨域请求数据 项目根目录中新建vite.config.ts文件 在文件中添加配置代理 注意&#xff1a;其中 /api 和target 的地址后面没有 / 2。在项目根目录中新建Httprequest.ts文件&#xff0c;引入axios&#xff0c;并…

网诺安全文件上传总结

一、文件上传简介 文件上传漏洞是指用户上传了一个可执行的脚本文件&#xff08;木马、病毒、恶意脚本、webshell等&#xff09;&#xff0c;并通过此脚本文件获得了执行服务器端命令的能力。上传点一般出现在头像、导入数据、上传压缩包等地方&#xff0c;由于程序对用户上传…