0

我有一个 Asp.NET MVC 应用程序,我在其中使用数据注释向某些字段添加验证:

    [Required]
    [DisplayName("Course Name")]
    string Name { get; set; }

然而,这似乎并没有像我预期的那样工作。基本上,如果页面包含我手动检查并抛出新 RuleViolation() 的任何其他错误,则所需的违规将显示在验证摘要中。如果所需的违规是唯一的错误,则不会显示。

我的控制器中有以下代码:

        catch (Exception ex)
        {
            ModelState.AddModelError("", ex.Message);
            ModelState.AddRuleViolations(courseViewModel.Course.GetRuleViolations());
            return View(courseViewModel);
        }

但鉴于规定的违规行为不是投掷,我从不进入这里。

我是否需要做一些我不知道的事情来捕获 DataAnnotation 违规引发的错误?

谢谢你的帮助

编辑:

这是控制器动作:

    [HttpPost]
    [ValidateInput(true)]
    public ActionResult Edit(int id, CourseViewModel courseViewModel)
    {

        var oldCourse = _eCaddyRepository.GetCourse(id);

        if (courseViewModel.Course == null)
        {
            return View("NotFound", string.Format("Course {0} Not Found", id));
        }

        try
        {
            courseViewModel.Update(oldCourse);
            _eCaddyRepository.SubmitChanges();

            return RedirectToAction("Index", "Course");
        }
        catch (Exception ex)
        {
            ModelState.AddModelError("", ex.Message);
            ModelState.AddRuleViolations(courseViewModel.Course.GetRuleViolations());
            return View(courseViewModel);
        }
    }

更新在哪里:

    public class CourseViewModel : BaseViewModel
{
    public Course Course { get; set; }

    public void Update(Course oldCourse)
    {
        oldCourse.Name = this.Course.Name != null ? this.Course.Name.Trim() : string.Empty;
        oldCourse.Postcode = this.Course.Postcode != null ? this.Course.Postcode.Trim() : string.Empty;

        for (var i = 0; i < 18; i++)
        {
            oldCourse.Holes[i].Par = this.Course.Holes[i].Par;
            oldCourse.Holes[i].StrokeIndex = this.Course.Holes[i].StrokeIndex;
        }
    }
}

编辑:使用数据注释按预期工作和验证的最终代码。感谢母马。

    [HttpPost]
    [ValidateInput(true)]
    public ActionResult Edit(int id, CourseViewModel courseViewModel)
    {
        var oldCourse = _eCaddyRepository.GetCourse(id);

        if (courseViewModel.Course == null)
        {
            return View("NotFound", string.Format("Course {0} Not Found", id));
        }

        if (ModelState.IsValid)
        {
            try
            {
                courseViewModel.Update(oldCourse);
                _eCaddyRepository.SubmitChanges();
                return RedirectToAction("Index", "Course");
            }
            catch (Exception ex)
            {
                ModelState.AddModelError("", ex.Message);
            }
        }

        // Return Model with errors
        ModelState.AddRuleViolations(courseViewModel.Course.GetRuleViolations());
        return View(courseViewModel);
    }
4

3 回答 3

3

我想知道没有其他人指出这一点(jfar 很接近,但他的措辞不正确,所以 chrisp_68 可能不理解 jfar 对模型状态违规的含义)但是你的控制器缺少这个:

        if (ModelState.IsValid) // this check for model validity, not try..catch block
        {
            // do your stuff here, update to the datastore and return another view
        }

        // you can add additional Model State errors here manually if you wish
        // with AddModelError() like you do it now
        return View(editing); // return the same view with errors

所以你需要的是 ModelState.IsValid 检查,因为 DataAnnotations 不会自己执行任何异常抛出。

编辑:实际上,准确地说,DataAnnotations 不会抛出异常,因为如果它们这样做将是无稽之谈,因为这会破坏您的应用程序的执行,这当然是您不想要的。你想回到同一个视图并给用户一个纠正他的错误的机会。

另一方面,您仍然可以在 if(ModelState.IsValid) 中使用 try..catch 块来捕获真正的异常,例如无法写入磁盘或无法存储到数据库或将空值插入到没有空值的数据库列中允许等

高温高压

于 2010-07-25T15:40:40.117 回答
1

MVC2 中没有任何内容会因为 [Required] 字段而引发异常。

你会违反模型状态,就是这样。当您尝试将“Joel Atwood”绑定到 DateTime 字段时,可以肯定只有手​​动调用 ModelBinder 才会引发异常。

于 2010-07-24T15:11:15.840 回答
0

在类属性上放置数据注释,命名空间应该是“YouProject.Model”

于 2010-07-24T15:34:53.160 回答