Linq-to-SQL能够根据需要执行插入或更新操作吗?

4
我有一个分布式应用程序,通过WCF将数据发送到服务器以存储在数据库中(SQL Server 2008)。
通常这些数据是新的。所以我只需使用InsertAllOnSubmit()。
但是偶尔由于运行客户端设备的通信异常,我会得到一个已经存在于服务器中的对象。
是否有一种方法可以说InsertOrUpdateAllOnSubmit?还是我必须更改我的代码来逐个检查每个对象是否在数据库中,然后根据需要执行插入或更新?我有相当多的对象类型,所以这将变得非常繁琐 :(

1
你是如何定义“重复”的?是相同的主键吗?你是否使用标识列作为主键? - AaronLS
@AaronLS - 重复项具有相同的主键(尽管我偶尔也会遇到唯一约束冲突)。由于我的数据来自许多设备,因此主键通常是GUID。 - Vaccano
所以你可能不想要一个InsertOrUpdate,因为如果存在GUID冲突,你不会想在现有记录上执行更新操作。也就是说,我猜测两个设备尝试插入完全不同的数据,但它们生成了相同的GUID,因此为了使两个记录都具有唯一的主键添加到数据库中,你需要重新生成第二个记录的GUID,然后插入,而不是对第二个记录进行更新。也许你的情况与我想象的不同,但这就是我所思考的。 - AaronLS
@AaronLS - 我们的情况是设备发送数据,然后(由于某种原因我们不确定)没有收到服务器已接收数据的确认。我们决定这些设备的连接使得确保设备在插入数据之前清除数据比它值得的更多工作。此外,即使设备不确定是否已发送数据,我们也希望获得数据。但是,无论如何,如果设备不能100%确定服务器已经收到数据,它将在清除数据之前再次发送数据。因此,这不是GUID冲突的问题(这非常不可能)。 - Vaccano
2个回答

2

更改数据库上的存储过程以处理重复插入。


1
我没有存储过程来支持这些数据。它只是使用Linq-to-SQL来进行数据插入。 - Vaccano
1
你可以在Linq-To-SQL中附加一个存储过程来执行插入/更新操作。你可以编写一个存储过程来同时处理插入和更新。相比于C#,这可能是处理重复项的更有效的方式。 - Viv
请注意,如果您通过存储过程执行此操作,可以使用新的MERGE语法一次性执行插入和更新。我认为这是在MS SQL 2008中添加的。 - AaronLS

2
通常情况下,当您尝试进行任何插入或更新操作时出现冲突(例如对象已经存在),我看到的模式是一旦检测到冲突,您就会请求新数据并对其应用更新。这使您可以灵活地决定哪个更改获胜,或以某种方式提示用户查看新数据,并决定他们的数据是否应该获胜。所有这些都取决于上下文和业务规则。
这主要适用于更新,但如果您考虑为什么这些冲突会发生在插入操作中,您可能能够调整实现以使用并发检测和解决技术。 http://msdn.microsoft.com/en-us/library/bb399373.aspx

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接