C# EFCore scaffold数据库,并在运行时迁移到另一个上下文

C# EFCore scaffold数据库,并在运行时迁移到另一个上下文,c#,generics,entity-framework-core,.net-4.8,C#,Generics,Entity Framework Core,.net 4.8,最近我开始创建一些PostgreSQL到Mdb/Accdb数据库转换器。我已经设法用一种比较通用的方式做到了: public static void TransferData<TSource, TDest>(DbContext sourceContext, DbContext destContext) where TSource : class where TDest : class { destContext.Set<TDest>().A

最近我开始创建一些PostgreSQL到Mdb/Accdb数据库转换器。我已经设法用一种比较通用的方式做到了:

public static void TransferData<TSource, TDest>(DbContext sourceContext, DbContext destContext)
    where TSource : class where TDest : class
{
            destContext.Set<TDest>().AddRange(sourceContext.Set<TSource>().Select(_mapper.Map<TDest>));
}
public void RegisterGenericMapping<TSource, TDest>() => CreateMap<TSource, TDest>();

foreach (var entityName in EntitiesList.DestinationDb)
{
    var sourceType = ReflectionHelper.GetType($"{EntitiesList.sourceNamespace}.{entityName}"); // My helper class to search in all assemblies
    var destType = ReflectionHelper.GetType($"{EntitiesList.destNamespace}.{entityName}");

    typeof(MappingProfile).GetMethods().First(x => x.Name == nameof(RegisterGenericMapping))
        .MakeGenericMethod(sourceType, destType).Invoke(this, null);
}
publicstaticvoidtransferdata(DbContext-sourceContext,DbContext-destContext)
where TSource:class where TDest:class
{
destContext.Set().AddRange(sourceContext.Set().Select(_mapper.Map));
}
以通用方式在AutoMapper中指定映射:

public static void TransferData<TSource, TDest>(DbContext sourceContext, DbContext destContext)
    where TSource : class where TDest : class
{
            destContext.Set<TDest>().AddRange(sourceContext.Set<TSource>().Select(_mapper.Map<TDest>));
}
public void RegisterGenericMapping<TSource, TDest>() => CreateMap<TSource, TDest>();

foreach (var entityName in EntitiesList.DestinationDb)
{
    var sourceType = ReflectionHelper.GetType($"{EntitiesList.sourceNamespace}.{entityName}"); // My helper class to search in all assemblies
    var destType = ReflectionHelper.GetType($"{EntitiesList.destNamespace}.{entityName}");

    typeof(MappingProfile).GetMethods().First(x => x.Name == nameof(RegisterGenericMapping))
        .MakeGenericMethod(sourceType, destType).Invoke(this, null);
}
public void RegisterGenericMapping()=>CreateMap();
foreach(EntityList.DestinationDb中的变量entityName)
{
var sourceType=ReflectionHelper.GetType($“{EntitiesList.sourceNamespace}.{entityName}”);//要在所有程序集中搜索的My helper类
var destType=ReflectionHelper.GetType($“{EntityList.destNamespace}.{entityName}”);
typeof(MappingProfile).GetMethods().First(x=>x.Name==nameof(RegisterGenericMapping))
.MakeGenericMethod(sourceType,destType).Invoke(this,null);
}
通过以下方式获取所需的实体列表:

public static List<string> DestinationDb = typeof(MsAccessContext).GetProperties()
    .Where(x => x.PropertyType.Name == "DbSet`1")
    .Select(x => x.PropertyType.GenericTypeArguments[0]?.Name).ToList();

public static string sourceNamespace = "DbConverter.NpgsqlSupport.Entities";
public static string destNamespace = "DbConverter.MsAccessSupport.Entities";
公共静态列表DestinationDb=typeof(MsAccessContext).GetProperties() .Where(x=>x.PropertyType.Name==“DbSet`1”) .Select(x=>x.PropertyType.GenericTypeArguments[0]?.Name).ToList(); 公共静态字符串sourceNamespace=“DbConverter.NpgsqlSupport.Entities”; 公共静态字符串destNamespace=“DbConverter.MsAccessSupport.Entities”; 但问题是我的核心仍然有模型。对于源和目标上下文。。。如果不在运行前先进行数据库迁移,并将相同的类粘贴到目标上下文中,则无法使用它

我想要实现的是摆脱上下文类中的所有模型类和数据库集:

在运行时构建源数据库并添加数据库集,然后基于源构建的模型创建目标模型和数据库集,将迁移应用到目标数据库,然后启动该过程


目前,我的解决方案只适用于一个准备好的数据库。我需要在运行时为每个数据库自动准备它。

不要为此使用EF。只需使用ADO.NET DataReaders和DataTables即可。它们在没有设计时元数据的情况下工作得非常好。

我将研究ADO.NET。我希望它不那么复杂,也不太容易启动。经过研究,我不能100%确定我是否正确,但我发现ADO.NET只是一个“接口”,允许用户打开与数据库的连接(例如PostgreSQL),执行查询和读卡器,检查结果集元数据,并将结果加载到内存中的数据表中,它们具有更改跟踪功能,并支持使用DataAdapter或大容量插入库写入目标数据库。好的,然后我看到ADO.NET是我第一次尝试管理数据库,一段时间后我得出结论,它的效率比实体框架低。但后来我只使用了
var conn=NpgsqlConnection.Open();var cmd=new命令(conn)[…]
,传递查询并执行,带或不带读卡器(取决于它是读取还是插入/删除/更新)。您是否可以准备使用
DataTables
DataAdapters
的简短示例?ADO.NET不会为您创建目标表。您必须检查数据集并生成DDL来创建目标表。