Changing default schema at runtime

Required Nuget Package:
Thinktecture.EntityFrameworkCore.Relational

Changes the default schema of the DbContext and its Migrations at runtime.

Usage

1. Implement IDbDefaultSchema

The DbContext has to implement the interface IDbDefaultSchema. The interface provides a new property Schema of type string.

public class DemoDbContext : DbContext, IDbDefaultSchema
{
   public string Schema { get; }

   public DemoDbContext(DbContextOptions<DemoDbContext> options, IDbDefaultSchema schema = null)
      : base(options)
   {
      Schema = schema?.Schema;
   }

Remarks: Setting the Schema in constructor by injecting an instance of IDbDefaultSchema is just an example. You can set the Schema in any way you want.

2. Register Components

Use extension method AddSchemaRespectingComponents to register some components so EF "knows" about IDbDefaultSchema.

ServiceCollection services = ...;

services
   .AddDbContext<DemoDbContext>(builder => builder
                                              //.UseSqlite("...")
                                              .UseSqlServer("...")
                                              ...
                                              .AddSchemaRespectingComponents());

3. (Optional) Using default schema in migrations

An instance of IDbDefaultSchema can (but don't have to) be injected into migration if some operations (like raw SQL) have to know the schema.

public partial class MyMigration : Migration
{
   public MyMigration(IDbDefaultSchema schema)
   {
   }

   ...
}

4. (Optional) Changing schema of MigrationsHistoryTable

The IDbDefaultSchema has no effect on the migration history table. Use the EF method MigrationsHistoryTable to change the table name and schema.

ServiceCollection services = ...;

services
   .AddDbContext<DemoDbContext>(builder => builder
          .UseSqlServer("conn-string", sqlOptions =>
                                      {
                                         if (schema != null)
                                            sqlOptions.MigrationsHistoryTable("__EFMigrationsHistory", schema);
                                       })
    ...

Remarks

For the change of the schema at runtime we have to decorate some EF Core components. The decoration of the components is done via AddSchemaRespectingComponents.
Following components are decorated:

  • IModelCustomizer by DefaultSchemaModelCustomizer
  • IModelCacheKeyFactory by DefaultSchemaRespectingModelCacheKeyFactory
  • IMigrationsAssembly by DefaultSchemaRespectingMigrationAssembly
1 visit in last 30 days

Comments