数据库管理实务(四) 触发器的实例分析
触发器的实例分析
1.触发器是一种特殊存储过程。一般存储过程通过调用执行,而触发器是通过事件触发而被执行。触发器是功能强大的工具,可以实施对服务器、数据库和表等对象的事件监控,实现更复杂的数据完整性和安全性的管理。
2.SQL Server 2008中触发器分为3类:登录触发器、DDL触发器和DML触发器。
① 登录触发器。当用户登录,与实例建立会话时触发执行
- 由登录事件而激发的触发器,用户与SQL Server实例建立会话时将引发此事件。登录触发器在登录身份验证完成后且用户会话实际建立之前触发,因此在触发器内部通常将到达用户的所有消息(例如错误消息和来自Print语句的消息)发送到SQL Server错误日志。如果身份验证失败,将不激活登录触发器。
- 可以使用登录触发器审核和控制服务器会话,例如通过跟踪登录活动、限制SQL Server的登录名或限制特定登录名的会话数。
② DDL触发器。服务器或数据库发生DDL(数据定义语言)事件时触发执行。
- DDL触发器为了响应各种DDL事件而编制,主要与以关键字CREATE、ALTER和DROP开头的Transact-SQL语句对应。执行 DDL 式操作的存储过程也可以激发 DDL 触发器。DDL触发器只有在完成相应的DDL语句后才会被触发,因此无法作为Instead Of触发器使用。
- 可用于管理任务,如审核和控制数据库操作:要防止对数据库架构进行更改;希望数据库中发生某种情况以响应数据库架构中的更改;要记录数据库架构中的更改或事件等。
③ DML触发器。当数据库中发生DML(数据插入、删除、修改)操作事件时触发执行。DML操作针对的对象是表或视图。
- DML触发器针对INSERT、UPDATE和DELETE操作。分为AFTER触发器和INSTEAD OF触发器两种。
- AFTER触发器(又称后触发器)只能在表上定义,可对INSERT、UPDATE、DELETE操作定义触发器。当操作发生后,触发器被触发,可以对操作改变的数据进行检查,如果发现错误,可回滚变动的数据。可以针对表的同一操作定义多个触发器。
- INSTEAD OF触发器(又称替代触发器)在操作之前触发,不去执行操作,而是执行触发器定义的操作以取代之。INSTEAD OF触发器既可在表上定义也可以在视图上定义,但对同一操作只能定义一个INSTEAD OF触发器。
3.触发器-主要特点和作用
- 触发器通过事件自动执行,因此可用于对用户登录、服务器或数据库上对象的创建、修改或删除,以及对表或视图的操作等进行监控。并可实现一些审计功能。
- 触发器可以实现比CHECK约束、外键约束等方法更复杂的数据库完整性约束。
- 可以增强数据库的安全性。
- 回滚违反数据完整性的操作,防止恶意或错误的INSERT、UPDATE、DELETE操作。
- 查找在数据修改前后,表状态之间的差别,并根据差别分别采取相应的措施。
- 在一张表同一类型的操作上设置多个触发器,从而可以针对同样的DML语句执行不同的多种操作。
accountData ( accounted,accountType,accountAmount)
CREATE TABLE wbf_UserTestAccountData
wbf_UserTest_log_loginname varchar(20),
wbf_UserTest_log_username varchar(20),
wbf_UserTest_log_actionType varchar(20),
wbf_UserTest_log_actionTime DATE,
CREATE TRIGGER t_accountData_insert
DECLARE @insertActionAmount MONEY
SELECT @insertActionAmount = accountAmount
INSERT INTO wbf_UserTestAccountData (wbf_UserTest_log_actionType,wbf_UserTest_log_amount)
VALUES ('INSERT', @insertActionAmount)
CREATE TRIGGER t_accountData_delete
DECLARE @deleteActionAmount MONEY
SELECT @deleteActionAmount = accountAmount
INSERT INTO wbf_UserTestAccountData (wbf_UserTest_log_actionType,wbf_UserTest_log_amount)
VALUES ('DELETE',@deleteActionAmount)
CREATE TRIGGER t_accountData_update
SELECT @oldValue = accountAmount FROM deleted
INSERT INTO wbf_UserTestAccountData (wbf_UserTest_log_actionType,wbf_UserTest_log_amount)
VALUES ('update_old_value ',@oldValue)
SELECT @newValue = accountAmount FROM inserted
INSERT INTO wbf_UserTestAccountData (wbf_UserTest_log_actionType,wbf_UserTest_log_amount)
VALUES ('update_new_value ',@newValue)
INSERT INTO accountData VALUES('1','存款',1300)
INSERT INTO accountData VALUES('2','存款',2600)
INSERT INTO accountData VALUES('3','存款',102)
INSERT INTO accountData VALUES ('4', '存款 ',1613030102)
然后查看审计表 wbf_UserTestAccountData 中插入的数据,可以看到,触发器的操作是正确的
SELECT * FROM wbf_UserTestAccountData
下面是一组删除数据的操作,这些删除操作完成之后,会触发 t_accountData_delete 触发器的执行,应该在 wbf_UserTestAccountData 中记录下来。删除记录的命令如下:
DELETE FROM accountData WHERE accounted = 1
DELETE FROM accountData WHERE accounted = 2
DELETE FROM accountData WHERE accounted = 3
DELETE FROM accountData WHERE accounted = 4
然后查看审计表 wbf_UserTestAccountData 中插入的数据,可以看到,触发器的操作是正确的
SELECT * FROM wbf_UserTestAccountData
1.示例测试触发器分析
DELETE FROM accountData WHERE accounted<=4 SELECT * FROM wbf_UserTestAccountData
根据触发器中的语句所执行的操作类型的不同,执行触发器过程中可以创建一个或者两个临时表(inserted 表和 deleted 表),下方说明了在进行何种操作时,触发器创建哪些表。
触发器类型 |
||
INSERT |
需要创建inserted表 |
不需要创建 deleted表 |
UPDATE |
需要创建inserted表 |
需要创建 deleted表 |
DELETE |
不需要创建inserted表 |
需要创建 deleted表 |
CREATE TRIGGER t_accountData_insert
INSERT INTO wbf_UserTestAccountData (wbf_UserTest_log_actionType,wbf_UserTest_log_amount)
SELECT 'insert',accountAmount FROM inserted
CREATE TRIGGER t_accountData_delete
INSERT INTO wbf_UserTestAccountData (wbf_UserTest_log_actionType,wbf_UserTest_log_amount)
SELECT 'delete',accountAmount FROM deleted
在数据更新时,将更新前的旧值表示为 update_old_value,将更新后的新值表示为 update_new_value
CREATE TRIGGER t_accountData_update
INSERT INTO wbf_UserTestAccountData (wbf_UserTest_log_actionType,wbf_UserTest_log_amount)
SELECT 'update_old_value',accountAmount FROM
INSERT INTO wbf_UserTestAccountData (wbf_UserTest_log_actionType,wbf_UserTest_log_amount)
SELECT 'update _ new _ value ',accountAmount
再次执行一次删除多条记录的命令,可以看到,它一次在 wbf_UserTestAccountData 表中记录了三条删除记录的信息,结果是正确的,达到了设计的目标,
DELETE FROM accountData WHERE accounted<=4 SELECT * FROM wbf_UserTestAccountData
CREATE TRIGGER t_accountData_idu
SELECT @ins_count=count(*) FROM inserted
SELECT @del_count=count(*) FROM deleted
IF @ins_count=1 and @del_count=0
INSERT INTO wbf_UserTestAccountData (wbf_UserTest_log_actionType,wbf_UserTest_log_amount)
SELECT 'insert',accountAmount FROM inserted
IF @ins_count=0 AND @del_count=1
INSERT INTO wbf_UserTestAccountData (wbf_UserTest_log_actionType,wbf_UserTest_log_amount)
SELECT 'delete',accountAmount FROM deleted
IF @ins_count=@del_count AND @ins_count=1
INSERT INTO wbf_UserTestAccountData (wbf_UserTest_log_actionType,wbf_UserTest_log_amount)
SELECT 'update_old_value',accountAmount FROM deleted
INSERT INTO wbf_UserTestAccountData (wbf_UserTest_log_actionType,wbf_UserTest_log_amount)
SELECT 'update_new_value',accountAmount FROM inserted
- accountData ( accounted,accountType,accountAmount) ,数据类型的确定上,INT不需要指定长度,能使用varchar尽量使用varchar。
- 即使是插入数据,也要注意,给每个列名插入值,不能空其中一个。
- 第一次测试仅仅是一次插入、删除一条记录,但是,如果一次插入、删除多条记录,触发器的设计仅考虑记录一行数据,其他插入、删除或更新的记录信息仍然丢掉了。
- 第二次测试需要事先删除表 accountData、wbf_UserTestAccountData,再重建这两个表,然后创建插入、删除、更新触发器,在 accountData 表中插入记录,执行下面的命令。(当时只是执行清除表中数据,最后发现执行命令时,上次执行的数据还存在)。
- 创建INSERT触发器脚本命令时,注意检查@与后方值之间不能出现空格。
- 在使用@ins_count>0时,出现了在应使用条件的上下文附近中指定了非布尔类型的表达式,最后我换了一种表达式,即@ins_count=1,因为bool值只有0和1。
数据库管理实务(四) 触发器的实例分析相关推荐
- Android10.0 Binder通信原理(四)-Native-C\C++实例分析
摘要:本节主要来讲解Android10.0 Binder的Native层实例流程 阅读本文大约需要花费35分钟. 文章首发微信公众号:IngresGe 专注于Android系统级源码分析,Androi ...
- 操作系统笔记——Linux系统实例分析、Windows系统实例分析
文章目录 传送门 Linux进程管理 Linux进程组成 Linux进程链表 Linux进程控制 用户进程创建与撤销 0,1,2号进程 Linux进程切换 Linux进程调度 内核同步 Linux储存 ...
- gpgpu-sim卡分配程序设计实例分析
gpgpu-sim卡分配程序设计实例分析 运行代码地址:https://github.com/gpgpu-sim/gpgpu-sim_distribution 一.概述 此文件包含有关安装.生成和运行 ...
- 马歇尔·赫伯特:人工智能的前沿技术与实例分析
来源:中国人工智能学会 2017年12月11日,国际知名机器人专家.美国卡耐基梅隆大学机器人研究所所长马歇尔·赫伯特(Martial Hebert)教授和首席科学家大卫·伯恩(David Bourne ...
- SSL/TLS 协议简介与实例分析
作者:drinkey 以前读RFC时总结的一篇文章,主要介绍了SSL/TLS协议的相关知识,包括协议本身以及简单的密码学概念,以及用实例解析了HTTP over SSL的协商过程,在最后简要列出了SS ...
- 【五线谱】还原记号 ( 还原记号使用简介 | 变音记号、还原记号实例分析 )
文章目录 一.还原记号 二.还原记号实例分析 1.原始音符分析 2.加入变音记号后的音符分析 一.还原记号 如果在 A3 音符前使用了变音记号 , 则默认其它音符也使用该变音记号 , 如果想要取消该变 ...
- 2017-2018-2 20155228 《网络对抗技术》 实验四:恶意代码分析
2017-2018-2 20155228 <网络对抗技术> 实验四:恶意代码分析 1. 实践内容 1.1 系统运行监控 使用如计划任务,每隔一分钟记录自己的电脑有哪些程序在联网,连接的外部 ...
- JPEG 原理详细实例分析及其在嵌入式 Linux 中的应用
http://www.ibm.com/developerworks/cn/linux/l-cn-jpeg/index.html 一.系统架构 本文以一个实际的产品为例,来说明 JPEG 在其中的应用. ...
- 数据挖掘技术在信用卡业务中的应用及实例分析
信用卡业务具有透支笔数巨大.单笔金额小的特点,这使得数据挖掘技术在信用卡业务中的应用成为必然.国外信用卡发卡机构已经广泛应用数据挖掘技术促进信用卡业务的发展,实现全面的绩效管理.我国自1985年发行第 ...
最新文章
- Django+Bootstrap+Mysql 搭建个人博客(五)
- banana pi BPI-R1 原理图下载地址:
- ML之FE:特征工程中的特征拼接处理(常用于横向拼接自变量特征和因变量特征)(daiding)
- 怎么会这样?delete [] 了,还能用!!!
- 用计算机和用纸的区别,英语四级机考与传统纸考的主要区别
- 【Elasticsearch】 es include_type_name unless the include_type_name parameter is set to true
- [历朝通俗演义-蔡东藩-前汉]第008回 葬始皇骊山成巨冢 戮宗室豻狱构奇冤
- ASP.NET MVC学习系列 WebAPI初探
- log nginx 显示时间_【日常小知识系列01】Nginx日志简述
- html5怎么设置黑色背景及亮度,网页背景怎么设置为纯黑色css样式
- 2021 年 35+ 最佳免费 WordPress 博客主题
- java的pdf转永中_永中pdf转word下载|
- cheap fifa coins Do restrict Alexander fantastic?
- 海信65E7G Pro评测
- python ——找出 每行中长度超过3的单词
- typescript工程_使用TypeScript构建游戏。 工程图网格2/5
- 【转】ST、SC、FC、LC光纤接头区别
- Servlet实例化异常以及tomcat子级启动失败的可能原因
- 高德地图使用心得,百度地图使用心得
- 华夫饼为什么不松软_华夫饼0添加太难了,在家才能做到,松软有营养,好吃又减肥...
热门文章
- 【sciter】:sciter 使用阿里矢量图标库
- 谈谈我对Ext的认识,元芳,你怎么看
- 为什么qt改不了ui的字体_为您的UI选择最佳字体
- 【Python】太神奇了,一行命令行将Notebook转换成PPT动态网页!
- 【第17天】丰富的阅历使话题源源不断
- ajax (阿贾克斯)----------- js 向后端索要数据的方式(技术)
- anylogic 学习(2)—— 简单行人库上楼模型
- ChatGPT和New Bing学术提问模版
- PCB天线设计 之 HFSS 导出天线文件, Altium 中天线封装及天线layout教程
- 手工使用二进制工具修改H大的breed的gpio复位键的心得