Содержание
Создание компонентов представлений как наследников класса ViewComponent имеет ещё одно преимущество — благодаря такому подходу мы получаем доступ ряду полезных для работы нашего компонента свойств. Рассмотрим пример использования этих свойств в приложении.
Свойства ViewComponent
Класс ViewComponent предоставляет нам следующие полезные свойства, которые мы можем использовать в компоненте представления:
HttpContext |
представляет контекст HTTP, с помощью которого можно получить доступ к данным запроса пользователя и ответа. Подробнее работу с объектом этого класса мы рассматривали при изучении «чистого» ASP.NET Core. |
ModelState |
представляет состояние модели в виде объекта ModelStateDictionary. Подробнее об объекте этого класса см. здесь |
Request |
представляет контекст запроса в виде объекта HttpRequest. Подробнее об объекте этого класса см. здесь. |
RouteData |
возвращает данные текущего маршрута |
Url |
представляет объект класса, реализующего интерфейс IUrlHelper, который используется для генерации адресов URL |
User |
представляет объект класса, реализующего интерфейс IPrincipal (данные пользователя). Может использоваться для авторизации пользователей |
User |
представляет объект класса ClaimsPrincipal для текущего пользователя. |
ViewBag |
представляет динамический объект, который может использоваться для передачи данных в представление. Подробнее об этом объекте см. здесь |
ViewContext |
описывает контекст представления, в котором вызывается компонент |
ViewComponentContext |
представляет объект ViewComponentContext, который инкапсулирует контекст компонента |
ViewData |
возвращает объект ViewDataDictionary, который может применяться для передачи данных в представление. Подробнее об этом объекте см. здесь |
Продемонстрируем работу со свойствами ViewComponent на примере информации о запросе пользователя (свойство Request). В предыдущей части мы разработали компонент меню:
сам компонент (файл Menu.cs)
using Microsoft.AspNetCore.Mvc;
namespace AspMvcComponents.Components.Menu
{
public class MenuItem
{
public string Name { get; set; }
public string Link { get; set; }
}
public class Menu : ViewComponent
{
public IViewComponentResult Invoke(List<MenuItem> items)
{
if (Request.Query.ContainsKey("exclude") && Convert.ToBoolean(Request.Query["exclude"]))
{
string path = Request.Path;
var selectItem = items.FirstOrDefault((item) => item.Link == path);
if (selectItem != null)
{
selectItem.Link = string.Empty;
}
}
return View(items);
}
}
}
частичное представление компонента (Default.cshtml)
@addTagHelper *, AspMvcComponents
@using AspMvcComponents.Components
@{
ViewData["Title"] = "Home Page";
}
<vc:menu items="@(new()
{ new MenuItem() { Name="Главная", Link = "/"},
new MenuItem() { Name="Privacy", Link = "/home/privacy"}
})">
</vc:menu
Доработаем метод Invoke() компонента следующим образом:
public IViewComponentResult Invoke(List<MenuItem> items)
{
if (Request.Query.ContainsKey("exclude") && Convert.ToBoolean(Request.Query["exclude"]))
{
string path = Request.Path;
var selectItem = items.FirstOrDefault((item) => item.Link == path);
if (selectItem != null)
{
selectItem.Link = string.Empty;
}
}
return View(items);
}
Здесь мы, используя свойство Request, проверяем наличие параметра запроса с именем exclude и, если этот параметр равен true, то удаляем ссылку на элемент, совпадающий с Url страницы на которой загружается компонент. По-хорошему, конечно, стоит проверить, действительно ли в параметре содержится то, что можно преобразовать в bool, но, в качестве примера, мы это проверку опустим. Также, немного изменим частичное представление компонента (Default.cshtml):
@using AspMvcComponents.Components;
@using AspMvcComponents.Components.Menu
@model IEnumerable<MenuItem>
<ul>
@foreach (var item in Model)
{
if (string.IsNullOrEmpty(item.Link))
{
<li><b>@item.Name</b></li>
}
else
{
<li><a href="@item.Link">@item.Name</a></li>
}
}
</ul>
Теперь, для наглядности, добавим наш компонент в ещё одно представление, которое создается по умолчанию в шаблонном проекте ASP.NET Core MVC — Privacy.cshtml:
@addTagHelper *, AspMvcComponents
@using AspMvcComponents.Components;
@using AspMvcComponents.Components.Menu
@{
ViewData["Title"] = "Privacy Policy";
}
<h1>@ViewData["Title"]</h1>
<vc:menu items="@(new()
{ new MenuItem() { Name="Главная", Link = "/"},
new MenuItem() { Name="Privacy", Link = "/home/privacy"}
})">
</vc:menu>
<p>Use this page to detail your site's privacy policy.</p>
Проверим работу компонента:
Таким образом мы смогли из компонента представления получить доступ к контексту запроса, проверить наличие параметра запроса и изменить логику работы компонента, используя полученные данные.
Итого
Наследование компонента представления от ViewComponent позволяет нам не только использоваться для рендеринга частичные представления, но и воспользоваться рядом полезных свойств, таких как контекст запроса, данные о маршруте, данные, передаваемые в представление (ViewData/ViewBag) и т.д.

