【问题标题】:complex type model wont pass list propery复杂类型模型不会传递列表属性
【发布时间】:2018-02-02 17:58:49
【问题描述】:

大家好,我的 mvc 应用程序有问题。它是一个简单的测验应用程序,我一直在为问题模型创建创建视图。

我有带有适当视图模型的问题和选项模型(在我的情况下,它们是 QustionDTO 和 OptionDTO),我想让 cshtml 为带有选项列表的问题创建视图。like this 但是当我提交表单时,我的列表选项为空。 这是我的问题和选项模型

 public class Question
 {
     [Key]
     [DatabaseGenerated(DatabaseGeneratedOption.Identity)]
     public int Id { get; set; }
     [Required]
     public string QuestionText { get; set; }
     public virtual ICollection<Option> Options { get; set; }
 }

public class Option
{
     [Key]
     [DatabaseGenerated(DatabaseGeneratedOption.Identity)]
     public int Id { get; set; }
     [Required]
     [Display(Name ="Answer text")]
     public string OptionText { get; set; }
     [Required]
     public bool IsCorrect { get; set; }
}

这是我的 DTO 模型

public class QuestionDTO
{
    public int Id { get; set; }
    public string QuestionText { get; set; }
    public List<OptionDTO> Options { get; set; }
}
public class OptionDTO
{
    public int Id { get; set; }
    public string OptionText { get; set; }
    public bool IsCorrect { get; set; }
}

这是我的视图,编辑器模板位于“~/views/shared/editortemplate/OptionDTO.cshtml”

@model Quiz.BusinessEntites.QuestionDTO

@using (Html.BeginForm())
{
    @Html.AntiForgeryToken()

    <div class="form-horizontal">
        <h4>QuestionDTO</h4>
        <hr />
        @Html.ValidationSummary(true, "", new { @class = "text-danger" })
        <div class="form-group">
            @Html.LabelFor(model => model.QuestionText, htmlAttributes: new { @class = "control-label col-md-2" })
            <div class="col-md-10">
                @Html.EditorFor(model => model.QuestionText, new { htmlAttributes = new { @class = "form-control" } })
                @Html.ValidationMessageFor(model => model.QuestionText, "", new { @class = "text-danger" })
            </div>
        </div>
        <table class="table" style="width:50%">
            @for (int i = 0; i < 3; i++)
            {
                @Html.EditorFor(model=>model.Options[i])
            }
        </table>
        <div class="form-group">
            <div class="col-md-offset-2 col-md-10">
                <input type="submit" value="Create" class="btn btn-default" />
            </div>
        </div>
    </div>
}

<div>
    @Html.ActionLink("Back to List", "Index")
</div>

这是 OptionDTO 编辑器模板

@using Quiz.BusinessEntites
@model Quiz.BusinessEntites.OptionDTO
<tr>
    <th class="col-md-2">
        @Html.DisplayNameFor(m => m.OptionText)
    </th>
    <th class="col-md-2">
        @Html.DisplayNameFor(m => m.IsCorrect)
    </th>
</tr>
<tr>
    <td class="col-md-2">
        @Html.EditorFor(m => m.OptionText)
    </td>
    <td class="col-md-2">
        @Html.EditorFor(m => m.IsCorrect)

    </td>
</tr>

从上图中你可以看到选项列表为空。如果您有任何建议,我们将不胜感激。

【问题讨论】:

  • 附带说明,它只是 @Html.EditorFor(m =&gt;m.Options) 而没有 for 循环(EditorFor() 方法接受 IEnumerable 并为集合中的每个项目生成正确的 html
  • 但如果我想为模板制作多个编辑器,我需要使用 for 循环吗?就像我的情况一样,或者我错过了什么。只是让你知道这是有效的。
  • 不,你没有。再次阅读评论!

标签: asp.net-mvc razor asp.net-mvc-5 mvc-editor-templates


【解决方案1】:

在您的 http post 操作方法中,带有 Include 列表的 Bind 属性告诉模型绑定器从已发布的表单数据中仅绑定 QuestionDto 对象的“Id”、“QuestionText”和“IsCorrect”属性.所以模型绑定器不会绑定Options属性值。

从您的 Http 发布操作方法中删除 Bind 属性。 如果您的视图模型特定于您的视图,则无需使用 Bind 属性,这意味着您只有视图所需的属性(在您的情况下看起来像这样)

public ActionResult Create(QuestionDTO model)
{
  // to do :return something
}

如果您想使用非特定视图的视图模型,但仍想使用Bind 属性仅指定属性的子集,请仅包含这些属性。在您的情况下,您的代码将类似于

public ActionResult Create([Bind(Include="Id,QuestionText",Options"] QuestionDTO model)
{
  // to do :return something
}

您还应该编辑器模板视图应该在一个名为 EditorTemplates 的目录中,而不是 EditorTemplate

【讨论】:

    猜你喜欢
    • 2016-10-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-04-29
    • 2017-03-26
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多