gpt4 book ai didi

c# - 使用 DI 访问 Startup.cs 中的 NPGSQL

转载 作者:太空宇宙 更新时间:2023-11-03 12:01:34 25 4
gpt4 key购买 nike

使用 .NET Core 2.1、NPGSQL、 Entity Framework 和 Linux。

在 Startups.cs 的 Configure 函数中,我在依赖注入(inject)类中调用一个函数,该类又调用另一个依赖注入(inject)类,该类使用 Entity Framework + NPGSQL 访问数据库。

配置服务:

    public void ConfigureServices(IServiceCollection services)
{
services.AddEntityFrameworkNpgsql()
.AddDbContext<MMContext>(options => options.UseNpgsql($"Host='localhost'; Port=1234;Database='mydb';Username='test';Password='test'"))
.BuildServiceProvider();
services.AddTransient<IMusicManager, MusicManager>();
services.AddTransient<IMusicRepo, MusicRepo>();

services.AddMvc()
.SetCompatibilityVersion(CompatibilityVersion.Version_2_1);
}

配置函数:

    public void Configure(IApplicationBuilder app, IHostingEnvironment env)
{
app.UseMvc();

using (var scope = app.ApplicationServices.GetService<IServiceScopeFactory>().CreateScope())
{
var mm = scope.ServiceProvider.GetRequiredService<IMusicManager>();
mm.DoSomeDBStartupStuff();
}
}

IMusicManager

实现看起来像这样:

    private readonly IMusicRepo _musicStoreRepo;
public MusicManager(IMusicRepo musicStoreRep)
{
_musicStoreRepo = musicStoreRepo;
}

public void DoSomeDBStartupStuff()
{
_musicStoreRepo.InsertSampleStuff();
_musicStoreRepo.CheckThisAndCheckThat();
}

IMusicRepo

实现看起来像这样:

    private readonly MMContext _context;
public MusicRepo(MMContext context)
{
_context = context;
}

public void InsertSampleStuff()
{
_context.Music.AddAsync(new music("abc"));
_context.Music.AddAsync(new music("123"));
_context.SaveChangesAsync();
}

MM上下文

这是这样实现的:

public class MMContext : DbContext
{
public MMContext(DbContextOptions<MMContext> options) : base(options) {}
... OnModelCreating etc...
}

启动时出现异常:

Application startup exception: System.InvalidOperationException: Reset() called on connector with state Executing at Npgsql.NpgsqlConnector.Reset() at Npgsql.ConnectorPool.Release(NpgsqlConnector connector) at Npgsql.NpgsqlConnection.Close(Boolean wasBroken) at Npgsql.NpgsqlConnection.Dispose(Boolean disposing) at System.ComponentModel.Component.Dispose() at Microsoft.EntityFrameworkCore.Storage.RelationalConnection.Dispose() at Microsoft.Extensions.DependencyInjection.ServiceLookup.ServiceProviderEngineScope.Dispose() at Microsoft.EntityFrameworkCore.DbContext.Dispose() at Microsoft.Extensions.DependencyInjection.ServiceLookup.ServiceProviderEngineScope.Dispose() at MM.Startup.Configure(IApplicationBuilder app, IHostingEnvironment env) in \Startup.cs:line 122 --- End of stack trace from previous location where exception was thrown --- at Microsoft.AspNetCore.Hosting.ConventionBasedStartup.Configure(IApplicationBuilder app) at Microsoft.AspNetCore.HostFilteringStartupFilter.<>c__DisplayClass0_0.b__0(IApplicationBuilder app) at Microsoft.AspNetCore.Hosting.Internal.AutoRequestServicesStartupFilter.<>c__DisplayClass0_0.b__0(IApplicationBuilder builder) at Microsoft.AspNetCore.Hosting.Internal.WebHost.BuildApplication()

我不确定是什么导致了这个问题。可能是我使用依赖注入(inject)的方式以及我使用范围的方式?感谢帮助。

最佳答案

注意到 void 函数中没有等待异步调用。

public void InsertSampleStuff()
{
_context.Music.AddAsync(new music("abc"));
_context.Music.AddAsync(new music("123"));
_context.SaveChangesAsync();
}

当您尝试保存这些更改时,这可能会导致 DbContext 出现线程问题。

要么使函数异步并正确等待这些调用,要么使用同步 API

public void InsertSampleStuff() {
_context.Music.Add(new music("abc"));
_context.Music.Add(new music("123"));
_context.SaveChanges();
}

如果采用异步路线,则考虑将该设置代码移至托管服务并在那里适本地等待它

引用引用Background tasks with hosted services in ASP.NET Core

关于c# - 使用 DI 访问 Startup.cs 中的 NPGSQL,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56806029/

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