先处理DBContext,然后用EF6将实体附加到新实例



我有一个应用程序,需要每隔一小时将内存中的数据与远程数据库同步。因此,在应用程序启动时从数据库中提取数据,并释放DbContext。

List<Department> Departments;
using (var context = new CompanyContext())
{
    this.Departments = context.Departments.Include("Employees").AsNoTracking().ToList();
}

另一个线程在一小时后启动同步功能。我可以确认对[this.Departments]集合(由所有线程共享)进行了HAVE更改。

bool changesDetectedAndSaved = false;
using (var context = new CompanyContext())
{
    foreach (var department in this.Departments)
    {
        foreach (var employee in department.Employees)
        {
            context.Departments.Attach(employee);
        }
        context.Departments.Attach(departments);
    }
    // Always returns false.
    context.ChangeTracker.DetectChanges();
    changesDetectedAndSaved = context.ChangeTracker.HasChanges());
    if (changesDetectedAndSaved) { context.SaveChanges(); }
}
Console.WriteLine("Saved: {0}.", changesDetectedAndSaved);

[context.ChangeTracker.HasChanges()]方法ALWAYS返回false。由于数据库是远程的,所以DbContext不可能保持这么长时间。DbSet<TEntity>.Attach(entity)不是应该处理这种事情吗?

请注意:这不是线程问题,因为当代码放入单个上下文(如此处)时,我会得到相同的结果。

没有DbContext来跟踪该小时内的更改;将实体附加到CCD_ 6是指示CCD_ 7实例跟踪所述实体。当您将实体对象附加到新的DbContext时,它将附加为Unchanged,而当您调用SaveChanges()时,它不会发生任何事情。

若要在数据库中更新实体,必须将其状态设置为Modified。连接和设置状态的最简单方法如下:

context.Entry( employee ).State = EntityState.Modified;

读取此

在实体框架5之前,有用于自跟踪实体的T4模板(仍可使用),其中实体对象本身可以跟踪其状态,但不再建议使用这些模板。

最新更新