我的应用程序包括将表单中的数据(“请求”)提交到Server 2005数据库中,供主管稍后审查和批准。用户应该拥有插入新请求的权限,但不能修改他们已经提交的请求。
对于单个表,这很简单:只授予他们插入特权,但不授予更新权限。但是请求实际上跨越了两个表,具有一对多的关系。我需要阻止用户为现有请求插入额外的子行。理想情况下,这应该在数据库级别强制执行:允许在相同事务中插入父行和一个或多个子行,但一旦该事务被提交,就不会使用该外键插入新的子行。
实现这一目标的最佳方法是什么?有没有什么方法可以在没有触发器的情况下执行这种特殊的“引用完整性”呢?如果触发器是唯一的方法,那么如何测试父行是否已插入到当前事务中?
发布于 2010-01-21 08:33:05
下面的示例演示如何使用触发器来实现此行为。请注意,如果子行在事务内一次插入一个行,而不是在单个INSERT语句中插入,则这将无法工作。
CREATE TABLE parent1
(id INT PRIMARY KEY)
CREATE TABLE child1
(id INT
,parent_id INT
)
GO
ALTER TABLE child1 ADD CONSTRAINT chilld1fk FOREIGN KEY (parent_id)
REFERENCES parent1 (id)
GO
CREATE TRIGGER trg_child1
ON child1
INSTEAD OF INSERT
AS
SELECT parent_id
FROM child1 AS c
WHERE EXISTS (SELECT 1
FROM inserted AS i
WHERE i.parent_id = c.parent_id
)
IF @@ROWCOUNT > 0
BEGIN
RAISERROR('You cannot amend this request',16,1)
END
ELSE
BEGIN
INSERT child1
SELECT id
,parent_id
FROM inserted
END
GO
BEGIN TRAN
INSERT parent1
VALUES (1)
INSERT child1
(id
,parent_id
)
SELECT 10,1
UNION SELECT 11,1
COMMIT
-- attempting to insert another child outside the transaction
-- will result in an error
INSERT child1
SELECT 12,1
SELECT * FROM child1https://stackoverflow.com/questions/2107552
复制相似问题