我在使用 Entity Framework Core 的 .NET Core 项目中面临依赖注入问题。我有多个 DbContext(
SourceDbContext
和 TargetDbContext
),都继承自 ApplicationDbContext
。目标是使用两个不同的连接字符串将数据从我的开发数据库(源)迁移到我的 QA 数据库(目标)。
但是,当我尝试打印
SourceDbContext
的连接字符串时,它始终使用 TargetDbContext
(DefaultConnection
) 的连接字符串,而不是使用 PreviousConnection
。
这是我的代码 -
Program.cs
:
builder.Services.AddDbContext<ApplicationDbContext>(options =>
options.UseNpgsql(builder.Configuration.GetConnectionString("DefaultConnection"))
.AddInterceptors(new PerformanceInterceptor()));
builder.Services.AddDbContext<SourceDbContext>(options =>
options.UseNpgsql(builder.Configuration.GetConnectionString("PreviousConnection")));
builder.Services.AddDbContext<TargetDbContext>(options =>
options.UseNpgsql(builder.Configuration.GetConnectionString("DefaultConnection")));
DataMigrationService
:
public class DataMigrationService
{
private readonly SourceDbContext _sourceContext;
private readonly TargetDbContext _targetContext;
public DataMigrationService(SourceDbContext sourceContext, TargetDbContext targetContext)
{
_sourceContext = sourceContext;
_targetContext = targetContext;
}
public async Task MigrateTableDataAsync()
{
Console.WriteLine($"Source DB Connection String: {_sourceContext.Database.GetConnectionString()}");
Console.WriteLine($"Target DB Connection String: {_targetContext.Database.GetConnectionString()}");
// Fetch data from source DB
var sourceWhiteLists = await _sourceContext.EmailDomainWhiteLists.ToListAsync();
// Fetch data from target DB
var targetWhiteLists = await _targetContext.EmailDomainWhiteLists.ToListAsync();
foreach (var wl in sourceWhiteLists)
{
var targetWL = await _targetContext.EmailDomainWhiteLists.FirstOrDefaultAsync(x => x.Value == wl.Value);
if (targetWL == null)
{
_targetContext.EmailDomainWhiteLists.Add(wl);
}
}
await _targetContext.SaveChangesAsync();
Console.WriteLine("Migration completed.");
}
}
SourceDbContext
:
public class SourceDbContext : ApplicationDbContext
{
public SourceDbContext(DbContextOptions<ApplicationDbContext> options)
: base(options)
{
}
}
在
Program.cs
中,我使用不同的连接字符串注入 SourceDbContext
和 TargetDbContext
。然而,SourceDbContext
似乎继承了ApplicationDbContext
的连接字符串,它始终指向QA数据库。
如何确保
SourceDbContext
使用自己的连接字符串 (PreviousConnection
),而不是从 ApplicationDbContext
继承默认连接字符串?
提前致谢!
附加信息:
SourceDbContext
仍在使用 DefaultConnection
SourceDbContext
和 TargetDbContext
才能将各自的连接字符串用于 DEV 和 QA 环境任何帮助将不胜感激!
问题可能源于此构造函数:
public SourceDbContext(DbContextOptions<ApplicationDbContext> options)
: base(options)
SourceDbContext 的构造函数应该期望
DbContextOptions<SourceDbContext>
,但这样做时,您将无法扩展基础 ApplicationDbContext,因为它需要 ApplicationDbContext 的选项。传递的 DbContextOptions 很可能是从 ApplicationDbContext 的默认注册解析的,而不是 SourceDbContext。
如果您想为源和目标的应用程序 DbContext 定义基类以使用不同的选项进行扩展,那么一种选择是使基 ApplicationDbContext 通用:
public abstract class ApplicationDbContext<T> : DbContext where T : ApplicationDbContext<T>
{
public ApplicationDbContext(DbContextOptions<T> options)
: base (options) { }
// ...
}
public class SourceDbContext : ApplicationDbContext<SourceDbContext>
{
public SourceDbContext(DbContextOptions<SourceDbContext> options)
: base(options)
{ }
}
...以及 TargetDbContext。
这应该确保您的源/目标 DbContext 可以分别解析它们的 DbOptions 并通过基本 ApplicationDbContext 向下传递它们。