C#MVC ViewModel返回Null - Postback

时间:2017-11-02 16:05:45

标签: c# sql asp.net-mvc linq

我认为我有多个奖项,每个奖项中都有相应的资格列表。我创建了一个ViewModel来显示每个奖项,只需点击一个按钮,就会出现一个模态,其中包含相关的资格,可以由用户标记为已完成/更新。但是在Post的数据上,它没有绑定到我的控制器方法中的ViewModel。数据显示在我看来如预期,每个奖项仅显示其相关资格。我已经使用FormCollection来访问某些字段以进行测试,并且正在回发数据。任何帮助都会很棒!

视图模型

public class CandidateExtended
{
    public CandidateExtended()
    {
        this.Qualifications = new List<Qualification_Extended>();
    }

    public int AwardID { get; set; }
    public int FrameworkID { get; set; }
    public string ULN { get; set; }
    public string Forename { get; set; }
    public string Surname { get; set; }
    public string TitleShort { get; set; }
    public string TitleFull { get; set; }
    public DateTime DOB { get; set; }
    public string Award { get; set; }
    public int AwardLevel { get; set; }
    public string Status { get; set; }
    public string Completion { get; set; }
    public string SelectedRoute { get; set; }

    public List<Qualification_Extended> Qualifications { get; set; }

    public void addQualification(Qualification_Extended qualification)
    {
        Qualifications.Add(qualification);
    }
}

控制器

  [HttpGet]
    public ActionResult Index()
    {

        var awardDetails = (from award in db.award
                            join candidate in db.candidate
                            on award.ULN equals candidate.ULN
                            join framework in db.framework
                            on award.QAN equals framework.QAN
                            where award.OrganisationIdentityID == organisationID
                            select new AwardDetails_Extended
                            {
                                AwardID = award.AwardID,
                                ULN = award.ULN,
                                AwardStatus = award.AwardStatus,
                                Forename = candidate.Forename,
                                Surname = candidate.Surname,
                                DOB = candidate.DOB,
                                FrameworkID = framework.FrameworkID,
                                TitleFull = framework.TitleFull,
                                TitleShort = framework.TitleShort, 
                                AwardLevel = framework.AwardLevel, 
                                Award = framework.Award,
                                Completion = framework.Completion
                            }).ToList();


        var qualificationDetails = (from candidateQualification in db.candidateQualification
                                    join qualification in db.qualification
                                    on candidateQualification.QualificationID equals qualification.QualificationID
                                    select new Qualification_Extended
                                    {
                                        ID = candidateQualification.ID,
                                        QualificationID = candidateQualification.QualificationID,
                                        ULN = candidateQualification.ULN,
                                        FrameworkID = candidateQualification.FrameworkID,
                                        Achieved = candidateQualification.Achieved,
                                        DateAchieved = candidateQualification.DateAchieved
                                    }).ToList();


        List<CandidateExtended> candidateVM = new List<CandidateExtended>();

        foreach (var item in awardDetails)
        {
            CandidateExtended vm = new CandidateExtended();
            vm.AwardID = item.AwardID;
            vm.FrameworkID = item.FrameworkID;
            vm.ULN = item.ULN;
            vm.Forename = item.Forename;
            vm.Surname = item.Surname;
            vm.DOB = item.DOB;
            vm.TitleShort = item.TitleShort;
            vm.TitleFull = item.TitleFull;
            vm.Award = item.Award;
            vm.AwardLevel = item.AwardLevel;
            vm.Status = item.AwardStatus;
            vm.Completion = item.Completion;
            vm.SelectedRoute = item.SelectedRoute;

            foreach (var qualification in qualificationDetails)
            {
                if (qualification.ULN == item.ULN && qualification.FrameworkID == item.FrameworkID)
                {
                    vm.addQualification(qualification);
                }
            }

            candidateVM.Add(vm);
        }

        return View(candidateVM);      
    }

查看

@using (Html.BeginForm("UpdateAward", "Organisation", FormMethod.Post))
{
@Html.HiddenFor(a => award.AwardID) 

<div class="row">
        <div class="col-md-12">
        <div class="row org-row-main">
            <div class="col-md-7"><h4 class="org-type">Qualification</h4></div>
            <div class="col-md-2"><h5 class="org-completed">Completed</h5></div>
            <div class="col-md-3"><h5 class="org-date">Date</h5></div>
        </div>

        <hr class="org-hr"/>

            @for (int i = 0; i < award.Qualifications.Count(); i++)
            {

                var qualification = award.Qualifications[i];

            <div class="row org-row">
                <div class="col-md-7">
                    @Html.HiddenFor(a => award.Qualifications[i].ID)
                </div>
                <div class="col-md-2">
                        @Html.CheckBoxFor(a => award.Qualifications[i].Achieved)
                </div>
                <div class="col-md-3">@Html.TextBoxFor(a => award.Qualifications[i].DateAchieved, "{0:dd/MM/yyyy}")
                </div>
            </div>
            }
        </div>
</div> 

<button type="submit" class="btn admin-button" style="margin-top: 0;">Save</button>

}

UpdateAward

[HttpPost]
    public ActionResult UpdateAward(CandidateExtended model, FormCollection collection)
    {

        return RedirectToAction("Index", "Login");

    }

2 个答案:

答案 0 :(得分:1)

首先(你可能已经有了这个,但是我们无法看到它):你的View应该以包含@model List<CandidateExtended>的行开头(在内部类型前面加上正确的命名空间)。

然后在视图中,您应该使用Model,这是@model关键字后指定的确切类型的定义。

我们发现您使用的是award,我们无法看到它的来源,可能是使用var award = Model[j]foreach (var award in Model)等设置。 从不在视图中使用此类临时或辅助变量(以提高效率)来呈现表单; View需要所有对象的完全限定名称,例如Model.Item [x] .SubItem [y] ,以生成可用于模型绑定的Form 字段名称

E.g。这:@Html.HiddenFor(a => award.Qualifications[i].ID)
应该是:@Html.HiddenFor(a => Model[j].Qualifications[i].ID)

在所有其他地方做同样的改变。

然后按照已经建议的那样,使用Controller Post方法中的List<...>

最后还请删除FormCollection,如果您按照此处的说明设置了所有内容,则不需要它。体面的MVC代码从不永远使用FormCollection

答案 1 :(得分:0)

尝试在单独的按钮而不是BeginForm上调用posted方法,它应该可以工作。