Public Class ProcessFile
Private _SettingsFile As String = "settings.bin"
Public Sub New()
End Sub
Public Sub New(settings As String)
_SettingsFile= settings
End Sub
Public Function ReadFile() As String
'Do stuff based on the settings stored in the _SettingsFile
End Function
End Class
在主mvc4项目名称SampleDependency. Unity.mvc4、unity.webapi和MicrosoftAsp.Net Web API 2.2 Web主机中安装以下Nuget包 在Web项目中
public static class Bootstrapper
{
public static IUnityContainer Initialise()
{
var container = BuildUnityContainer();
DependencyResolver.SetResolver(new UnityDependencyResolver(container));
GlobalConfiguration.Configuration.DependencyResolver = new Unity.WebApi.UnityDependencyResolver(container);
return container;
}
private static IUnityContainer BuildUnityContainer()
{
var container = new UnityContainer();
// register all your components with the container here
// it is NOT necessary to register your controllers
// e.g. container.RegisterType<ITestService, TestService>();
container.RegisterType<IUserDetailLogic, UserDetailLogic>();
container.RegisterType<IUserData, UserData>();
RegisterTypes(container);
return container;
}
public static void RegisterTypes(IUnityContainer container)
{
}
}
现在你可能会想:“但那是什么serviceCollection?它是一个列表?一个字典?".我现在的答案:服务集合是一个类,它可能在内部使用List或Dictionary或其他东西,但您不应该担心这些。 在哪里可以找到这个服务集合?这取决于你正在构建的应用类型。在关于App startup in ASP.NET Core的页面上,你可以看到这行代码:
public class IndexModel : PageModel
{
public void OnGet([FromServices] IGet i)
{
var queryHandler = i.Get<ProductOverviewQueryHandler>();
// do something
}
}
或者像这样
public class IndexModel : PageModel
{
private readonly IGet i;
public IndexModel(IGet iget)
{
i = iget;
}
public void OnGet()
{
var queryHandler = i.Get<ProductOverviewQueryHandler>();
// do something
}
public Task<IActionResult> OnPost(FilledOutForm request)
{
var result = i.Get<OtherHandler>().Handle(request);
// return something
}
}
或者为你的页面创建一个基类:
public class PageBase : PageModel
{
private IGet _iget;
private IGet i => _iget ??= HttpContext.RequestServices.GetRequiredService<IGet>();
}
像这样使用它:
public class IndexModel : PageBase
{
public void OnGet()
{
var queryHandler = i.Get<ProductOverviewQueryHandler>();
// do something
}
}
9条答案
按热度按时间snz8szmq1#
这里有一个常见的例子,你需要登录你的应用程序,但是在设计时,你不确定客户端是想登录数据库、文件还是事件日志。
因此,您希望使用DI将该选择推迟到可由客户机配置的选择。
这是一些伪代码(大致基于Unity):
创建日志记录接口:
然后在类中使用此接口
在运行时注入这些依赖项
示例在app.config中配置:
现在,如果您想更改日志记录器的类型,只需进入配置并指定另一种类型。
w7t8yxp52#
Ninject必须有一个最酷的样本:(从样品中截取)
这,对我来说,读起来非常流利,在你开始你的 dojo 之前,你可以决定如何武装你的武士。
hpcdzsge3#
我认为你首先学习没有IoC容器的DI是很重要的。因此,我写了一个例子,慢慢地构建一个IoC容器。这是我工作中的一个真实的的例子,但仍然足够基础,让新手抓住DI的本质。你可以在这里找到它:https://dannyvanderkraan.wordpress.com/2015/06/15/real-world-example-of-dependeny-injection/
它使用C#.NET,后来使用Unity。
评论后更新:
“观察原始设计的以下变化:
我们使用“构造函数注入”模式来实现DI,重构步骤如下:
1.通过创建接口ICardPresenceChecker抽象出CardPresenceChecker接口;
1.通过将其名称更改为XCardPresenceChecker,明确此CardPresenceChecker仅适用于公司X的库;
1.使用XCardPresenceChecker实现接口ICardPresenceChecker ;
1.将LogInService的属性抽象为ICardPresenceChecker类型,而不是“知道”船上的具体实现;
1.最后但并非最不重要的是,LogInService的用户(其他开发人员)要求他们提供至少实现ICardPresenceChecker的任何类,以便LogInService可以做它的事情。
LogInService的构造函数如下所示:
那么你在哪里为LogInService提供一个ICardPresenceChecker的实现呢(在该示例中,我们将ICardPresenceChecker“Map”到XCardPresenceChecker)在应用程序启动时的一个中心位置,在概念上称为“组合根”。对于可以是Program类中的空Main的常规控制台应用程序。因此对于该示例,这段代码将在前面提到的地方使用:
LogInService logInService = new LogInService(new XCardPresenceChecker());”
kgsdhlau4#
我有一个非常简单的依赖注入的例子。
看看下面的类,你会得到整个想法。正如你所看到的,除非你提供文件,它将使用默认的一个设置文件,但你可以设置一个设置文件,然后类将使用它。
显然这是最基本的情况。在真实的世界中,你可以对类类型做同样的事情,比如你有数据库层,你可以通过依赖注入来切换底层数据库dll,只要你能提供有效的类(一个实现你正在使用的接口的类),你的代码就可以与任何数据库一起工作。
在掌握了基础知识之后,你可以在更大的范围内完成这项工作,并通过使用像unity这样的DI框架完全独立于应用程序。
3mpgtkmj5#
你基本上在构造函数中传递了所有必需的对象。或者,你可以在运行时使用接口解析器来解析它们(尽管这不太类型安全)。你可以在Ninject网站上找到第一种方法的优秀例子,Unity网站上有第二种方法的很好的例子。这就避免了对单例的需要,并允许您轻松地放入符合所需接口的替换对象
gpnt7bae6#
在主mvc4项目名称SampleDependency. Unity.mvc4、unity.webapi和MicrosoftAsp.Net Web API 2.2 Web主机中安装以下Nuget包
在Web项目中
ffscu2ro7#
添加类型类库的业务逻辑项目,并在其中添加以下代码。public class UserDetailLogic:IUserDetailLogic {私有IUserData用户数据=空;
在你的主项目中添加下面的代码在家庭控制器。
公共类家庭控制器:控制器{ private readonly IUserDetailLogic _userDetailLogic;
58wvjzkj8#
创建数据库层项目(类库),并添加以下代码。
ou6hu8tu9#
这里的dependencies是什么意思?
一个类在其构造函数中拥有的所有参数都是该类的依赖项(好吧,有时属性可以被标记为依赖项,但现在让我们忽略它)。在下面的类中,依赖项是
ILogger
和IDbConnectionFactory
:请注意,
Handle
方法的参数MyRequest
不是类的依赖项,因为您不需要它来创建类的示例。这里的injection是什么意思?
而不是手动注入依赖项:
您可以将
MyConnectionFactory
和MyLogger
注册到“服务集合”,并自动注入这些依赖项。将类注册到服务集合
在.NET中,一个服务集合实现了
IServiceCollection
interface。假设你想让一个logger从应用程序启动到关闭都是同一个示例。然后你在启动时将它添加为“singleton”:现在你可能会想:“但那是什么
serviceCollection
?它是一个列表?一个字典?".我现在的答案:服务集合是一个类,它可能在内部使用List或Dictionary或其他东西,但您不应该担心这些。在哪里可以找到这个服务集合?这取决于你正在构建的应用类型。在关于App startup in ASP.NET Core的页面上,你可以看到这行代码:
builder
具有IServiceCollection
类型的属性Services
,并且已将IStartupFilter
添加到服务集合中。因此,在ASP.NET Core应用中,您可以在builder.Services
处找到服务集合。其他应用类型的命名可能不同,但您可能会在文档或示例项目中轻松找到它。如何使用这些服务?
在app启动的某个时候,从你的service集合中创建了一个实现
IServiceProvider
interface的新类,它有一个方法GetService
。理论上一个类可以实现两个接口:但实际上(经常)不是这种情况。
那么,我们如何找到
IServiceProvider
类型的属性呢?当构建ASP.NET Core应用时,页面有一个实际上是IServiceProvider
的HttpContext.RequestServices
property。但是,你可能不需要使用它,因为如果你向页面的构造函数添加依赖项,它会自动注入:另一种方法是在页面的
Get
或Post
方法中使用[FromServices]
attribute:注册什么,不注册什么?
ProductOverviewQueryHandler
。但是,如果该查询处理程序具有依赖关系怎么办?我如何注入它们?请继续阅读...注入高层类依赖
这可以通过多种方式实现。一种方式是在页面的任何地方使用
ActivatorUtilities
class:但很多人会觉得这是一个丑陋的阅读。
我发现非常干净的方法是使用NuGet包IGet。您的页面类看起来像这样:
或者像这样
或者为你的页面创建一个基类:
像这样使用它:
安装IGet
通过NuGet Package Manager in Visual Studio安装IGet,并添加到应用程序的启动:
之后,您可以使用IGet,如上面的示例所示。
进一步阅读