我将一些值传递给我的控制器动作,一切都很好。 POST设计中将缺少两个属性。
然后我设置了缺失值,但后来我想验证模型,它仍然是假的,因为看起来ModelState没有赶上我的更改。
[HttpPost, Authorize]
public ActionResult Thread(int id, string groupSlug, Comment comment, string submitButton)
{
comment.UserID = UserService.UID;
comment.IP = Request.UserHostAddress;
UpdateModel(comment); //throws invalidoperationexception
if (ModelState.IsValid) // returns false if i skip last line
{
//save and stuff
//redirect
}
//return view
}
最简洁的方法是轻拍模拟状态并告诉它一切都会好的,同时仍然验证从用户的POST绑定的所有其他内容
答案 0 :(得分:39)
如果您的模型需要缺少值,但在绑定之后才会提供,您可能需要清除ModelState
中这两个值导致的错误。
[HttpPost, Authorize]
public ActionResult Thread(int id, string groupSlug, Comment comment, string submitButton)
{
comment.UserID = UserService.UID;
comment.IP = Request.UserHostAddress;
//add these two lines
ModelState["comment.UserID"].Errors.Clear();
ModelState["comment.IP"].Errors.Clear();
UpdateModel(comment); //throws invalidoperationexception
if (ModelState.IsValid) // returns false if i skip last line
{
//save and stuff
//redirect
}
//return view
}
答案 1 :(得分:6)
我使用的是ASP.NET Core 1.0.0和异步绑定,对我来说解决方案是使用ModelState.Remove并传递属性名称(不带对象名称)。
[HttpPost]
[ValidateAntiForgeryToken]
public async Task<IActionResult> Submit([Bind("AerodromeID,ObservationTimestamp,RawObservation")] WeatherObservation weatherObservation)
{
weatherObservation.SubmitterID = this.User.FindFirst(ClaimTypes.NameIdentifier)?.Value;
weatherObservation.RecordTimestamp = DateTime.Now;
ModelState.Remove("SubmitterID");
if (ModelState.IsValid)
{
_context.Add(weatherObservation);
await _context.SaveChangesAsync();
return RedirectToAction("Index", "Aerodrome");
}
return View(weatherObservation);
}
答案 2 :(得分:1)
在 .NET Core 之前,您可以使用控制器的 Validate(TEntity entity)
功能。但首先您必须清除现有的 ModelState 错误。
假设您为实体设置了一个缺失的必需属性。
ModelState.Clear();
Validate(entity);
if (!ModelState.IsValid) {}
使用 Core 您可以使用 TryValidateModel
而不是 ModelState.IsValid
看到这个:https://docs.microsoft.com/en-us/aspnet/core/mvc/models/validation?view=aspnetcore-5.0