gpt4 book ai didi

c# - 如果所有配置都在 DbContext 的 OnConfiguring 方法中,如何使用 AddDbContextPool

转载 作者:太空狗 更新时间:2023-10-30 00:37:11 31 4
gpt4 key购买 nike

我正在使用 PostgreSQL 并且我有如下 ApplicationDbContext:

public class ApplicationDbContext : DbContext
{
private readonly DatabaseSettings _databaseOptions;
public ApplicationDbContext() { }
public ApplicationDbContext(IOptions<DatabaseSettings> databaseOptions)
{
_databaseOptions = databaseOptions.Value;
}
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
modelBuilder.HasPostgresExtension("citext");
}
protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder)
{
if (_databaseOptions == null)
{
optionsBuilder.UseInMemoryDatabase(Guid.NewGuid().ToString());
}
else
{
optionsBuilder.UseNpgsql(_databaseOptions.ConnectionString,
npgsqlOptionsAction: sqlOptions =>
{
sqlOptions.EnableRetryOnFailure(
maxRetryCount: _databaseOptions.MaxRetryCount,
maxRetryDelay: TimeSpan.FromSeconds(_databaseOptions.MaxRetryDelay),
errorCodesToAdd: null);
});
}
}
}

该上下文是许多其他上下文的基础。我正在改进性能并尝试使用上下文池。文档说要添加轮询我应该:

services.AddDbContextPool<EmployeeContext>(options => options.UseNpgsql(connection));

但我想在 OnConfiguring 方法中存储.UseNpgsql 和 DbContext 的其他配置。如何实现?

最佳答案

除了使用它的有争议的好处(来自文档:“具有节省一些 DbContext 实例初始化成本的优势”),DbContext pooling根本不适用于您的场景,因为您的上下文包含 EF Core 不知道的状态:

private readonly DatabaseSettings _databaseOptions;

Limitations文档的部分明确指出:

Warning!

Avoid using DbContext Pooling if you maintain your own state (for example, private fields) in your derived DbContext class that should not be shared across requests. EF Core will only reset the state that is aware of before adding a DbContext instance to the pool.


AddDbContextPooloptionsAction 是必需的,而 AddDbContext 是可选的,这是有原因的。这是因为上述限制,加上额外的要求,您的 DbContext 派生类必须具有 single 公共(public)构造函数和 single DbContextOptions参数。通过传递空操作来欺骗 AddDbContextPool,您可以很容易地看到这一点:

services.AddDbContextPool<ApplicationDbContext>(options => { });

但是在运行时你会得到 InvalidOperationException

The DbContext of type 'ApplicationDbContext' cannot be pooled because it does not have a single public constructor accepting a single parameter of type DbContextOptions.

所以为了符合池化的条件,你必须移除所有这些

private readonly DatabaseSettings _databaseOptions;
public ApplicationDbContext() { }
public ApplicationDbContext(IOptions<DatabaseSettings> databaseOptions)
{
_databaseOptions = databaseOptions.Value;
}

然后添加这个

public ApplicationDbContext(DbContextOptions<ApplicationDbContext> options) : base(options) { }

现在您应该清楚地看到为什么您所要求的是不可能的。您的 OnConfiguring 方法需要 DatabaseSettings,但您无法提供它。因此,选项 必须在外部配置。

换句话说,你的要求是互斥的,因此没有解决方案。

关于c# - 如果所有配置都在 DbContext 的 OnConfiguring 方法中,如何使用 AddDbContextPool,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/55819175/

31 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com