11

基本上我想要做的是通过让他们输入他们的帐户和他们的社会安全号码来验证用户。如果他们输入了错误的组合,我会在Authenticatepost 操作中执行以下操作:

ModelState.AddModelError("Authenticated", authenticationError);
return View();

这将显示错误,但随后我丢失了查询字符串中的内容。保留查询字符串的另一种方法是:

ModelState.AddModelError("Authenticated", authenticationError);
return Redirect(Request.Url + "?returnUrl=" + returnUrl);

这将保留查询字符串,但不会显示错误。我认为这是因为ModelState已经改变了。

我需要,因为每当用户单击以查看特定事件时,他们都会returnUrl被迫访问该页面。Authenticate我想对其进行设置,以便他们在进行身份验证后仍然可以参加此活动。

有没有办法既可以保存查询字符串又可以显示模型错误?

4

3 回答 3

9

Ivan Korytin答案是最好的(也是我能找到的唯一答案,它似乎在不使用隐藏字段黑客的情况下实际上可以正常工作),我用Request.QueryString.

您必须将参数作为表单操作的一部分:

<form action="@Url.Action("CreateEntity", "Employee")?@(Request.QueryString)"
  enctype="multipart/form-data" method="POST">

当您执行以下操作时,查询字符串(和GET参数)现在被保留:

[HttpPost]
public ActionResult MyAction(MyAction model)
{
    if (!ModelState.IsValid)
    {
        return View(model);
    }
于 2018-07-05T14:50:50.693 回答
5

您的第二种情况没有模型状态,因为当您进行重定向时,浏览器向该位置发出单独的请求,单独的请求 = 新的模型状态。

我建议使用您的第一个场景并在您的模型中放置一个“ReturnUrl”并将其作为隐藏字段呈现给客户端。

//In your model add the ReturnUrl Property
public class AuthenticatModel
{
     public string Account {get; set;}
     public string SocialSecurityNumber {get;set;}
     public string ReturnUrl {get;set;}
}



ModelState.AddModelError("Authenticated", authenticationError);
//Set the return URL property before returning the view
model.ReturnUrl = returnUrl;
return View(model);


@* add the return URL as a hidden field to your view so it can be posted back *@
@Html.HiddenFor(model => model.ReturnUrl)
于 2013-05-31T15:11:23.310 回答
0

对于ASP.NET Core ,您可以使用 asp-route-* 属性:

<form asp-action="Login" asp-route-returnUrl="@Model.ReturnUrl">

其他详细示例: 假设您有一个带有动作的车辆控制器

指数

细节

编辑

并且您可以从索引或详细信息中编辑任何车辆,因此如果您单击从索引编辑,您必须在编辑后返回到索引;如果您单击从详细信息编辑,您必须在编辑后返回到详细信息。

//In your viewmodel add the ReturnUrl Property
public class VehicleViewModel
{
     ..............
     ..............
     public string ReturnUrl {get;set;}
}



Details.cshtml
<a asp-action="Edit" asp-route-previous="Details" asp-route-id="@Model.CarId">Edit</a>

Index.cshtml
<a asp-action="Edit" asp-route-previous="Index" asp-route-id="@item.CarId">Edit</a>

Edit.cshtml
<form asp-action="Edit" asp-route-previous="@Model.ReturnUrl" class="form-horizontal">
        <div class="box-footer">
            <a asp-action="@Model.ReturnUrl" class="btn btn-default">Back to List</a>
            <button type="submit" value="Save" class="btn btn-warning pull-right">Save</button>
        </div>
    </form>

在您的控制器中:

// GET: Vehicle/Edit/5
    public ActionResult Edit(int id,string previous)
    {
            var model = this.UnitOfWork.CarsRepository.GetAllByCarId(id).FirstOrDefault();
            var viewModel = this.Mapper.Map<VehicleViewModel>(model);//if you using automapper
    //or by this code if you are not use automapper
    var viewModel = new VehicleViewModel();

    if (!string.IsNullOrWhiteSpace(previous)
                viewModel.ReturnUrl = previous;
            else
                viewModel.ReturnUrl = "Index";
            return View(viewModel);
        }



[HttpPost]
    public IActionResult Edit(VehicleViewModel model, string previous)
    {
            if (!string.IsNullOrWhiteSpace(previous))
                model.ReturnUrl = previous;
            else
                model.ReturnUrl = "Index";
            ............. 
            .............
            return RedirectToAction(model.ReturnUrl);
    }
于 2019-12-22T14:40:01.603 回答