简体   繁体   English

如何在Entity Framework中实现两个不同的外键?

[英]How I can achieve two different foreign keys in Entity Framework?

I need to bind some relations in Entity Framework Code First but I don't know how to. 我需要先在实体框架代码中绑定一些关系,但是我不知道该如何做。 I searched deeply, I tried a lot of ways but still without luck. 我进行了深入的搜索,尝试了很多方法,但是仍然没有运气。 I think I need to use the fluent API. 我想我需要使用流畅的API。

Scenario 情境

Organizations has many Notes . 组织有很多注释 Projects has many Notes . 项目有很多注释 Notes has one Organization or Project . Notes有一个组织项目

The idea is to bind every entity ( Organization or Project ) to only one column in Note entity: SourceKey . 这个想法是将每个实体( 组织项目 )仅绑定到Note实体的一个列: SourceKey

Organization 组织

public class Organization
{
    [DatabaseGenerated(DatabaseGeneratedOption.Identity)]
    public Guid ID { get; set; }

    [Required(ErrorMessage = "A name is required.")]
    public string Name { get; set; }

    public virtual ICollection<Project> Projects { get; set; }
    public virtual ICollection<Note> Notes { get; set; }
}

Project 项目

public class Project
{
    [DatabaseGenerated(DatabaseGeneratedOption.Identity)]
    public Guid ID { get; set; }

    [Required(ErrorMessage = "An organization is required.")]
    [Display(Name = "Organization")]
    public Guid OrganizationID { get; set; }

    [Required(ErrorMessage = "A name is required.")]
    public string Name { get; set; }

    public virtual Organization Organization { get; set; }
    public virtual ICollection<Note> Notes { get; set; }
}

Note 注意

public class Note
{
    [DatabaseGenerated(DatabaseGeneratedOption.Identity)]
    public Guid ID { get; set; }

    public Guid SourceKey { get; set; }

    [Required(ErrorMessage = "A title is required.")]
    public string Title { get; set; }

    [Column(TypeName = "ntext")]
    public string Value { get; set; }

    public string Tags { get; set; }
}

So an example of data can be: 因此,数据示例可以是:

Organizations 组织机构

7846ac27-d490-4483-8f0b-975a11333dea, Google

Projects 专案

3446ac27-d490-4323-8121-921a11333dac, Search
7846ac27-8497-5683-213b-933a11233abc, Maps

Notes 笔记

1236ac27-d490-4323-8121-921a11333dac, 7846ac27-d490-4483-8f0b-975a11333dea, A note for Google organization
2346ac27-d490-4323-8121-921a11335aab, 7846ac27-d490-4483-8f0b-975a11333dea, Another note for Google organization
3456ac27-d490-4323-8121-921a11331bcc, 7846ac27-8497-5683-213b-933a11233abc, Just a note for Maps project

BTW BTW

I don't need to navigate from Notes (up) to Organization or Project. 我不需要从Notes(向上)导航到Organization或Project。 If I have an Organization or Project, I will need to navigate (down) to Notes. 如果我有一个组织或项目,则需要导航(向下)到Notes。

As mentioned above, if you don't require navigation properties from notes, you can omit them. 如上所述,如果您不需要注释的导航属性,则可以忽略它们。

If you then included two fields on the Note class to use for foreign key associations: 如果然后在Note类上包括两个字段以用于外键关联:

public class Note
{
    // Code

    public Guid OrganizationId { get; set; }
    public Guid ProjectId { get; set; }
}

I assume most notes won't belong to both an Organisation , and a Project (although they can). 我认为大多数笔记不会同时属于OrganisationProject (尽管它们可以属于)。

You should be able to configure your mapping using the fluent API like this: 您应该能够使用流利的API配置映射,如下所示:

modelBuilder.Entity<Organization>()
        .HasMany(o => o.Notes)                    // Many Notes
        .WithOptional()                           // No navigation property on Notes            
        .HasForeignKey(n => n.OrganizationId );   // Use OrganizationId as a foreign key

modelBuilder.Entity<Project>()
        .HasMany(o => o.Notes)
        .WithOptional()
        .HasForeignKey(n => n.ProjectId);

You can define the Note entity without navigation properties, 您可以定义没有导航属性的Note实体,

public class Note
{
    [DatabaseGenerated(DatabaseGeneratedOption.Identity)]
    public Guid ID { get; set; }

    public Guid SourceKey { get; set; }

    [Required(ErrorMessage = "A title is required.")]
    public string Title { get; set; }

    [Column(TypeName = "ntext")]
    public string Value { get; set; }

    public string Tags { get; set; }

    public int OrganizationId { get; set; }
    public int ProjectId { get; set; }
}

If you don't need navigation properties, you can define it simply using the class below: 如果不需要导航属性,则可以使用下面的类轻松定义它:

public class Note
{
    [DatabaseGenerated(DatabaseGeneratedOption.Identity)]
    public Guid NoteID { get; set; }

    public Guid SourceKey { get; set; }

    [Required(ErrorMessage = "A title is required.")]
    public string Title { get; set; }

    [Column(TypeName = "ntext")]
    public string Value { get; set; }

    public string Tags { get; set; }

    public Guid OrganizationId { get; set; }
    public Guid ProjectId { get; set; }

}

Note OrganizationId and ProjectId are of type Guid . 注意OrganizationIdProjectId的类型为Guid

I think that the use of one column (SourceKey) for multiple foreign keys is not possible. 我认为不可能对多个外键使用一列(SourceKey)。 It throws you an error. 它会抛出一个错误。 I was pretty sure that was possible but maybe I'm confused with the MyISAM tables in MySQL. 我非常确定这是可能的,但是也许我对MySQL中的MyISAM表感到困惑。 I will use the foreign keys columns in the Note model as Chris suggest. 我将使用克里斯建议的Note模型中的外键列。 Thanks to everybody. 感谢大家。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM