我有一个模型User
:
public class User
{
[Key]
public int IDUser { get; set; }
[Required]
public string Forename { get; set; }
[Required]
public string Name { get; set; }
public int? IDUser_CreatedBy { get; set; }
public User User_CreatedBy { get; set; }
}
用户可以让其创建者(User_CreatedBy
)的ID(IDUser_CreatedBy
)当然位于同一个表中,但我希望有机会将其保留为空值({{1与未知的创作者)。这就是为什么User
具有IDUser_CreatedBy
可空类型的原因。
我不知道如何设置我的流畅API,以便将该外键int?
绑定到同一个表中的主键IDUser_CreatedBy
。
我知道如果我从该模型中删除IDUser
外键并添加新迁移,那么EF核心将隐式为我提供shadow属性外键,但我希望有机会更新我的IDUser_CreatedBy
稍后(在MVC控制器中)使用自定义创建的列User
并能够为自己命名该列。此外,我不想要阴影属性,因为我无法控制命名该列。
我怎样才能做到这一点?
修改
@IvanStoev - 感谢您的回答,但您的示例并没有为我提供有效的迁移代码:
IDUser_CreatedBy
它确实生成了我想要的ForeignKey列(protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropForeignKey(
name: "FK_Users_Users_CreatedByIDUser",
table: "Users");
migrationBuilder.RenameColumn(
name: "CreatedByIDUser",
table: "Users",
newName: "UserIDUser");
migrationBuilder.RenameIndex(
name: "IX_Users_CreatedByIDUser",
table: "Users",
newName: "IX_Users_UserIDUser");
migrationBuilder.AddColumn<int>(
name: "IDUser_CreatedBy",
table: "Users",
nullable: true);
migrationBuilder.CreateIndex(
name: "IX_Users_IDUser_CreatedBy",
table: "Users",
column: "IDUser_CreatedBy");
migrationBuilder.AddForeignKey(
name: "FK_Users_Users_IDUser_CreatedBy",
table: "Users",
column: "IDUser_CreatedBy",
principalTable: "Users",
principalColumn: "IDUser",
onDelete: ReferentialAction.Restrict);
migrationBuilder.AddForeignKey(
name: "FK_Users_Users_UserIDUser",
table: "Users",
column: "UserIDUser",
principalTable: "Users",
principalColumn: "IDUser",
onDelete: ReferentialAction.Restrict);
}
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropForeignKey(
name: "FK_Users_Users_IDUser_CreatedBy",
table: "Users");
migrationBuilder.DropForeignKey(
name: "FK_Users_Users_UserIDUser",
table: "Users");
migrationBuilder.DropIndex(
name: "IX_Users_IDUser_CreatedBy",
table: "Users");
migrationBuilder.DropColumn(
name: "IDUser_CreatedBy",
table: "Users");
migrationBuilder.RenameColumn(
name: "UserIDUser",
table: "Users",
newName: "CreatedByIDUser");
migrationBuilder.RenameIndex(
name: "IX_Users_UserIDUser",
table: "Users",
newName: "IX_Users_CreatedByIDUser");
migrationBuilder.AddForeignKey(
name: "FK_Users_Users_CreatedByIDUser",
table: "Users",
column: "CreatedByIDUser",
principalTable: "Users",
principalColumn: "IDUser",
onDelete: ReferentialAction.Restrict);
}
)和该键列的有效索引(IDUser_CreatedBy
),但它还添加了另一个ForeignKey(IX_Users_IDUser_CreatedBy
)女巫是一个我想是影子属性。因此,我有两个不同的ForeignKey列,它们引用同一个表中的一个Primerykey列(UserIDUser
)。在我的情况下,迁移实际上将旧列(IDUser
)重命名为新列(CreatedByIDUser
),这是我之前的shadow属性ForeignKey列的残余。我正在寻找的是迁移将完全摆脱之前的shadow属性并且只引入一个新的ForeignKey列(UserIDUser
)。有什么建议 ?
编辑2
@viveknuna - 谢谢你的榜样,但它也不适合我。
迁移看起来像这样:
IDUser_CreatedBy
它将我的补余阴影属性ForeignKey重命名为一个新名称,但它保留了该阴影属性。迁移还会添加新列 protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropForeignKey(
name: "FK_Users_Users_CreatedByIDUser",
table: "Users");
migrationBuilder.RenameColumn(
name: "CreatedByIDUser",
table: "Users",
newName: "User_CreatedByIDUser");
migrationBuilder.RenameIndex(
name: "IX_Users_CreatedByIDUser",
table: "Users",
newName: "IX_Users_User_CreatedByIDUser");
migrationBuilder.AddColumn<int>(
name: "IDUser_CreatedBy",
table: "Users",
nullable: true);
migrationBuilder.AddForeignKey(
name: "FK_Users_Users_User_CreatedByIDUser",
table: "Users",
column: "User_CreatedByIDUser",
principalTable: "Users",
principalColumn: "IDUser",
onDelete: ReferentialAction.Restrict);
}
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropForeignKey(
name: "FK_Users_Users_User_CreatedByIDUser",
table: "Users");
migrationBuilder.DropColumn(
name: "IDUser_CreatedBy",
table: "Users");
migrationBuilder.RenameColumn(
name: "User_CreatedByIDUser",
table: "Users",
newName: "CreatedByIDUser");
migrationBuilder.RenameIndex(
name: "IX_Users_User_CreatedByIDUser",
table: "Users",
newName: "IX_Users_CreatedByIDUser");
migrationBuilder.AddForeignKey(
name: "FK_Users_Users_CreatedByIDUser",
table: "Users",
column: "CreatedByIDUser",
principalTable: "Users",
principalColumn: "IDUser",
onDelete: ReferentialAction.Restrict);
}
,而不是ForeignKey(该列没有IDUser_CreatedBy
和AddForeignKey
方法。)
编辑3
@Ivan Stoev - 你是对的。我还没有提交整个模型,因为我认为它对结果没有任何影响,但现在很明显它已经...... :)首先 - 我确实创建了一个全新的命令行项目,并设法将正确的迁移支持为你说。然后我意识到我的模型有另一个属性CreateIndex
,它描述了由特定public List<User> UsersAdded { get; set; }
添加的所有用户。这就是罪魁祸首。它为新创建的迁移添加了新列User
。所以最后一个问题是:如何通过新属性UserIDUser
实现我所需要的一切?因为我希望有机会在我的MVC控制器中获得public List<User> UsersAdded { get; set; }
时User
创建的User
collecion。作为一种形式,我提交了我的整个模型(这次是正确的):
User
答案 0 :(得分:2)
EF Core fluent API使您可以完全控制对表列的命名,无论您使用的是显式属性还是影子模型属性。非常规外键属性使用 relationship 配置的HasForeignKey
流畅API进行映射。
您的实体模型属于Single Navigation Property,具有明确的FK属性类别,可以这样映射:
modelBuilder.Entity<User>()
.HasOne(e => e.User_CreatedBy) // reference navigation property
.WithMany() // no collection navigation property
.HasForeignKey(e => e.IDUser_CreatedBy); // foreign key property
答案 1 :(得分:-1)
添加到@Ivan回答,您也可以在课堂上使用dict
属性来更改列名。