entity-frameworkentity-framework-coreentity-framework-migrationsef-core-2.0cross-database

EF Core 2 cross database migrations


I am trying to create a cross database migration by using EF Core 2.0

When I am at the office I work by using a shared sql server database with the team. For this reason the code uses a configuration that reference the sql server provider

optionsBuilder.UseSqlServer(connectionString, serverOptions => {
    serverOptions.MigrationsHistoryTable("__EFMigrations", "dbo");
});

When a new migration is created this make the migration code use specific configuration of the sql server provider like

migrationBuilder.CreateTable(
    name: "Customers",
    schema: "dbo",
    columns: table => new
    {
        EntityID = table.Column<int>(nullable: false)
            .Annotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn),
        Name = table.Column<string>(maxLength: 255, nullable: false)
    },
    constraints: table => {
        table.PrimaryKey("PK_Customers", x => x.EntityID);
    });

Please note the Annotation method.

When out of office I am using a postgreSQL instance installed on my mac and I need to have a slightly different migration which makes use of the specific postgreSQL provider

.Annotation("Npgsql:ValueGenerationStrategy", NpgsqlValueGenerationStrategy.SerialColumn),

I know that I can manually modify the migration to specify both annotation as this does not have impact when running on a specifica database type.

However manually modify the migration is a tedious and error prone job that I would like to avoid.

Is there any way to make EF generate both Annotation methods automatically?

I have also tried to use the DbContext OnModelCreating method by specifying options on the ModelBuilder

modelBuilder
    .HasAnnotation("Npgsql:ValueGenerationStrategy", NpgsqlValueGenerationStrategy.SerialColumn)
    .HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn);

or

modelBuilder.ForNpgsqlUseSerialColumns();
modelBuilder.ForSqlServerUseIdentityColumns();

but the generated migration it is always related to the provider used at that specific moment.


Solution

  • There is no way to get EF Core to do it for you. What you're doing is the best approach. A slightly less tedious approach is to keep two separate sets of migrations--one for each provider.

    See EF Core Migrations with Multiple Providers for more details.