Asp.net mvc 5 模型绑定不适用于.net Core 2.1中的属性路由

Asp.net mvc 5 模型绑定不适用于.net Core 2.1中的属性路由,asp.net-mvc-5,asp.net-core-mvc,attributerouting,asp.net-core-mvc-2.0,asp.net-core-mvc-2.1,Asp.net Mvc 5,Asp.net Core Mvc,Attributerouting,Asp.net Core Mvc 2.0,Asp.net Core Mvc 2.1,我可以让模型绑定在没有属性路由的情况下正常工作-例如: /// <summary> /// Collect user details /// </summary> public IActionResult RegisterDetails(Guid CustomerId) { var Details = new Details() { CustomerID = CustomerId }; return View(Detail

我可以让模型绑定在没有属性路由的情况下正常工作-例如:

/// <summary>
/// Collect user details
/// </summary>
public IActionResult RegisterDetails(Guid CustomerId)
{
    var Details = new Details()
    {
        CustomerID = CustomerId
    };

    return View(Details);
}

/// <summary>
/// Save user details in Db if valid
/// </summary>
[HttpPost]
public IActionResult RegisterDetails(Details Details)
{
    if (ModelState.IsValid)
    {
        // Do stuff
    }

    // Error, return ViewModel to view
    return View(RegisterDetails);
}
//
///收集用户详细信息
/// 
公共IActionResult注册表详细信息(Guid CustomerId)
{
var Details=new Details()
{
CustomerID=CustomerID
};
返回视图(详细信息);
}
/// 
///如果有效,将用户详细信息保存在数据库中
/// 
[HttpPost]
公共IActionResult注册表详细信息(详细信息)
{
if(ModelState.IsValid)
{
//做事
}
//错误,将ViewModel返回到视图
返回视图(注册表详细信息);
}
但我不确定如何将模型传递给处理它的方法。当我提交表单时,它会运行原始方法,而不是[HttpPost]下的方法-它会一次又一次地发布到原始方法(其中//Do stuff是-当我这样做时:

/// <summary>
/// Collect user details
/// </summary>
[Route("Register/Details/{CustomerId}")]
public IActionResult RegisterDetails(Guid CustomerId)
{
    var Details = new Details()
    {
        CustomerID = CustomerId
    };

    return View(Details);
}

/// <summary>
/// Save user details in Db if valid
/// </summary>
[HttpPost]
[Route("Register/Details")]
public IActionResult RegisterDetails(Details Details)
{
    if (ModelState.IsValid)
    {
        // Do stuff
    }

    // Error, return ViewModel to view
    return View(RegisterDetails);
}
//
///收集用户详细信息
/// 
[路由(“注册/详细信息/{CustomerId}”)]
公共IActionResult注册表详细信息(Guid CustomerId)
{
var Details=new Details()
{
CustomerID=CustomerID
};
返回视图(详细信息);
}
/// 
///如果有效,将用户详细信息保存在数据库中
/// 
[HttpPost]
[路线(“登记/详细信息”)]
公共IActionResult注册表详细信息(详细信息)
{
if(ModelState.IsValid)
{
//做事
}
//错误,将ViewModel返回到视图
返回视图(注册表详细信息);
}
使用属性路由时如何正确绑定模型

我搜索了谷歌-我发现了一些没有帮助的东西,例如:

thx

更新

我还注意到CustomerId被附加到Url中,即使在表单发布之后也是如此。我认为MVC 5中不会发生这种情况,也不需要这样做,CustomerId隐藏在页面中


如何删除此项(它导致路由与[HttpPost]修饰方法不匹配)。

通常,您可以通过API类控制器添加属性“route”作为基本路径,然后添加参数。为了更好地理解,我还尝试始终为控制器添加动词

[Route("Register/Details/")]
public class RegistrerExampleController : ControllerBase
{

    /// <summary>
    /// Collect user details
    /// </summary>
    [HttpGet("{CustomerId}", Name = nameof(RegisterDetails))]
    public IActionResult RegisterDetails(Guid CustomerId)
    {
        var Details = new Details()
        {
            CustomerID = CustomerId
        };

        return View(Details);
    }

    /// <summary>
    /// Save user details in Db if valid
    /// </summary>
    [HttpPost]
    public IActionResult RegisterDetails(Details Details)
    {
        if (ModelState.IsValid)
        {
            // Do stuff
        }

        // Error, return ViewModel to view
        return View(RegisterDetails);
    }
}
[路线(“登记/详细信息/”)
公共类寄存器ExampleController:ControllerBase
{
/// 
///收集用户详细信息
/// 
[HttpGet(“{CustomerId}”,Name=nameof(RegisterDetails))]
公共IActionResult注册表详细信息(Guid CustomerId)
{
var Details=new Details()
{
CustomerID=CustomerID
};
返回视图(详细信息);
}
/// 
///如果有效,将用户详细信息保存在数据库中
/// 
[HttpPost]
公共IActionResult注册表详细信息(详细信息)
{
if(ModelState.IsValid)
{
//做事
}
//错误,将ViewModel返回到视图
返回视图(注册表详细信息);
}
}

您尝试过这个吗?

通常,您可以通过API类控制器添加属性“route”作为基本路径,然后添加参数。为了更好地理解,我还尝试始终为控制器添加动词

[Route("Register/Details/")]
public class RegistrerExampleController : ControllerBase
{

    /// <summary>
    /// Collect user details
    /// </summary>
    [HttpGet("{CustomerId}", Name = nameof(RegisterDetails))]
    public IActionResult RegisterDetails(Guid CustomerId)
    {
        var Details = new Details()
        {
            CustomerID = CustomerId
        };

        return View(Details);
    }

    /// <summary>
    /// Save user details in Db if valid
    /// </summary>
    [HttpPost]
    public IActionResult RegisterDetails(Details Details)
    {
        if (ModelState.IsValid)
        {
            // Do stuff
        }

        // Error, return ViewModel to view
        return View(RegisterDetails);
    }
}
[路线(“登记/详细信息/”)
公共类寄存器ExampleController:ControllerBase
{
/// 
///收集用户详细信息
/// 
[HttpGet(“{CustomerId}”,Name=nameof(RegisterDetails))]
公共IActionResult注册表详细信息(Guid CustomerId)
{
var Details=new Details()
{
CustomerID=CustomerID
};
返回视图(详细信息);
}
/// 
///如果有效,将用户详细信息保存在数据库中
/// 
[HttpPost]
公共IActionResult注册表详细信息(详细信息)
{
if(ModelState.IsValid)
{
//做事
}
//错误,将ViewModel返回到视图
返回视图(注册表详细信息);
}
}

您尝试过这个吗?

问题有两个方面。首先,您有您的
注册表详细信息(Guid CustomerId)
通过
route
属性设置路由的操作。这将打开它以接受所有HTTP动词:GET、POST等。第二,虽然您没有发布视图,但我可以假设您可能有一个带有空操作的表单,即:

 <form method="post">
     ...
 </form>
然后,如果要保留此路由方案,则需要在表单中显式显示。但是,由于两个操作具有相同的名称,这有点困难。ASP.NET Core将尝试回填路由的CustomerId部分,因为它已存在于路由数据中。您有三个选项:

  • 使用不同的操作名称。然后,您可以将表单显式绑定到post操作:

    [HttpPost("Register/Details")]
    public IActionResult RegisterDetailsPost(Details Details)
    
    然后:

    然后:

    您仍然可以提供客户id,但您需要使用查询字符串,即
    /Register/Details?CustomerId=123456
    。在链接中生成URL,这不会有什么不同。ASP.NET Core会将包含的任何没有明确路由参数的路由数据自动附加为查询字符串参数。换句话说,您仍然可以只需做如下操作:

    <a asp-action="RegisterDetails" asp-route-customerId="123456">Click me</a>
    
    点击我
    

  • 这个问题有两个方面。首先,您的
    RegisterDetails(Guid CustomerId)
    操作通过
    route
    属性设置了路由。这将打开它以接受所有HTTP动词:GET、POST等。第二,尽管您没有发布视图,但我可以假设您可能有一个带有空操作的表单,即:

     <form method="post">
         ...
     </form>
    
    然后,如果要保留此路由方案,则需要在表单中显式显示。但是,由于两个操作具有相同的名称,这有点困难。ASP.NET Core将尝试回填路由的CustomerId部分,因为它已存在于路由数据中。您有三个选项:

  • 使用不同的操作名称。然后,您可以将表单显式绑定到post操作:

    [HttpPost("Register/Details")]
    public IActionResult RegisterDetailsPost(Details Details)
    
    然后:

    然后:

    您仍然可以提供客户id,但您需要使用查询字符串,即
    /Register/Details?CustomerId=123456
    。在链接中生成URL,这不会有什么不同。ASP.NET Core将附加任何包含的没有明确说明的路由数据
    [HttpGet("Register/Details")]
    public IActionResult RegisterDetails(Guid CustomerId)
    
    <a asp-action="RegisterDetails" asp-route-customerId="123456">Click me</a>
    
    public IActionResult RegisterDetails([FromBody]Details Details)