使用Linq2SQL更新存储过程

4
我们使用由Linq生成的查询语句来检索数据,但对于INSERT和UPDATE,我们不允许生成SQL,而是限制使用存储过程。
我将DBML中的Update和Insert行为连接到了存储过程。存储过程被调用,数据被插入/更新=一切都很好,除了乐观并发的情况。
如果在检索和更新之间更改了记录,则更新应该失败。
当Linq自己生成Update语句时,它会像预期的那样抛出ChangeConflictException异常,但是使用存储过程时没有抛出任何异常。
非常感谢您对此的任何帮助!
2个回答

3
当将UPDATE行为配置为使用更新存储过程时,Linq2SQL会生成一个不会引发并发异常的方法。要处理乐观并发,可以在MSDN论坛中找到一个提议的解决方案
您可以在部分DataContext类中自己实现Update方法,并抛出一个ChangeConflictException
为了实现这一点,您需要:
  • 编写一个Update存储过程,该存储过程将当前值和原始值作为参数
    • 使用WHERE columnA = OriginalValueA ...仅在值未更改的情况下进行更新
    • 存储过程的最后一行是RETURN @@ROWCOUNT
    • rowcount让您查看是否已更新行
  • 在DBML中将Update行为设置为"use runtime"
  • 在xxxDataContext的部分类中实现Update方法,如下所示:
    • 代码取自Linq2SQL生成的代码,只添加了抛出异常的最后一行
partial void UpdateYourEntityClass(YourEntityClass obj)
        {
            EntityClass original = ((YourEntityClass)(EntityClasss.GetOriginalEntityState(obj)));
            int result = this.YourEntityClassUpdate((...));
            if (result == 0) throw new ChangeConflictException();
        }

工作正常,但不是直接的方式。还有其他选项吗?


0

这并不让我感到惊讶。当调用存储过程来执行更新和删除操作时,您将不得不进行自己的并发检查。L2S无法做到这一点,因为您基本上通过使用存储过程将L2S排除在循环之外。

这就是为什么我们在进行插入/更新/删除操作时不使用任何存储过程与我们的L2S后端之一的原因之一。使用存储过程的另一个缺点是您失去了对插入/更新/删除语句的强类型检查。


DBML 设计器允许将 INSERT、UPDATE 和 DELETE 行为映射到存储过程,并允许将原始值映射到更新存储过程的参数。唯一缺失的部分是行数检查和抛出 ChangeConflictException 异常。所有这些都已经存在,但 Designer.cs 中生成的代码没有抛出异常。谢谢! - PeterFromCologne

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