asp.net core mvc view中使用依赖注入

时间:2023-02-03 21:35:43

asp.net core 支持依赖注入到View视图,这可以对某些特定的视图提供服务,例如:仅对于填充视图元素所需的本地化或数据。

你应该尽量保持控制器和视图之间的分离。您的视图显示的大部分数据应从控制器传入。

1、一个简单的例子

你可以直接使用@inject注入一个服务到视图中。您可以这么认为使用@inject 关键词像View中添加一个属性,并使用DI来填充该

属性。

 语法:@inject <type> <name>

下面这个例子展示@inject用法:

 

@using System.Threading.Tasks
@using ViewInjectSample.Model
@using ViewInjectSample.Model.Services
@model IEnumerable<ToDoItem>
@inject StatisticsService StatsService
<!DOCTYPE html>
<html>
<head>
<title>To Do Items</title>
</head>
<body>
<div>
<h1>To Do Items</h1>
<ul>
<li>Total Items: @StatsService.GetCount()</li>
<li>Completed: @StatsService.GetCompletedCount()</li>
<li>Avg. Priority: @StatsService.GetAveragePriority()</li>
</ul>
<table>
<tr>
<th>Name</th>
<th>Priority</th>
<th>Is Done?</th>
</tr>
@foreach (var item in Model)
{
<tr>
<td>@item.Name</td>
<td>@item.Priority</td>
<td>@item.IsDone</td>
</tr>
}
</table>
</div>
</body>
</html>

这个示例中显示ToDoItem列表的实例,以及显示总体统计信息的摘要。这个服务从过依赖注入进去在Startup

// For more information on how to configure your application, visit http://go.microsoft.com/fwlink/?LinkID=398940
public void ConfigureServices(IServiceCollection services)
{
services.AddMvc();

services.AddTransient<IToDoItemRepository, ToDoItemRepository>();
services.AddTransient<StatisticsService>();
services.AddTransient<ProfileOptionsService>();
}

StatisticsService 用于某些计算ToDoItem实例,它内部访问一个repository。

 

using System.Linq;
using ViewInjectSample.Interfaces;

namespace ViewInjectSample.Model.Services
{
public class StatisticsService
{
private readonly IToDoItemRepository _toDoItemRepository;

public StatisticsService(IToDoItemRepository toDoItemRepository)
{
_toDoItemRepository = toDoItemRepository;
}

public int GetCount()
{
return _toDoItemRepository.List().Count();
}

public int GetCompletedCount()
{
return _toDoItemRepository.List().Count(x => x.IsDone);
}

public double GetAveragePriority()
{
if (_toDoItemRepository.List().Count() == 0)
{
return 0.0;
}

return _toDoItemRepository.List().Average(x => x.Priority);
}
}
}


这个例子中的respository使用了内存集合,上面代码展示了实现的,不推荐远程访问一些大的数据。

这个例子显示的数据通过模型绑定到View和依赖注入到Service

 

2、填充查找数据

视图中使用依赖注入可以填充用户界面元素,例如:下拉列表框。考虑到用户配置文件窗体,

其中包含用于指定性别、状体和其他一些选项。使用标准的MVC方式访问需要控制器请求获取数据服务为每个选项,

为每个选项绑定填充数据用model或ViewBag.

另一种方式直接将服务注入视图以获取选项。减少了控制器上的代码数量。此视图元素构造逻辑代码移植到了视图

本身。要显示配置文件的编辑窗体,只需要将此实例传递到窗体中。

using Microsoft.AspNetCore.Mvc;
using ViewInjectSample.Model;

namespace ViewInjectSample.Controllers
{
public class ProfileController : Controller
{
[Route("Profile")]
public IActionResult Index()
{
// TODO: look up profile based on logged-in user
var profile = new Profile()
{
Name = "Steve",
FavColor = "Blue",
Gender = "Male",
State = new State("Ohio","OH")
};
return View(profile);
}
}
}

用于更新这些选项的 HTML 窗体包括有关三个属性的下拉列表中:

asp.net core mvc view中使用依赖注入

这写列表通过注入到视图里面的服务来填充数据:

@using System.Threading.Tasks
@using ViewInjectSample.Model.Services
@model ViewInjectSample.Model.Profile
@inject ProfileOptionsService Options
<!DOCTYPE html>
<html>
<head>
<title>Update Profile</title>
</head>
<body>
<div>
<h1>Update Profile</h1>
Name: @Html.TextBoxFor(m => m.Name)
<br/>
Gender: @Html.DropDownList("Gender",
Options.ListGenders().Select(g =>
new SelectListItem() { Text = g, Value = g }))
<br/>

State: @Html.DropDownListFor(m => m.State.Code,
Options.ListStates().Select(s =>
new SelectListItem() { Text = s.Name, Value = s.Code}))
<br />

Fav. Color: @Html.DropDownList("FavColor",
Options.ListColors().Select(c =>
new SelectListItem() { Text = c, Value = c }))
</div>
</body>
</html>
ProfileOptionsService是 UI 级服务,旨在提供所需的此窗体数据:
using System.Collections.Generic;

namespace ViewInjectSample.Model.Services
{
public class ProfileOptionsService
{
public List<string> ListGenders()
{
// keeping this simple
return new List<string>() {"Female", "Male"};
}

public List<State> ListStates()
{
// a few states from USA
return new List<State>()
{
new State("Alabama", "AL"),
new State("Alaska", "AK"),
new State("Ohio", "OH")
};
}

public List<string> ListColors()
{
return new List<string>() { "Blue","Green","Red","Yellow" };
}
}
}