牛腩新闻发布系统:触发器

前言:之前在学习SQL Server时接触过这个概念,但当时只是简单提及,而且也没有具体教学例子,因此只是对这个概念略知一二,今天接触到了,按照惯例我将讲解该知识点。

 

触发器:

触发器是SQL Server提供给程序员和数据分析员来保证数据完整性的一种方法,它是与表事件相关的特殊的存储过程。

触发器的执行不是由程序调用,也不是手工启动,而是由事件来触发,比如当对一个表进行操作( insert,delete, update)时就会激活它执行。触发器经常用于加强数据的完整性约束和业务规则等。

                                                                                                                                                                   ---百度百科

从概念上来看,触发器是一种存储过程,而它的执行需要事件来触发,作用是用来加强数据的完整性约束,这几点我们需要知道。

 

我们来结合牛腩视频的例子:

首先我们在类别表内添加类别,之后在新闻表添加属于某个类别的新闻,再在评论表中添加属于某条新闻的评论:

 

我们要增加一个删除类别的功能,而删除类别的同时需要将类别下的新闻也全部删掉,删掉新闻的同时也要将这些新闻下的评论都删掉(想想你在删掉某条说说的时候,是不是评论、点赞的信息都没有了)。这个功能如果我在D层只用以下代码来实现:

/// <summary>
/// 删除类别(连同其下的新闻及新闻评论一起删除)
/// </summary>
/// <param name="id"></param>
/// <returns></returns>

public bool Delete(string id)
{
        bool flag = false;
        string sql = "Delete from category where id=@id";

        SqlParameter[] paras = new SqlParameter[] 
        {
        new SqlParameter("@id",id)
        };

        int res = sqlhelper.ExecuteNonQuery(sql, paras);
        if (res > 0)
        {
            flag = true;
        }
        return flag;
}

Web层:

//删除新闻
protected void Button4_Click(object sender, EventArgs e)
{
        string catName = TextBox1.Text;
        string id = TextBox2.Text;
        Category cat = new Category(id, catName);
        bool b = new CategoryDAO().Delete(id);//删除类别除功能
        Response.Write(b);
        GridView1.DataSource = new CategoryDAO().SelectAll();//取出当前所有新闻类
        GridView1.DataBind();
}

得到的结果(由于还原案发现场有点麻烦,我就直接把错误打出来吧):

DELETE 语句与REFERENCE约束...冲突。该冲突发生于...

 

问题原因:我们在刚刚创建数据库的时候,在三个表之间建立了数据库关系图:

如果单单只删除类别表,而类别表下面有新闻存在,就会造成空数据的存在。SQL Server为了保证数据的完整性,不允许这种情况出现。

所以,我们需要建立触发器:

 

触发器语法:

USE [newssystem]
GO
/****** Object:  Trigger [dbo].[trigCategoryDelete]    Script Date: 2019/6/5 19:07:24 ******/
SET ANSI_NULLS ON
GO
SET QUOTED_IDENTIFIER ON
GO
-- =============================================
-- Author:	任博扬
-- Create date: 2019-6-5,10:32
-- Description:	删除类别触发器
-- =============================================
ALTER TRIGGER [dbo].[trigCategoryDelete] 
   ON  [dbo].[category]
   --触发器代替了Delete操作
   instead of DELETE
AS 
BEGIN
	declare @caId int
        --从临时表中取出刚刚删除的类别
	select @caId=id from deleted
	--删除评论
	delete comment where newsid in (select newsid from news where caID=@caId)
	--删除新闻
	delete news where caId=@caId
	--删除类别
	delete category where id=@caId
END

其中,instead of DELETE代表触发器代替原来的Delete语句;临时表deleted中存储刚刚删除的数据,可以用于查询;子查询不用多说,很好理解。

 

结果:(左上角的True代表操作正确执行)

 

 

 

 

评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值