我有3个实体:问题
public enum QuestionType
{
Scenario,
Step
}
public class Question
{
public int Id { get; set; }
public int CategoryId { get; set; }
[Required] [MaxLength(255)] public string Text { get; set; }
[MaxLength(255)] public string FrameText { get; set; }
public int Order { get; set; }
public QuestionType Type { get; set; }
public DefaultAnswer DefaultAnswer { get; set; }
public IList<Answer> Answers { get; set; }
}
答案
public class Answer
{
public int Id { get; set; }
public int QuestionId { get; set; }
[Required] [MaxLength(255)] public string Text { get; set; }
public int Order { get; set; }
public Scenario Scenario { get; set; }
public IList<Formula> Formulas { get; set; }
public IList<Image> Images { get; set; }
}
最后, DefaultAnswer :
public class DefaultAnswer
{
public int QuestionId { get; set; }
public int AnswerId { get; set; }
public Answer Answer { get; set; }
public Question Question { get; set; }
}
问题和答案之间的关系是显而易见的。我想为问题设置 DefaultAnswer ,所以我已将导航属性DefaultAnswer
添加到 Question 模型中。
这是可选的,因为它可以为空。
所以,我试图建立这样的关系:
modelBuilder.Entity<DefaultAnswer>().HasKey(m => new { m.QuestionId, m.AnswerId });
modelBuilder.Entity<Question>().HasOptional(m => m.DefaultAnswer).WithRequired(m => m.Question);
modelBuilder.Entity<DefaultAnswer>().HasRequired(m => m.Answer).WithMany().HasForeignKey(m => m.AnswerId);
但这不起作用,它在 DefaultAnswers 表中创建了另一个名为Question_Id
的字段。
这是EF生成的:
public override void Up()
{
CreateTable(
"dbo.DefaultAnswers",
c => new
{
QuestionId = c.Int(nullable: false),
AnswerId = c.Int(nullable: false),
Question_Id = c.Int(nullable: false),
})
.PrimaryKey(t => new { t.QuestionId, t.AnswerId })
.ForeignKey("dbo.Answers", t => t.AnswerId, cascadeDelete: true)
.ForeignKey("dbo.Questions", t => t.Question_Id)
.Index(t => t.AnswerId)
.Index(t => t.Question_Id);
}
这不是我想要的。 我实际上想要这个:
public override void Up()
{
CreateTable(
"dbo.DefaultAnswers",
c => new
{
QuestionId = c.Int(nullable: false),
AnswerId = c.Int(nullable: false),
})
.PrimaryKey(t => new { t.QuestionId, t.AnswerId })
.ForeignKey("dbo.Answers", t => t.AnswerId, cascadeDelete: true)
.ForeignKey("dbo.Questions", t => t.QuestionId)
.Index(t => t.AnswerId)
.Index(t => t.QuestionId);
}
有人知道我如何创建这种关系,同时又将导航属性保留在问题中吗?
答案 0 :(得分:0)
首先,建议仅将答案标记为“默认”的评论听起来不错,但试图帮助解决实际问题。...
确定,我认为所做的编辑会为您提供所需的内容。...
所以,我在这里使用的模型:
public enum QuestionType
{
Scenario,
Step
}
public class Question
{
public int Id { get; set; }
public int CategoryId { get; set; }
[Required] [MaxLength(255)]
public string Text { get; set; }
[MaxLength(255)]
public string FrameText { get; set; }
public int Order { get; set; }
public QuestionType Type { get; set; }
public DefaultAnswer DefaultAnswer { get; set; }
public IList<Answer> Answers { get; set; }
}
public class Answer
{
public int Id { get; set; }
public int QuestionId { get; set; }
[Required]
[MaxLength(255)]
public string Text { get; set; }
public int Order { get; set; }
public Scenario Scenario { get; set; }
public Question Question { get; set; }
//commented these out for the sake of this
//example
/*public IList<Formula> Formulas { get; set; }
public IList<Image> Images { get; set; }*/
}
public class DefaultAnswer
{
public int QuestionId { get; set; }
public int AnswerId { get; set; }
public Answer Answer { get; set; }
public Question Question { get; set; }
}
因此定义的关系:
//don't need a compound key for answers...
//easier to just let each answer be entirely unique.
modelBuilder.Entity<Answer>().HasKey(m => m.Id );
modelBuilder.Entity<Answer>().HasRequired(m => m.Question)
.WithMany(q => q.Answers).HasForeignKey(m => m.QuestionId);
modelBuilder.Entity<Question>()
.HasOptional(m => m.DefaultAnswer)
.WithOptionalDependent(m => m.Question);
//default answer is basically a mapping table between questions and answers.
//so it has a compound key. In fact the table should consist of ONLY these two key
//fields...
modelBuilder.Entity<DefaultAnswer>()
.HasKey(m => new { m.AnswerId, m.QuestionId });
这对我来说是这样的:
CreateTable(
"dbo.DefaultAnswers",
c => new
{
AnswerId = c.Int(nullable: false),
QuestionId = c.Int(nullable: false),
})
.PrimaryKey(t => new { t.AnswerId, t.QuestionId })
.ForeignKey("dbo.Answers", t => t.AnswerId, cascadeDelete: true)
.Index(t => t.AnswerId);
我唯一不了解的是如何设置级联删除行为...有点担心删除'DefaultAnswer'记录会删除答案-为时已晚,我的大脑无法正常工作恐怕这个!
答案 1 :(得分:0)
我不确定引入DefaultAnswer实体的目的是什么。但是没有这种关系就可以建模。 EG:
public enum QuestionType
{
Scenario,
Step
}
public class Question
{
public int Id { get; set; }
public int CategoryId { get; set; }
[Required] [MaxLength(255)] public string Text { get; set; }
[MaxLength(255)] public string FrameText { get; set; }
public int Order { get; set; }
public QuestionType Type { get; set; }
public int? DefaultAnswerId { get; set; }
[ForeignKey("Id,DefaultAnswerId")]
public Answer DefaultAnswer { get; set; }
public IList<Answer> Answers { get; set; }
}
public class Answer
{
public int Id { get; set; }
public int QuestionId { get; set; }
[Required] [MaxLength(255)] public string Text { get; set; }
public int Order { get; set; }
public virtual Question Question { get; set; }
//public Scenario Scenario { get; set; }
//public IList<Formula> Formulas { get; set; }
//public IList<Image> Images { get; set; }
}
class Db: DbContext
{
public DbSet<Question> Question { get; set; }
public DbSet<Answer> Answer { get; set; }
protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
base.OnModelCreating(modelBuilder);
modelBuilder.Entity<Answer>().HasKey(m => new { m.QuestionId, m.Id });
modelBuilder.Entity<Answer>().HasRequired(m => m.Question).WithMany(q => q.Answers).HasForeignKey( m => m.QuestionId);
modelBuilder.Entity<Question>().HasOptional(m => m.DefaultAnswer);
}
}