Отображение сообщения об ошибке в представлении из контроллера asp.net mvc 5

Я новичок в веб-разработке и пытаюсь изучить ASP.Net MVC 5. Я ищу одну запись в базе данных, если запись не найдена, то я хочу вывести пользователю сообщение об ошибке. Ниже приведена моя попытка:

Контроллер

    [HttpGet]
    public ActionResult Search()
    {
        return View();
    }

    [HttpPost]
    [ValidateAntiForgeryToken]
    public ActionResult Search(ForgotPasswordMV viewModel)
    {
        if (Temp.Check(viewModel.Email))
            return RedirectToAction("VerifyToken", new { query = viewModel.Email });
        else
        {
            ViewBag.ErrorMessage = "Email not found or matched";
            return View();
        }
    }

Вид:

<p>@ViewBag.ErrorMessage</p>

ViewModel

public class ForgotPasswordMV
{
    [Display(Name = "Enter your email"), Required]
    public string Email { get; set; }
}

Но я где-то читал, что я должен поместить одно свойство в мою модель представления и установить сообщение об ошибке на этом свойстве. Я запутался, как этого добиться и как потом отобразить ошибку в View? И какой вариант рекомендуется/лучшая практика?

Решение

Но я где-то читал, что я должен поместить одно свойство в модель представления... и установить сообщение об ошибке на этом свойстве. Я запутался, как добиться этого и как отобразить ошибку в View? И какой вариант является рекомендуемой/лучшей практикой?

Лучшая практика заключается в изменении свойства словаря ModelState вашего контроллера следующим образом:

[HttpPost]
[ValidateAntiForgeryToken]
public ActionResult Search(ForgotPasswordMV viewModel)
{
    // ... 
    else
    {
        ModelState.AddModelError("Email", "Email not found or matched");
        return View(viewModel);
    }
}

Затем в представлении добавьте следующую строку рядом с полем email;

@Html.ValidationMessageFor(m => m.Email)
Комментарии (8)

Но я где-то читал, что я должен поместить одно свойство в мою модель представления и установить сообщение об ошибке на этом свойстве.

Это верно. Вы можете добавить сообщение об ошибке в модель представления:

public class ForgotPasswordMV
{
    [Display(Name = "Enter your email"), Required]
    public string Email { get; set; }

    public string ErrorMessage { get; set; }
}

а затем установить это свойство в модели представления и передать модель представления в представление:

...
else
{
    viewModel.ErrorMessage = "Email not found or matched";
    return View(viewModel);
}

и, наконец, в вашем сильно типизированном представлении используйте свойство вашей модели:

@model ForgotPasswordMV
...
<p>@Model.ErrorMessage</p>

Таким образом, в основном мы заменяем использование ViewBag на сильно типизированную модель представления.

Комментарии (2)

Как по мне, принятый ответ не является лучшей практикой. Мы можем обработать все ошибки в аннотациях.
В нашей ViewModel мы указываем ErrorMessage для наших объектов.

public class UserLoginViewModel
{
    [Required(ErrorMessage = "User name is required")]
    [Display(Name = "User name")]
    [StringLength(500, ErrorMessage = "User name is too short", MinimumLength = 3)]
    public string Login { get; set; }

    [Required(ErrorMessage = "Password is required")]
    [Display(Name = "Password")]
    public string Password { get; set; }
}

В нашем контроллере

[HttpPost]
[ValidateAntiForgeryToken]
public ActionResult Login(UserLoginViewModel model)
{
    if (!this.ModelState.IsValid)
    {
        return this.View();
    }
    ...
}

И в нашем представлении

@Html.ValidationMessageFor(model => model.Login)
@Html.EditorFor(model => model.Login)
@Html.ValidationMessageFor(model => model.Password)
@Html.EditorFor(model => model.Password)
Комментарии (2)