EF,每个层次结构表,抽象类中的属性

时间:2012-04-12 11:50:51

标签: c# entity-framework data-annotations table-per-hierarchy

我想知道我是否可以在基类(抽象)中使用虚拟属性定义来创建具有其他具体类型的链接。

例如:

public abstract class AbstractService
{
   public int Id {get;set;}

   public int? SiteId {get;set;}
   public virtual Site Site {get;set;}
}

public class StudyTeamService : AbstractService
{
   public int? RoleId {get;set;}
   public virtual Role Role {get;set;}
}


public abstract class AbstractSite
{
   public int Id {get;set;}

   public string Name {get;set;}
}

public class Site : AbstractSite
{
   public virtual ICollection<StudyTeamService> StudyTeamServices {get;set;}
}

我认为我必须在ICollection上添加注释,以便它知道如何正确映射,但我找不到正确的注释。

你们有什么想法吗?

似乎如果我在ICollection上设置[InverseProperty(“Site”)],它会因为错误而崩溃,告知组件中没有定义关系......

1 个答案:

答案 0 :(得分:1)

我认为您的代码存在问题

public class Site : AbstractSite
{
   public virtual ICollection<StudyTeamService> StudyTeamServices {get;set;}
}

因为关系介于Site and AbstractService , not with StudyTeamService`之间。

以下代码适用于我:

using System;
using System.Collections.Generic;
using System.ComponentModel.DataAnnotations;
using System.Data.Entity;
using System.Data.Entity.ModelConfiguration;

namespace StackOverflow
{

    public abstract class AbstractService
    {
        public int Id { get; set; }
        public virtual Site Site { get; set; }

        public int SiteId { get; set; }
    }

    [Table("StudyTeamServices")]
    public class StudyTeamService : AbstractService
    {
        public virtual Role Role { get; set; }
    }

    public class Role
    {
        public int Id { get; set; }
        public string Name { get; set; }
    }


    public abstract class AbstractSite
    {
        public int Id { get; set; }
        public string Name { get; set; }
    }

    public class Site : AbstractSite
    {
        public virtual ICollection<AbstractService> StudyTeamServices { get; set; }
    }

    public class Context : DbContext
    {
        static Context()
        {
            Database.SetInitializer<Context>(null);
        }

        public DbSet<AbstractService> AbstractServices { get; set; }
        public DbSet<StudyTeamService> StudyTeamServices { get; set; }
        public DbSet<Site> Sites { get; set; }

        protected override void OnModelCreating(DbModelBuilder modelBuilder)
        {
            //Not EdmMetadata Table on DB
            //modelBuilder.Conventions.Remove<IncludeMetadataConvention>();

            modelBuilder.Configurations.Add(new AbstractServiceMap());
        }

    }

    public class AbstractServiceMap : EntityTypeConfiguration<AbstractService>
    {
        public AbstractServiceMap()
        {
            HasRequired(a => a.Site).WithMany(s => s.StudyTeamServices).HasForeignKey(a => a.SiteId);
        }
    }

    class Program
    {
        static void Main(string[] args)
        {
            var context = new Context();
            context.Database.Delete();
            context.Database.Create();

            var studyTeamService = new StudyTeamService();
            studyTeamService.Role = new Role { Name = "role1" };
            studyTeamService.Site = new Site { Name = "Site1" };

            context.StudyTeamServices.Add(studyTeamService);
            context.SaveChanges();
            Console.WriteLine("Done");
            Console.ReadLine();
        }
    }
}