Fluent Api 未创建完全正确的迁移文件内容,因此不会将唯一索引应用于数据库
Posted
技术标签:
【中文标题】Fluent Api 未创建完全正确的迁移文件内容,因此不会将唯一索引应用于数据库【英文标题】:Fluent Api is NOT creating a fully correct Migration file content, so that unique indexes are not being applied to the database 【发布时间】:2018-04-12 21:14:59 【问题描述】:(标题已更改,请参阅下面的编辑以了解更改)
当前项目:
点网 4.7 MVC 5 C# 7.1 MSSQL Server 2012(最新,全部最新)当我使用 fluent API 定义具有两个唯一索引的表时:
Property(x => x.UserId)
.HasColumnOrder(1)
.HasColumnName("UserId")
.HasColumnType("uniqueidentifier")
.HasDatabaseGeneratedOption(DatabaseGeneratedOption.Identity)
.HasColumnAnnotation(
"UserId",
new IndexAnnotation(
new IndexAttribute("IX_UserId")
IsUnique = true
)
)
.IsRequired();
Property(x => x.UserName)
.HasColumnOrder(2)
.HasColumnName("UserName")
.HasColumnType("nvarchar")
.HasMaxLength(256)
.HasColumnAnnotation(
"Username",
new IndexAnnotation(
new IndexAttribute("IX_Username")
IsUnique = true
)
)
.IsRequired();
我am在迁移文件中看到了正确的迁移条目:
UserId = c.Guid(
nullable: false,
identity: true,
defaultValueSql: "NEWID()",
annotations: new Dictionary<string, AnnotationValues>
"UserId",
new AnnotationValues(
oldValue: null,
newValue: "IndexAnnotation:
Name: IX_UserId,
IsUnique: True
"
)
),
UserName = c.String(
nullable: false,
maxLength: 256,
annotations: new Dictionary<string, AnnotationValues>
"Username",
new AnnotationValues(
oldValue: null,
newValue: "IndexAnnotation:
Name: IX_Username,
IsUnique: True
"
)
),
但是,当我检查数据库并查看表的键/索引时,我注意到 UserId
索引不是命名为 IX_UserId
(它被称为相当默认PK_dbo.User
),并且 UserName
不存在索引/唯一性根本。我需要在 SQL Management Studio 中手动创建它。
虽然 EF Fluent API 能够创建看起来像正确的迁移文件,并包含所有适当的属性,但这并没有转化为完全成功迁移到数据库,因为仅需要创建默认索引 (迁移文件中指定的所有索引信息都被完全忽略,有利于主键的默认装饰)。
谁能解释我哪里出错了?
编辑:
嗯……刚刚遇到this other example,也许是我哪里出错了?根据它,我的 Fluent API 应该是这样的:
Property(x => x.UserId)
.HasColumnOrder(1)
.HasColumnName("UserId")
.HasColumnType("uniqueidentifier")
.HasDatabaseGeneratedOption(DatabaseGeneratedOption.Identity)
.HasColumnAnnotation(
"UserId",
new IndexAnnotation(
new IndexAttribute("IX_UserId")
IsUnique = true,
Order = 1
)
)
.IsRequired();
Property(x => x.UserName)
.HasColumnOrder(2)
.HasColumnName("UserName")
.HasColumnType("nvarchar")
.HasMaxLength(256)
.HasColumnAnnotation(
"Username",
new IndexAnnotation(
new IndexAttribute(),
new IndexAttribute("IX_Username")
IsUnique = true
Order = 2
)
)
.IsRequired();
我是否正确阅读了其他帖子?
编辑 2:
Uhhhh... 我刚刚发现 使用了正确的索引名称,但仅在这些键作为 外键 存在于其他表中的位置上。因此,无论UserId
作为外键存在于其他表中,它都有正确的索引名称IX_UserId
,即使我的 Fluent API 从未在该表中描述该外键的索引。
威士忌。探戈。狐步舞。
编辑 3:
Fluent API没有创建正确的迁移文件。刚刚将那些其他表的外键与迁移文件进行了比较,那些其他表显然有以下内容:
.Index(t => t.UserId)
.Index(t => t.CourseId);
是的,Fluent API 没有构建正确的迁移文件,因为它缺少一大堆 .Index()
主键等条目。
【问题讨论】:
【参考方案1】:查看 HasColumnAnnotation 方法的文档:
我的猜测是您没有使用有效的 C#/EDM 注释名称。尝试使用IndexAnnotation.AnnotationName
常量作为索引的参数:
using System.Data.Entity.Infrastructure.Annotations;
...
Property(x => x.UserId)
...
.HasColumnAnnotation(
IndexAnnotation.AnnotationName, <-- this is the valid annotation name.
new ndexAttribute("Ix_UserId") IsUnique = true);
这是一个等于 "Index"
的常量值,但我怀疑这可能是您的问题的原因。
希望这会有所帮助!
【讨论】:
以上是关于Fluent Api 未创建完全正确的迁移文件内容,因此不会将唯一索引应用于数据库的主要内容,如果未能解决你的问题,请参考以下文章
QuickBlox - 如何使用 REST API + PHP 创建 blob 内容
流体力学模拟软件fluent,使用Gambit创建网格后无法导出网格文件
使用 Entity Framework 6.1 fluent API 创建唯一索引