c# - 错误回发 ASP.NET MVC 的模型列表

标签 c# asp.net-mvc asp.net-mvc-4

所以我有一个 View 模型:

public class ClientViewModel
{
    public int ClientID { get; set; }
    [Required]
    [DisplayName("Client Name")]
    public string Name { get; set; }
    [Required]
    [DisplayName("Client Surname")]
    public string Surname { get; set; }
}

以及我使用此 View 模型的 View (用于搜索客户列表的按钮、用于按姓名对客户进行排序的按钮和用于按姓氏对客户进行排序的按钮):

@model IList<ClientViewModel>

@using (Html.BeginForm("Index", "Client", FormMethod.Post))
{
@Html.AntiForgeryToken()

<div class="form-horizontal">

<div class="form-group">
    <label class="control-label col-md-2">Enter client info:</label>
    <div class="col-md-10">
        <input type="text" id="clientInfo" name="clientInfo" value="@Session["input"]" />
    </div>
</div>

<div class="form-group">
    <div class="col-md-offset-2 col-md-10">
        <input type="submit" name="command" value="Search Client" class="btn btn-default" />
    </div>
</div>

<div class="form-group">
    <div class="col-md-offset-2 col-md-2">
        <input type="submit" name="command" value="Sort by client name" class="btn btn-default" />
    </div>
    <div class="col-md-2">
        <input type="submit" name="command" value="Sort by client surname" class="btn btn-default" />
    </div>
</div>

</div>

<table class="table">
<tr>
    <th>
        @Html.DisplayNameFor(model => model[0].Name)
    </th>
    <th>
        @Html.DisplayNameFor(model => model[0].Surname)
    </th>
</tr>

@for (var i = 0; i < Model.Count; i++)
{
    @Html.HiddenFor(x => x[i].ClientID)
    <tr>
        <td>
            @Html.HiddenFor(x => x[i].Name)
            @Html.DisplayFor(x => x[i].Name)
        </td>
        <td>
            @Html.HiddenFor(x => x[i].Surname)
            @Html.DisplayFor(x => x[i].Surname)
        </td>
        <td>
            @Html.ActionLink("Delete Client", "DeleteClient", new { id = Model[i].ClientID }, new { @class = "btn btn-danger" })
        </td>
        <td>
            @Html.ActionLink("Edit Client", "EditClient", new { id = Model[i].ClientID }, new { @class = "btn btn-default" })
        </td>
    </tr>
}

</table>
}

假设初始客户是:

Name       Surname
Adam       Gnb
Brandon    Cook
Kevin      Ginger
Patrick    Star

现在,当我在 clientInfo 输入文本框中输入“g”并单击搜索按钮时,它会使用我输入的关键字正确显示客户端。输出是:

Name      Surname
Adam      Gnb
Kevin     Ginger

现在,当我单击“按客户姓氏排序”时。期望的输出是:

Name      Surname
Kevin     Ginger
Adam      Gnb

但出于某种原因,post 方法中的客户参数持有客户“Adam Gnb”和“Brandon Cook”。这就是为什么输出是:

Name      Surname
Brandon   Cook
Adam      Gnb

似乎从 View 中返回 IList 并没有保存当前正在显示的客户端。真的不知道如何解决这个问题。

编辑 1:

过滤方法:

public IEnumerable<ClientDTO> GetByClientInfo(string info)
    {
        if (info.Trim() == "")
            throw new ValidationException("Set the input textbox.", "");
        var mapper = new MapperConfiguration(cfg => cfg.CreateMap<Client, ClientDTO>()).CreateMapper();
        return mapper.Map<IEnumerable<Client>, List<ClientDTO>>(Database.Clients.Find(x => x.Name.ToLower().Contains(info.ToLower()) || x.Surname.ToLower().Contains(info.ToLower())));
    }

排序方法:

public IEnumerable<ClientDTO> SortBySurname(IEnumerable<ClientDTO> clients)
    {
        if (clients == null)
            throw new ValidationException("The client list is empty", "");

        var sortedClients = from client in clients
                            orderby client.Surname
                            select client;

        return sortedClients;
    }

发布方式:

[HttpPost]
    public ActionResult Index(IList<ClientViewModel> clients, string command, string clientInfo)
    {
        if(command.Equals("Sort by client name"))
        {
            var mapper = new MapperConfiguration(cfg => cfg.CreateMap<ClientViewModel, ClientDTO>()).CreateMapper();
            var mapperReverse = new MapperConfiguration(cfg => cfg.CreateMap<ClientDTO, ClientViewModel>()).CreateMapper();

            var sortedClients = clientService.SortByName(mapper.Map<IList<ClientViewModel>, List<ClientDTO>>(clients));
            var afterMap = mapperReverse.Map<IEnumerable<ClientDTO>, IList<ClientViewModel>>(sortedClients);
            return View("Index", afterMap);
        }
        else if(command.Equals("Sort by client surname"))
        {
            var mapper = new MapperConfiguration(cfg => cfg.CreateMap<ClientViewModel, ClientDTO>()).CreateMapper();
            var mapperReverse = new MapperConfiguration(cfg => cfg.CreateMap<ClientDTO, ClientViewModel>()).CreateMapper();

            var sortedClients = clientService.SortBySurname(mapper.Map<IList<ClientViewModel>, List<ClientDTO>>(clients));
            var afterMap = mapperReverse.Map<IEnumerable<ClientDTO>, IList<ClientViewModel>>(sortedClients);
            return View("Index", afterMap);
        }
        else
        {
            Session["input"] = clientInfo;
            IEnumerable<ClientDTO> clientDtos;
            try
            {
                clientDtos = clientService.GetByClientInfo(clientInfo);
                var mapper = new MapperConfiguration(cfg => cfg.CreateMap<ClientDTO, ClientViewModel>()).CreateMapper();
                var resultClients = mapper.Map<IEnumerable<ClientDTO>, IList<ClientViewModel>>(clientDtos);
                return View("Index", resultClients);
            }
            catch (ValidationException ex)
            {
                ViewBag.Error = ex.Message;
                if (clients == null)
                {
                    return View(new List<ClientViewModel>());
                }
                return View("Index", clients);
            }
        }
    }

最佳答案

看看这个link

尝试将隐藏输入更改为不使用 Html 助手。导致它将发布值绑定(bind)回输入控件。而是使用像下面这样的纯 html 元素

@for (var i = 0; i < Model.Count; i++)
{
    <input type="hidden" name="[@(i)].ClientId" value="@(Model[i].ClientId)" />
    <tr>
        <td>
            <input type="hidden" name="[@(i)].Name" value="@(Model[i].Name)" />
            @Html.DisplayFor(x => x[i].Name)
         </td>
         <td>
             <input type="hidden" name="[@(i)].Surname" value="@(Model[i].Surname)" />
             @Html.DisplayFor(x => x[i].Surname)
         </td>
         <td>
             @Html.ActionLink("Delete Client", "DeleteClient", new { id = Model[i].ClientID }, new { @class = "btn btn-danger" })
          </td>
          <td>
              @Html.ActionLink("Edit Client", "EditClient", new { id = Model[i].ClientID }, new { @class = "btn btn-default" })
          </td>
    </tr>
}

关于c# - 错误回发 ASP.NET MVC 的模型列表,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/50647837/

相关文章:

c# - 错误 LNK2028 : Thrown when instantiating an native C++ class within C++/CLI

jquery - 在 Asp.Net Mvc 中使用 Ajax 刷新表列表

asp.net-mvc - 在 asp.net mvc 中使用大量 View 模型是不好的做法吗

asp.net-mvc - 如何自定义简单的成员资格提供程序以使用我自己的数据库 ASP.NET mvc 4

javascript - 显示/隐藏 div (ASP.NET MVC)

c# - 如何从 C# 使用 C++ dll

c# - Model Class DisplayFormat() 如何本地化 NullDisplayText?

javascript - MVC JavaScript 相对路径

c# - ASP.NET,MVC4,授权: users should see only own content

C# 关闭事件处理程序不工作