如何在使用身份的多表视图上编写INSTEAD OF INSERT触发器?

编程入门 行业动态 更新时间:2024-10-25 16:17:06
本文介绍了如何在使用身份的多表视图上编写INSTEAD OF INSERT触发器?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧! 问题描述

我有两个具有1:1关系的表,并使用 IDENTITY 列作为其主键。

I have two tables that have a 1:1 relationship and use IDENTITY columns for their primary keys.

视图将两个表连接在一起,给人的印象是所有列实际上都存储在一个表中。

A view is joining both tables together to give the impression that all columns are really stored in one table.

出于查看目的,这很好,但是视图需要 INSTEAD OF INSERT 触发器。

For viewing purposes this is fine, but the view needs an INSTEAD OF INSERT trigger as well.

如何编写这样的触发器来在两个表中拆分列值?

How do you write such a trigger that splits the column values across both tables?

注意:除父表中的identity列外,没有其他候选键。否则,这个问题可能会有所帮助:

Note: There is no candidate key other than the identity column in the parent table. Otherwise this question may help:

插入视图,插入触发器,身份,多个表?

(还有一种可能的方法是声明一个变量

(There is also a possible solution that declares a variable for every field in an answer of that question.)

简化的模式(我省略了PKEY,FKEY,COLLATIONS等):

Simplified schema (I left out PKEYs, FKEYs, COLLATIONS, etc.):

CREATE TABLE [dbo].[parent] ( [parent_id] INT IDENTITY(1,1) , [name] NVARCHAR(100) ) CREATE TABLE [dbo].[child] ( [parent_id] INT NOT NULL , [child_id] INT IDENTITY(1,1) , [name] NVARCHAR(100) ) GO CREATE VIEW [dbo].[parent_child] AS SELECT par.[parent_id] , par.[name] AS "parent_name" , chi.[child_id] , chi.[name] AS "child_name" FROM [dbo].[parent] par LEFT OUTER JOIN [dbo].[child] chi ON chi.[parent_id] = par.[parent_id] GO

触发模板:

CREATE TRIGGER [dbo].[parent_child_instead_of_insert] ON [dbo].[parent_child] INSTEAD OF INSERT AS BEGIN -- Implementation here END GO

示例数据:

INSERT INTO [dbo].[parent_child] ( [parent_name] , [child_name] ) SELECT 'parent1' , 'child1' UNION SELECT 'parent2' , 'child2'

推荐答案

受到以下问题的启发:对INSTEAD OF INSERT触发器进行未来的保护我想出了一个使用临时表 #inserted 的解决方案插入的表的完整副本。

Inspired by the question Future-proofing an INSTEAD OF INSERT trigger I came up with a solution which uses a temporary table #inserted that is a complete copy of the inserted table.

触发器将在该表上添加一个临时标识列,以使其成为可能

The trigger adds a temporary identity column on that table to make it possible to iterate over the inserted rows using a unique value.

然后剩下的就是一个简单的循环,使用游标,该游标首先将每一行插入父表并使用 SCOPE_IDENTITY()插入子行。

The rest is then a simple loop using a cursor that inserts each row into the parent table first and uses the SCOPE_IDENTITY() to insert the child row.

此解决方案比为每个列声明var具有优势

This solution has the advantage over the "declare a var for every column" solution that you have to fetch only the temporary identity value instead of all columns.

在性能方面,它可能不是很好,因为必须复制插入表中的所有数据

Performance wise it is probably not very good, because all data in the inserted table must be copied.

SELECT * INTO [dbo].[#inserted] FROM [inserted] ALTER TABLE [dbo].[#inserted] ADD [temp_id] INT IDENTITY(1,1) DECLARE @temp_id int DECLARE cur CURSOR FOR SELECT [temp_id] FROM [dbo].[#inserted] OPEN cur FETCH cur INTO @temp_id WHILE @@FETCH_STATUS = 0 BEGIN INSERT INTO [dbo].[parent] ( [name] ) SELECT [parent_name] FROM [#inserted] WHERE [temp_id] = @temp_id INSERT INTO child ( [parent_id] , [name] ) SELECT SCOPE_IDENTITY() , [child_name] FROM [dbo].[#inserted] WHERE [temp_id] = @temp_id FETCH cur INTO @temp_id END CLOSE cur DEALLOCATE cur

更多推荐

如何在使用身份的多表视图上编写INSTEAD OF INSERT触发器?

本文发布于:2023-10-21 17:31:05,感谢您对本站的认可!
本文链接:https://www.elefans.com/category/jswz/34/1514889.html
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,我们将在24小时内删除。
本文标签:触发器   视图   身份   如何在   INSERT

发布评论

评论列表 (有 0 条评论)
草根站长

>www.elefans.com

编程频道|电子爱好者 - 技术资讯及电子产品介绍!