如何在一对多关系中处理可选的外键约束错误

时间:2017-08-27 04:58:03

标签: sql-server asp.net-mvc entity-framework asp.net-mvc-5 ef-fluent-api

我是ASP.Net MVC 5的初学者,目前仍处于Fluent API问题。我有一个推荐类,可以与Coverletter类有一对多的关系。有时Rererral行可能不存在封面(我认为0 .. *)。

Fluent API:

//// one cover letter can be there in many referral request
dBModelBuilder.Entity<CoverLetter>()
    .HasMany(u => u.Referrals)
    .WithOptional(u => u.CoverLetter)
    .HasForeignKey(u => u.CoverLetterId);

推介模式:

public class Referral
{
    [Key]
    public int ReferralId { get; set; }
    // I added "?" to make FK Optional
    public int? CoverLetterId { get; set; }
    public virtual CoverLetter CoverLetter { get; set; }
}

ReferralViewModel:

public class ReferralViewModel
{
    public int ReferralViewModelId { get; set; }
    [Display(Name = "Cover Letter")]
    public int CoverLetterId { get; set; }
    public IEnumerable<CoverLetter> CoverLetters { get; set; }
}

控制器操作:

[HttpPost]
public ActionResult Create(ReferralViewModel viewModel)
{
    var candidateId = User.Identity.GetUserId();
    var referral = new Referral
    {
        CoverLetterId = viewModel.CoverLetterId
    };
   // I get exception here
    _context.Referrals.Add(referral);
    _context.SaveChanges();
    return RedirectToAction("ReferralCenter");
}

问题 当我没有从UI中选择任何封面信息时,CoverLetter ID从我的viewModel变为0。而且我认为因为在DB中没有ID为0的封面,我得到DB Contraint异常。

例外:

  

{&#34; INSERT语句与FOREIGN KEY约束冲突   \&#34; FK_dbo.Referrals_dbo.CoverLetters_CoverLetterId \&#34 ;.冲突   发生在数据库\&#34; aspnet-Bridge-20170730012232 \&#34;,表中   \&#34; dbo.CoverLetters \&#34;,列&#39; CoverLetterId&#39;。\ r \ n声明包含   已被终止。&#34;}

要使FK可选,我执行了两个步骤

一个。添加&#34;?&#34;在模型属性

湾添加了&#34; HasOptional&#34;在Fluent API中。

修正:

当我没有选择任何CoverlLetter然后在表单提交时我希望CoverLetter ID为 NULL 而不是Zero。

1 个答案:

答案 0 :(得分:2)

更改控制器中的封面信件ID分配

CoverLetterId = viewModel.CoverLetterId == 0 ? null : viewModel.CoverLetterId;

OR

你也可以

public int CoverLetterId { get; set; }

改为 public int? CoverLetterId { get; set; }中的ReferralViewModel

然后,在控制器中,您将不得不使用额外的检查

CoverLetterId = viewModel.CoverLetterId.HasValue ? ((viewModel.CoverLetterId.Value == 0) ? null : viewModel.CoverLetterId.Value) : null

如果你知道你要在HttpPost的前端传递0,并且不让viewModel.CoverLetterId采用它的默认值,你可以使用。

CoverLetterId = (viewModel.CoverLetterId.Value == 0) ? null : viewModel.CoverLetterId.Value