在.NET 6中为PostgreSQL配置DbContext

a64a0gku  于 2023-11-18  发布在  PostgreSQL
关注(0)|答案(1)|浏览(172)

首先,我展示我的db相关类:

DbContext.cs

public class BookingDbContext : DbContext
    {
        public BookingDbContext(DbContextOptions<BookingDbContext> options) : base(options)
        { }

        protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder)
        {
            if (!optionsBuilder.IsConfigured)
                optionsBuilder.UseNpgsql("Server=localhost;Port=5432;User Id=postgres;Password=password;Database=db");
        }

        protected override void OnModelCreating(ModelBuilder modelBuilder) 
        {
            base.OnModelCreating(modelBuilder);

            modelBuilder.Entity<Place>()
                .HasOne(p => p.Address)
                .WithOne(ad => ad.Place)
                .HasForeignKey<Address>(ad => ad.PlaceId)
                .OnDelete(DeleteBehavior.Cascade);
        }

        public DbSet<Place> Places { get; set; }
        public DbSet<Address> Addresses { get; set; }
    }

字符串

Program.cs

var builder = WebApplication.CreateBuilder(args);

builder.Services.AddDbContext<BookingDbContext>();

builder.Services.AddTransient<IPlaceService, PlaceService>();
builder.Services.AddTransient<IPlaceRepository, PlaceRepository>();

builder.Services.AddControllers().AddJsonOptions(options => options.JsonSerializerOptions.ReferenceHandler = ReferenceHandler.IgnoreCycles);

var app = builder.Build();

app.MapGet("/", () => "Hello World!");

app.UseHttpsRedirection();

app.MapControllers();

app.Run();


我像往常一样创建了CRUD方法,所以添加,删除,更新和获取。前3个方法没有问题,只有GET失败。我得到一个错误消息:

System.InvalidOperationException: No database provider has been configured for this DbContext. 
A provider can be configured by overriding the 'DbContext.OnConfiguring' method or by using 'AddDbContext' on the application service provider. 
If 'AddDbContext' is used, then also ensure that your DbContext type accepts a DbContextOptions<TContext> object in its constructor and passes it to the base constructor for DbContext.


你知道这是什么原因吗?就像我之前说的-当我添加,删除一些东西到数据库,从数据库,一切都很好。只有对于get方法,我得到了这样的错误。
编辑:

public async Task<IEnumerable<Place>> GetPlaces(bool includeAddress)
{
    if (includeAddress)
    {
       return await _dbContext.Places.Include(a => a.Address).ToListAsync();
    }
    else
    {
        return await _dbContext.Places.ToListAsync();
    }
}

public async Task<Place> GetById(int id)
{
   Place? place = await _dbContext.Places
                .Where(p => p.Id == id)
                .Include(p => p.Address)
                .FirstOrDefaultAsync();

   return place ?? throw new KeyNotFoundException($"Place with id: {id} not found.");
}

2ekbmq32

2ekbmq321#

我的想法是,当你的DbContext服务注册为Scoped时,它的示例将像一个Unit of Work一样执行,但生命周期很短。可能你的GET过程执行了多个作业,在你的工作完成之前,示例就被释放了。你可以尝试使用AddDbContextFactory方法:

builder.Services.AddDbContextFactory<BookingDbContext>();

字符串
并将创建DbContext的每个作业包含在using块中:

using (var db = _contextFactory.CreateDbContext())
{

 ...get operation code

}


这样,在所有的get操作之后,db一定会被处理掉。

相关问题