【问题标题】:Why does my asp.net model binding not work?为什么我的 asp.net 模型绑定不起作用?
【发布时间】:2021-11-13 17:34:53
【问题描述】:

我的控制器没有从我的视图中的表单接收数据。
我之前在其他模型上使用过基本完全相同的代码,并且它工作得非常好。
有人可以解释为什么这不起作用吗?

控制器:

[HttpPost]
[ValidateAntiForgeryToken]
public IActionResult ChangeWiFiNetwork(Models.Settings.NetworkSettings model)
{
    Logger.LogInformation("SSID:", model.SSID);
    Logger.LogInformation("PASS:", model.Password);
    return RedirectToAction("Index");
}

查看:

@model Webserver.Models.Settings.Settings

<h1>Settings</h1>

<div class="row">
    <div class="col-6">
        <form asp-action="ChangeWiFiNetwork">
            <div class="form-group">
                <label asp-for="Network.SSID" class="control-label"></label>
                <input asp-for="Network.SSID" class="form-control" />
                <span asp-validation-for="Network.SSID" class="text-danger"></span>
            </div>
            <div class="form-group">
                <label asp-for="Network.Password" class="control-label"></label>
                <input asp-for="Network.Password" class="form-control" />
                <span asp-validation-for="Network.Password" class="text-danger"></span>
            </div>
            <div class="form-group">
                <input type="submit" value="Save" class="btn btn-primary" />
            </div>
        </form>
    </div>
</div>

型号:

namespace Webserver.Models.Settings
{
    public class Settings
    {
        public NetworkSettings Network { get; set; }
    }
}

namespace Webserver.Models.Settings
{
    public class NetworkSettings
    {
        public string SSID { get; set; }
        public string Password { get; set; }
    }
}

输出

SSID: 
PASS: 

在调试模式下都显示为 null。

Firefox Network-Analysis 显示 Network.SSID 和 Network.Password 正在 Form-Data 中发送。

我正在使用 .Net 5

谢谢

【问题讨论】:

  • 提交是否命中控制器动作?你能看到 Logger.LogInformation("SSID:", model.SSID);记录?什么是价值模型.SSID?
  • 是的。我在控制台中得到输出“SSID:”。并且带有断点模型。SSID 为空。

标签: asp.net asp.net-mvc asp.net-core .net-core


【解决方案1】:

现在我将手动从 Request.Form 中提取值。

这真是糟糕的代码,但我就是不明白为什么模型绑定不起作用。

[HttpPost]
[ValidateAntiForgeryToken]
public IActionResult ChangeWiFiNetwork(Models.Settings.NetworkSettings throwaway)
{
    if (!(Request.Form.ContainsKey("NetworkSettings.SSID") && Request.Form.ContainsKey("NetworkSettings.Password")))
    {
        throw new Exception("SSID or Password missing!");
    }

    Models.Settings.NetworkSettings settings = new()
    {
        SSID = Request.Form["NetworkSettings.SSID"],
        Password = Request.Form["NetworkSettings.Password"]
    };

    Logger.LogInformation("SSID: " + settings.SSID);
    Logger.LogInformation("PASS: " + settings.Password);

    return RedirectToAction("Index");
}

【讨论】:

    【解决方案2】:

    修复视图,因为您使用 AntiForgeryToken 将其添加到表单

     <form asp-action="ChangeWiFiNetwork">
     @Html.AntiForgeryToken()
    

    动作输入参数与模型相同

    public IActionResult ChangeWiFiNetwork(Models.Settings.Settings model)
    

    【讨论】:

    • 那还是不行。从控制器中删除 [ValidateAntiForgeryToken] 也无济于事。
    【解决方案3】:

    您将模型设置为@model Webserver.Models.Settings.Settings,但在您的操作中,您将输入参数设置为Models.Settings.NetworkSettings model

    所以你应该像这样改变你的行为:

    public IActionResult ChangeWiFiNetwork(Models.Settings.Settings model)
    

    或者改变视图中的绑定模型:

    @model Webserver.Models.Settings.NetworkSettings
    

    无论如何,您需要在视图和控制器操作中保持模型相同。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2020-01-13
      • 1970-01-01
      • 2011-01-16
      • 2018-06-18
      • 1970-01-01
      相关资源
      最近更新 更多