asp.net - 如何在 ASP.NET Core 2.0 和 EF Core 2.0 中将应用程序设置从项目根目录获取到 IDesignTimeDbContextFactory 实现

标签 asp.net entity-framework entity-framework-core asp.net-core-2.0 ef-core-2.0

我正在 ASP.NET Core 2.0 中构建应用程序,但遇到 EntityFramework 迁移问题。

我的 DbContext 在一个单独的项目 (SolutionName\ProjectNamePrefix.Data) 中,因此我为 IDesignTimeDbContextFactory 接口(interface)创建了一个实现。

我想为不同的环境使用不同的连接字符串,为此我需要 appsettings.json

快速搜索后,我发现我可以在 CreateDbContext 函数中创建一个新的 IConfigurationRoot 对象,如下所示: https://codingblast.com/entityframework-core-idesigntimedbcontextfactory/

我添加了它,然后为了测试,尝试从 Data 项目根文件夹运行 dotnet ef migrations list -c MyContext

然后我得到以下错误:

The configuration file 'appsettings.json' was not found and is not optional. The physical path is 'C:\dev\*SolutionName*\*ProjectNamePrefix*.Data\bin\Debug\netcoreapp2.0\appsettings.json'.

所以,基本上,我尝试了 3 个选项来获得正确的根路径:

并且它们都返回相同的 ..\bin\debug\netcoreapp2.0\ 路径。当我从 VS 运行 Data 项目时,前两个选项会为我提供正确的项目根文件夹。

有没有办法获取正确的项目内容根文件夹?

因为当我将 --verbose 添加到 EF 命令时,它会注销一行:

Using content root 'C:\dev\FitsMeIdentity\FitsMeIdentity.Data\'.

所以我知道 EF 以某种方式知道项目根目录,但上面提到的所有选项都会返回已构建应用程序的路径。

我发现唯一可行的选项是我将 Copy output to root folder 更改为 Copy always 但从这里找到:https://www.benday.com/2017/02/17/ef-core-migrations-without-hard-coding-a-connection-string-using-idbcontextfactory/这不是一个好主意。

起初我什至考虑过为 IDesignTimeDbContextFactory 实现创建一个构造函数,它获取 IOptions 作为参数但没有用,遇到了与这里解释的相同的问题: Injecting Env Conn String into .NET Core 2.0 w/EF Core DbContext in different class lib than Startup prj & implementing IDesignTimeDbContextFactory

最佳答案

有点晚了,但对于那些讨厌硬编码连接字符串的人来说,这是解决方案:

internal class MigrationDbContextFactory : IDesignTimeDbContextFactory<AppDbContext>
{
    public AppDbContext CreateDbContext(string[] args)
    {
        IConfigurationRoot configuration = new ConfigurationBuilder()
            .AddJsonFile("appsettings.json", false)
            .Build();
        
        string connectionString = configuration.GetConnectionString("DefaultConnection");

        DbContextOptionsBuilder<AppDbContext> optionsBuilder = new DbContextOptionsBuilder<AppDbContext>();
        optionsBuilder.UseMySql(connectionString,
            ServerVersion.AutoDetect(connectionString),
            mySqlOptions =>
                mySqlOptions.EnableRetryOnFailure(
                    maxRetryCount: 10,
                    maxRetryDelay: TimeSpan.FromSeconds(30),
                    errorNumbersToAdd: null));

        return new AppDbContext(optionsBuilder.Options);
    }
}

关于asp.net - 如何在 ASP.NET Core 2.0 和 EF Core 2.0 中将应用程序设置从项目根目录获取到 IDesignTimeDbContextFactory 实现,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/47054063/

相关文章:

javascript - Request.QueryString 未定义

c# - 如何将 Dictionary 对象传递给泛型类型参数?

c# - PagedList 不会在 asp.net mvc 中进行真正的分页

asp.net-mvc - Entity Framework 验证的单元测试

Oracle DB 与 .NET Core 使用 ODP.Net Provider - 如何设置架构

asp.net - 在数据绑定(bind)到 sql 数据源后需要更改下拉列表

c# - 以编程方式发送短信

entity-framework - Entity Framework ,数据库优先还是模型优先?

c# - 是否可以在一个实体中拥有具有相同基类 (TPH) 的实体的多个集合属性?

c# - 实体类型上的导航还没有被添加到模型中,或者被忽略,或者 entityType 被忽略