![](/img/trans.png)
[英]How to solve `A second operation started on this context ` error in this case
[英]How to prevent second operation on context in this case?
我有这样的代码:
它从资料库,在“自定义”谓词加载数据Where
这必须询问数据库有关确定真/假的权限
public List<User> getUsersWhoCanDoSomething()
{
return _context
.Users
.Where(x => CanPerformAction(user))
.Take(10000)
.OrderByDescending(x => x.CreationDate)
.ToList();
}
private bool CanPerformAction(User user)
{
var permission = _context
.Permissions
.FirstOrDefault(x => x.Name == user.Permissions.Name)
.Level;
return permission > 5;
}
如何更改此代码以防止出现此异常:
A second operation started on this context before a previous operation completed.
解:
移动Where
/ Filter
出来的LINQ链
public List<User> getUsersWhoCan...()
{
var users = _context
.Users
.Include(x => x.Permissions)
.Take(10000)
.OrderByDescending(x => x.CreationDate)
.ToList();
var tempList = new List<User>();
foreach (var user in users)
{
if (CanPerformAction(user))
{
tempList.Add(user);
}
}
return tempList;
}
问题的根源在于,一次只能将DbContext
对象用于一个查询。 但CanPerformAction
在getUsersWhoCanDoSomething
执行期间执行了自己的数据库调用(由于FirstOrDefault
)。 这就是为什么您要获得例外。
您的答案会奏效,但您要获取的数据超出了您的期望,然后丢弃了一些数据。 如果您的用户数超过10,000,则可能会因此而丢失一些用户(因为Take(10000)
)。
这应该做同样的事情(我想-我不知道您的确切数据库架构)。 它将条件合并到查询中,因此您仅获得所需的数据。
return _context
.Users
.Where(u => u.Permissions.Any(l => l.Level > 5))
.Take(10000)
.OrderByDescending(x => x.CreationDate)
.ToList();
执行同一操作的另一种方法是仍然使用单独的方法(从技术上讲=>
之后的任何东西在任何情况下都是单独的方法),但不要引用_context
或FirstOrDefault
(这会触发单独的db调用)。 如果使用.Where(x => CanPerformAction(user))
,这将与我的代码完全相同。
private bool CanPerformAction(User user)
{
return user.Permissions.Any(l => l.Level > 5);
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.