c# - 如何在桌面应用程序中使用 DbContext 和 DI?

标签 c# wpf entity-framework .net-core dependency-injection

我一直在使用 Entity Framework 开发几个非 Web 应用程序。我一直在努力寻找正确的方法来实现 Generic Repository使用 DbContext。

我搜索了很多,很多文章都是关于具有短暂上下文的 Web 应用程序。在桌面方法中,我找不到合适的方法。

一种方法是DbContext per ViewModel但我不同意将 View 与 Repository 层耦合。

另一个正在使用 using这样子句:

using(var context = new AppDbContext())
{
    // ...
}

但是这样我们就不会有Unit of Work也不能使用IoC Containers .

那么在桌面应用程序中使用 DbContext 的最佳实践是什么?

最佳答案

一个 DbContext意味着是短暂的:它本身就代表了一个工作单元。如果您需要长期的对象状态管理,那么您可以使用 ObjectStateManager直接在 Entity Framework 中。

为了确保访问 DbContext ,添加接口(interface)IDbContextFactory<TDbContext> (或者只是 IMyDbContextFactory 如果您只有一个 DbContext 类型)并将其注入(inject)您的 ViewModel 并使用短暂的 DbContext从中:

interface IDbContextFactory<TDbContext>
    where TDbContext : DbContext
{
    TDbContext Create();
}

// Configure:

void ConfigureServices( YourContainer container )
{
    container.RegisterSingleton( IDbContextFactory<YourDbContextType1>, // etc );
    container.RegisterSingleton( IDbContextFactory<YourDbContextType2>, // etc );
    container.RegisterSingleton( IDbContextFactory<YourDbContextType3>, // etc );
}

// Usage:

public class LongLivedViewModel
{
    private readonly IDbContextFactory<YourDbContextType3> dbFactory;

    public LongLivedViewModel( IDbContextFactory<YourDbContextType3> dbFactory)
    {
        this.dbFactory = dbFactory ?? throw new ArgumentNullException(nameof(dbFactory));

        this.DoSomethingCommand = new RelayCommand( this.DoSomethingAsync )
    }

    public RelayCommand DoSomethingCommand { get; }

    public async RelayCommand DoSomethingAsync()
    {
        using( YourDbContextType3 db = this.dbFactory.Create() )
        {
            // do stuff

            await db.SaveChangesAsync();
        }
    }
}

关于c# - 如何在桌面应用程序中使用 DbContext 和 DI?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/62233491/

相关文章:

c# - String.Format 参数空异常

WPF MEF + Prism 初始区域加载

c# - 类型引用找不到名为 '{clr-namespace :xxx}ClassName on MergedDictionary

c# - 对复制下数据库模式的持续开发的建议

c# - Cortana 是否支持 webhooks/调用外部 API?

c# - (重复) 'public int x;' 和 'public int x { get; 之间的区别放; }

c# - 将类型作为属性参数传递

wpf - 如何将容器的高度限制为特定内容元素的高度?

c# - Entity Framework - 如何在多个应用程序之间共享一些表

entity-framework - EF : Can I mix TPH and TPT when abstract base and a few concrete types are in TPH-table and other types have their own table?