插入到表中时发生错误,而不是从实体数据框架中触发
我正在使用entity framework4,插入一个新的logging使用entity framework,而不是插入触发器,而有一个标识列的表,而不是触发器用于修改插入的值之一,根据某些逻辑,entity framework引发exception“存储更新,插入或删除语句影响了意外数量的行(0)。实体可能已被修改或删除,因为实体被加载。刷新ObjectStateManager条目”。
任何人都可以帮助解决这个exception吗?
使用entity framework4.1,Ladislav发布的解决scheme添加一个selectScope_Identity()到触发器体的末尾解决了我的问题。 我已经复制了整个触发器创build的完整性。 有了这个触发器defenition,我可以使用context.SaveChanges()将行添加到表中。
ALTER TRIGGER [dbo].[CalcGeoLoc] ON [dbo].[Address] INSTEAD OF INSERT AS BEGIN -- SET NOCOUNT ON added to prevent extra result sets from -- interfering with SELECT statements. SET NOCOUNT OFF; -- Insert statements for trigger here INSERT INTO Address (Street, Street2, City, StateProvince, PostalCode, Latitude, Longitude, GeoLoc, Name) SELECT Street, Street2, City, StateProvince, PostalCode, Latitude, Longitude, geography::Point(Latitude, Longitude, 4326), Name FROM Inserted; select AddressId from [dbo].Address where @@ROWCOUNT > 0 and AddressId = scope_identity(); END
编辑处理计算值 (感谢Chris Morgan在评论中):
如果表中还有其他任何计算值,则必须将它们包含在SELECT中。 例如,如果你有一个使用GETDATE()
的CreatedDate
列,你可以像这样做select:
SELECT [AddressId], [CreatedDate] from [dbo].Addresses where @@ROWCOUNT > 0 and AddressId = scope_identity();
执行而不是由entity framework创build的插入操作。 这可能是潜在的问题,因为一旦您使用标识列,每个插入后面跟着:
select [Id] from [dbo].[TableXXX] where @@ROWCOUNT > 0 and [Id] = scope_identity()
所以问题是一旦插入被replace,这个查询会发生什么。 如果它被执行并返回null,你会得到和exception。 你可以在你的触发器中插入logging后添加它,但是如果原始查询也被执行,它也不会起作用。
您可以将您的触发器更改为插入和修改数据之前或之后。
您还需要返回标记为“ 计算”的任何属性
select [Id], [YourComputedColumn] from [dbo].[TableXXX] where @@ROWCOUNT > 0 and [Id] = scope_identity()
我还发现,您需要将StoreGeneratedPattern设置为Identity以使其在我用作主键但不生成标识值的nvarchar列上工作。 这是一个后插入触发器的情况下计算出一个唯一的值存储在键列中。 在其他情况下(添加和更新),可能需要将其设置为计算。