簡體   English   中英

C#EF6實體映射

[英]C# EF6 entity mapping

我目前正在開發一個項目(WCF服務),該項目應將EF6與MySql數據庫一起使用。 該部分本身已經可以正常工作,但是映射存在很大問題。

我有3個實體,如下所示:

Employee - ManyToMany - Project - OneToMany - ProjectStep

我的數據庫模型是這樣建立的:

員工表:

CREATE TABLE `employee` (
  `ID` int(11) NOT NULL AUTO_INCREMENT,
  `Name` varchar(255) DEFAULT NULL,
  `JobDescription` varchar(255) DEFAULT NULL,
  `Department` varchar(255) DEFAULT NULL,
  `DirectDialing` varchar(255) DEFAULT NULL,
  `Status` bit(1) DEFAULT NULL,
  PRIMARY KEY (`ID`)
)

項目表:

CREATE TABLE `project` (
  `ID` int(11) NOT NULL AUTO_INCREMENT,
  `Titel` varchar(255) DEFAULT NULL,
  `StartDate` datetime DEFAULT NULL,
  `EndDate` datetime DEFAULT NULL,
  `Description` varchar(255) DEFAULT NULL,
  `ProjectLeader` int(11) DEFAULT NULL,
  `Status` int(11) DEFAULT NULL,
  PRIMARY KEY (`ID`),
  CONSTRAINT `project_fk` FOREIGN KEY (`ProjectLeader`) REFERENCES `employee` (`ID`)
)

ProjectStep表:

CREATE TABLE `project_step` (
  `ID` int(11) NOT NULL AUTO_INCREMENT,
  `Description` text,
  `StartDate` datetime DEFAULT NULL,
  `EndDate` datetime DEFAULT NULL,
  `Project` int(11) DEFAULT NULL,
  PRIMARY KEY (`ID`),
  CONSTRAINT `project_step_fk` FOREIGN KEY (`Project`) REFERENCES `project` (`ID`)
)

映射表員工-項目

CREATE TABLE `employee_project` (
  `ID` int(11) NOT NULL AUTO_INCREMENT,
  `EmployeeId` int(11) DEFAULT NULL,
  `ProjectId` int(11) DEFAULT NULL,
  PRIMARY KEY (`ID`),
  CONSTRAINT `projectId_fk` FOREIGN KEY (`ProjectId`) REFERENCES `project` (`ID`)
  CONSTRAINT `employeeId_fk` FOREIGN KEY (`EmployeeId`) REFERENCES `employee` (`ID`)
)

然后,我按如下方式創建我的實體:

[DataContract(Namespace = "Shared")]
public class Employee
{
    public Employee()
    {
        this.Projects = new List<Project>();
    }

    [DataMember]
    [Key]
    public int ID { get; set; }

    [DataMember]
    public String Name { get; set; }

    [DataMember]
    public String Berufsbezeichnung { get; set; }

    [DataMember]
    public String Abteilung { get; set; }

    [DataMember]
    public String Durchwahl { get; set; }

    [DataMember]
    public bool Status { get; set; }

    [DataMember]
    public virtual ICollection<Project> Projects { get; set; }
}

[DataContract(Namespace = "Shared")]
public class Project
{

    public Project()
    {
        this.EmployeesWorkingOnProject = new List<Employee>();
        this.ProjectSteps = new List<ProjectStep>();
    }

    [DataMember]
    [Key]
    public int ID { get; set; }

    [DataMember]
    public String Titel { get; set; }

    [DataMember]
    public DateTime StartDatum { get; set; }

    [DataMember]
    public DateTime EndDatum { get; set; }

    [DataMember]
    public String Beschreibung { get; set; }

    [DataMember]
    [Column("Projektleiter")]
    public Employee Projektleiter { get; set; }

    [DataMember]
    public bool Status { get; set; }

    [DataMember]
    public virtual ICollection<Employee> EmployeesWorkingOnProject { get; set; }

    [DataMember]
    [ForeignKey("Project")]
    public virtual ICollection<ProjectStep> ProjectSteps { get; set; }
}

[DataContract(Namespace = "Shared")]
public class ProjectStep
{
    [DataMember]
    public int ID { get; set; }

    [DataMember]
    public String Beschreibung { get; set; }

    [DataMember]
    public DateTime StartDatum { get; set; }

    [DataMember]
    public DateTime EndDatum { get; set; }

    [DataMember]
    public Project Project { get; set; }
}

並使用Fluent API創建ManyToMany關系以及OneToMany

protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
    modelBuilder.Conventions.Remove<PluralizingTableNameConvention>();

    modelBuilder.Entity<Employee>().HasMany(e => e.Projects).WithMany(t => t.EmployeesWorkingOnProject).Map(m =>
    {
        m.MapLeftKey("MitarbeiterID");
        m.MapRightKey("ProjektID");
        m.ToTable("mitarbeiter_projekte");
    });

    modelBuilder.Entity<ProjectStep>().HasRequired<Project>(p => p.Project).WithMany(p => p.ProjectSteps);
}

我真的很茫然,因為當我嘗試插入一個新的Project ,出現錯誤:

類型'Shared.Project'上屬性'ProjectSteps'上的ForeignKeyAttribute無效。 在從屬類型“ Shared.ProjectStep”上找不到外鍵名稱“ Project”。 Name值應該是逗號分隔的外鍵屬性名稱列表。

我認為映射中存在一些問題,這是導致此錯誤的原因。 對於我的映射錯誤以及我什至使用了正確的方法,我完全是茫然。

因此,我的問題是,是否應該將DataAnnotationsFluent API混合使用,有人可以幫助我正確實現此映射嗎?

請注意,這是我的第一個C#/ EF6項目,我在所有方面都不是很普通,因此歡迎您進行一些解釋。

數據注釋和流利的配置可以混合使用。 但是特別是對於關系,我發現流暢的配置更加直觀。 ForeignKey屬性的問題在於它可以應用於FK屬性,在這種情況下,它用於指定導航屬性名稱。 或者可以將其應用於導航屬性,在這種情況下,它應包含FK 屬性名稱(或復合FK屬性名稱的逗號分隔列表)。

要知道的重要一點是,它不能用於指定FK 名稱。 列名由Column屬性控制,因此僅當您具有顯式FK屬性(您沒有)時才可以使用它。

Fluent API沒有這樣的限制。 你要么使用HasForeignKey當你有明確的FK財產,或MapMapKey ,當你不知道。

在您的情況下,為了將您不尋常的“ Project”指定為FK列名,您可以使用以下流暢的配置(並且不要忘記從ProjectSteps刪除無效的ForeignKey屬性):

modelBuilder.Entity<ProjectStep>()
    .HasRequired(p => p.Project)
    .WithMany(s => s.ProjectSteps)
    .Map(m => m.MapKey("Project"));

為了能夠向數據庫添加新的“ Project”,您需要從“ Project”類的“ ProjectSteps”屬性中刪除外鍵注釋。 “外鍵”注釋只能應用於不是集合類型的屬性。

[DataContract(Namespace = "Shared")]
public class Project
{

    public Project()
    {
        this.EmployeesWorkingOnProject = new List<Employee>();
        this.ProjectSteps = new List<ProjectStep>();
    }

    [DataMember]
    [Key]
    public int ID { get; set; }

    [DataMember]
    public String Titel { get; set; }

    [DataMember]
    public DateTime StartDatum { get; set; }

    [DataMember]
    public DateTime EndDatum { get; set; }

    [DataMember]
    public String Beschreibung { get; set; }

    [DataMember]
    [Column("Projektleiter")]
    public Employee Projektleiter { get; set; }

    [DataMember]
    public bool Status { get; set; }

    [DataMember]
    public virtual ICollection<Employee> EmployeesWorkingOnProject { get; set; }

    [DataMember]
    public virtual ICollection<ProjectStep> ProjectSteps { get; set; }
}

另外回答您的問題:

所以我的問題是,是否應該將DataAnnotations與Fluent API混合使用,有人可以幫助我正確實現此映射嗎?

混合不是一個好習慣。 Imho Fluent API總是更好,因為它提供了更多的映射選項。

有關EF映射的更多信息,請查看THIS

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM