Sql server 防止将不适当的行插入SQL Server数据库

Sql server 防止将不适当的行插入SQL Server数据库,sql-server,data-integrity,Sql Server,Data Integrity,我有一个帐篷租金表,表中有以下列: RentID, DateStarted, DateEnded, CustomerID, etc. datestart始终在租赁期开始时输入,dateend初始为空,仅在租赁期到期时填写CustomerID是租用帐篷的客户的ID 我需要做的是防止用户为任何给定客户(由CustomerID表示)插入新行,如果该客户有dateend=NULL的租金 我不知道怎么做。我正在考虑检查约束,但它们不允许我查看其他行。我在考虑独特的约束,但不知道它们是否可以用于这种情

我有一个帐篷租金表,表中有以下列:

RentID, DateStarted, DateEnded, CustomerID, etc.  
datestart
始终在租赁期开始时输入,
dateend
初始为空,仅在租赁期到期时填写
CustomerID
是租用帐篷的客户的ID

我需要做的是防止用户为任何给定客户(由
CustomerID
表示)插入新行,如果该客户有
dateend=NULL
的租金

我不知道怎么做。我正在考虑检查约束,但它们不允许我查看其他行。我在考虑独特的约束,但不知道它们是否可以用于这种情况。我正在考虑插入触发器,但我不确定如果条件不满足,是否可以取消插入


谢谢你的帮助

我建议您查看MS的
而不是
触发器。这里的文档。。。


您还可以在传统的插入触发器中使用
回滚事务

您描述的内容听起来更像是应用程序逻辑的一部分。我会想,当你考虑你的数据库,以及你想要执行什么“规则”时,想想什么会使数据记录出错。根据您的描述,DateEnded为null的记录是有效的记录

根据我的经验,如果你真的需要触发器的话,触发器是很好的,但是非常危险,而且会很快以指数的方式增加问题的复杂性

如果可以的话,我个人会避免触发,并在应用程序端执行该逻辑


如果您使用的是SQL Server 2008,只需我的2美分

CREATE UNIQUE INDEX ix ON Rents(CustomerID) WHERE DateEnded IS NULL
早期版本可以使用索引视图(对于此选项,需要为更新基表的连接正确配置各种
SET
选项,但在SQL Server 2005中可能已经配置了这些选项。)


我不知道对SQL Server语法的检查有什么限制,但在SQLite中,它是一个表达式,实际上意味着任何可以查询的内容,都可以检查。(顺便说一句,SQL Server语法树的好资源在哪里?)您使用的是哪个版本的SQL Server?但您仍然应该在数据库中强制使用它作为最后一道防线。根本不需要扳机我也在想类似的事情,但是我突然想到,你可以插入一个填充了
dateend
的行并绕过规则。@Andriy-如果这真的是一个问题,OP可以删除基表的insert权限,并提供一个具有insert权限但不包含
dateend
列的视图。哇,这是一个很好的方案!你似乎毫不费力地就想到了。你最近一定吃了一顿营养丰富的饭谢谢我使用的是SQL Server 2008,因此第一个解决方案应该可以工作。由于数据库中的一些无效数据,我还不能让它工作,但我确信这正是我们需要的:-)谢谢!
CREATE VIEW dbo.ConstrainRents
WITH SCHEMABINDING
AS
SELECT CustomerID
FROM dbo.Rents 
WHERE DateEnded IS NULL

GO

CREATE UNIQUE CLUSTERED INDEX ix ON dbo.ConstrainRents(CustomerID)