EF Core 2.0 迁移命名约定
EF Core 2.0 migrations naming conventions
我正在尝试将使用 EF 6 的项目移动到 EF Core 2。
旧项目中的迁移生成了一个数据库,所有内容都带有 "dbo." 前缀,例如表是 "dbo.Something",外键是 "FK_dbo.Something_dbo.SomethingElse_Id".
但 EF Core 不遵循此约定,它省略了 "dbo."。
有没有办法让 EF Core 遵循旧约定,这样我现有的数据库仍然可以工作?
您可以使用 DbContext
的 OnModelCreating
方法更改命名约定。这是 blog post I wrote:
的示例
public class BloggingContext : DbContext
{
public DbSet<Blog> Blogs { get; set; }
public DbSet<Post> Posts { get; set; }
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
base.OnModelCreating(modelBuilder);
// Singularize table name
// Blogs => Blog
foreach (var entityType in modelBuilder.Model.GetEntityTypes())
{
// Add NuGet package "Humanizer" to use Singularize()
entityType.Relational().TableName = entityType.Relational().TableName.Singularize();
}
// Prefix column names with table name
// Id => Blog_Id
foreach (var entityType in modelBuilder.Model.GetEntityTypes())
{
foreach (var property in entityType.GetProperties())
{
property.Relational().ColumnName = entityType.Relational().TableName + "_" + property.Relational().ColumnName;
}
}
// Rename Foreign Key
// FK_Post_Blog_BlogId => FK_Post_Blog_BlogId_Test
foreach (var entityType in modelBuilder.Model.GetEntityTypes())
{
foreach (var property in entityType.GetProperties())
{
foreach (var fk in entityType.FindForeignKeys(property))
{
fk.Relational().Name = fk.Relational().Name + "_Test";
}
}
}
// Rename Indices
// IX_Blog_Url => IX_Blog_Url_Test
foreach (var entityType in modelBuilder.Model.GetEntityTypes())
{
foreach (var index in entityType.GetIndexes())
{
index.Relational().Name = index.Relational().Name + "_Test";
}
}
}
}
没有直接的方法可以实现这一点。唯一的方法是手动构建 PK 和 FK 名称。重写 DBContext 的 OnModelCreating 方法,如下所示。如果您已经在 OnModelCreating 中有定义,那么请确保将代码粘贴到最后(在您流畅的 api 配置之后,如果有的话)。
protected override void OnModelCreating(ModelBuilder builder)
{
foreach (var pk in builder.Model
.GetEntityTypes()
.SelectMany(t => t.GetKeys()))
{
pk.Relational().Name = "PK_dbo." + pk.DeclaringEntityType.ClrType.Name;
}
foreach (var fk in builder.Model
.GetEntityTypes()
.SelectMany(t => t.GetForeignKeys()))
{
fk.Relational().Name = "FK_dbo." + fk.DeclaringEntityType.ClrType.Name +
"_dbo." + fk.PrincipalEntityType.ClrType.Name +
"_" + fk.Properties.First().Name;
}
}
我正在尝试将使用 EF 6 的项目移动到 EF Core 2。
旧项目中的迁移生成了一个数据库,所有内容都带有 "dbo." 前缀,例如表是 "dbo.Something",外键是 "FK_dbo.Something_dbo.SomethingElse_Id".
但 EF Core 不遵循此约定,它省略了 "dbo."。
有没有办法让 EF Core 遵循旧约定,这样我现有的数据库仍然可以工作?
您可以使用 DbContext
的 OnModelCreating
方法更改命名约定。这是 blog post I wrote:
public class BloggingContext : DbContext
{
public DbSet<Blog> Blogs { get; set; }
public DbSet<Post> Posts { get; set; }
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
base.OnModelCreating(modelBuilder);
// Singularize table name
// Blogs => Blog
foreach (var entityType in modelBuilder.Model.GetEntityTypes())
{
// Add NuGet package "Humanizer" to use Singularize()
entityType.Relational().TableName = entityType.Relational().TableName.Singularize();
}
// Prefix column names with table name
// Id => Blog_Id
foreach (var entityType in modelBuilder.Model.GetEntityTypes())
{
foreach (var property in entityType.GetProperties())
{
property.Relational().ColumnName = entityType.Relational().TableName + "_" + property.Relational().ColumnName;
}
}
// Rename Foreign Key
// FK_Post_Blog_BlogId => FK_Post_Blog_BlogId_Test
foreach (var entityType in modelBuilder.Model.GetEntityTypes())
{
foreach (var property in entityType.GetProperties())
{
foreach (var fk in entityType.FindForeignKeys(property))
{
fk.Relational().Name = fk.Relational().Name + "_Test";
}
}
}
// Rename Indices
// IX_Blog_Url => IX_Blog_Url_Test
foreach (var entityType in modelBuilder.Model.GetEntityTypes())
{
foreach (var index in entityType.GetIndexes())
{
index.Relational().Name = index.Relational().Name + "_Test";
}
}
}
}
没有直接的方法可以实现这一点。唯一的方法是手动构建 PK 和 FK 名称。重写 DBContext 的 OnModelCreating 方法,如下所示。如果您已经在 OnModelCreating 中有定义,那么请确保将代码粘贴到最后(在您流畅的 api 配置之后,如果有的话)。
protected override void OnModelCreating(ModelBuilder builder)
{
foreach (var pk in builder.Model
.GetEntityTypes()
.SelectMany(t => t.GetKeys()))
{
pk.Relational().Name = "PK_dbo." + pk.DeclaringEntityType.ClrType.Name;
}
foreach (var fk in builder.Model
.GetEntityTypes()
.SelectMany(t => t.GetForeignKeys()))
{
fk.Relational().Name = "FK_dbo." + fk.DeclaringEntityType.ClrType.Name +
"_dbo." + fk.PrincipalEntityType.ClrType.Name +
"_" + fk.Properties.First().Name;
}
}