EF4 中的并发 - 如何有条件地创建实体

2024-03-21

我需要能够创建一个新的用户实体only if提供的电子邮件是唯一的。

我以前总是通过执行一个简单的操作来处理这个问题if (!UserSet.Any(...))在我之前AddToUserSet(...)。然而,这不是一个并发解决方案,并且会在重负载下崩溃。

我一直在研究事务,但据我所知,我也需要在 SELECT 上设置 UPDLOCK,但 EF4 不支持此操作。

其他人如何处理这个问题?


您可以通过在事务中包含 SELECT 来强制锁定:

using (var scope = new TransactionScope())
{
    // Create context
    // Check non existing email
    // Insert user
    // Save changes
}

这将使用可序列化事务,如果您想要并发插入解决方案,这就是您所需要的 - UPDLOCK 不足以确保在事务期间不会添加新记录。

这可能是非常糟糕的瓶颈,所以我同意@paolo:只需将唯一约束放置到数据库中,并在插入期间捕获异常(如果电子邮件不唯一)。

可序列化的事务来自在线书籍 http://msdn.microsoft.com/en-us/library/ms173763.aspx:

指定以下内容:

    Statements cannot read data that has been modified but not yet  
    committed by other transactions.

    No other transactions can modify data that has been read by the  
    current transaction until the current transaction completes.

    Other transactions cannot insert new rows with key values that
    would fall in the range of keys read by any statements in the current
    transaction until the current transaction completes.

范围锁被放置在与匹配的键值的范围内 每个语句的搜索条件 在事务中执行。这块 来自更新或的其他交易 插入任何符合条件的行 对于由执行的任何语句 当前交易。这意味着 如果 a 中的任何语句 交易第二次执行 时间,他们会读同一组 行。范围锁定一直保持到 交易完成。这是 最严格的隔离 级别,因为它锁定整个范围 钥匙并持有锁直到 交易完成。因为 并发较低,使用此选项 仅在必要时。该选项有 与设置 HOLDLOCK 相同的效果 所有 SELECT 语句中的所有表 一笔交易。

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

EF4 中的并发 - 如何有条件地创建实体 的相关文章

随机推荐