在ASP.NET MVC中使用Unity进行依赖注入的三种方式

2013-12-15 21:07 by 小白哥哥, 146 阅读, 0 评论, 收藏编辑

在ASP.NET MVC4中,为了在解开Controller和Model的耦合,我们通常需要在Controller激活系统中引入IoC,用于处理用户请求的Controller,让Controller依赖于ModelRepository的抽象而不是它的实现。

我们可以在三个阶段使用IoC实现上面所说的解耦操作,首先需要简单介绍一下默认情况下Controller的激活过程:

  1. 用户发送请求黑ASP.NET,路由系统对请求进行解析,根据注册的路由规则对请求进行匹配,解析出Controller和Action的名称等信息。
  2. 将解析出的信息交给一个MvcRouteHandler对象进行处理,MvcHttpHandler中存在以个ControllerFactory成员,如果构造函数中没有提供一个实现IControllerFactory接口的对象,则默认构造函数通过调用ControllerBuilder.Current.GetControllerFactory()获取一个这样的对象。
  3. 系统调用上文对象中德GetHttpHandler获得了一个实现了IHttpHandler接口的MvcHandler对象最终处理请求。
  4. 在MvcHandler中调用BeginProcessRequest方法继续处理请求,方法中从1中解析的信息中获得Controller和Action的信息,而后利用2种的IControllerFactory对象激活Controller对象,并最终执行相应的Action。

第一种方法

由上文2种可知,我们可以创建自己的IControllerFactory对象实现依赖注入,然而我们可以通过直接继承DefaultControllerFactory并重写GetControllerInstance方法来实现,这样可以免去重新实现其他一些功能的工作。

以下是使用Unity创建的继承自DefaultControllerFactory的UnityControllerFactory的简单示例:

namespace UnitySample
{
public class UnityControllerFactory:DefaultControllerFactory
{
private IUnityContainer container; public UnityControllerFactory(IUnityContainer container)
{
this.container = container;
}
protected override IController GetControllerInstance(RequestContext requestContext, Type controllerType)
{
return null == controllerType ? null : (IController)this.container.Resolve(controllerType);
//return base.GetControllerInstance(requestContext, controllerType);
}
}
}

我们可以在App_Start中使用ControllerBuilder设置系统使用这个ControllerFactory

IUnityContainer container = new UnityContainer();
container.RegisterType<IXXXRepository, XXXRepository>();
UnityControllerFactory factory = new UnityControllerFactory(container);
ControllerBuilder.Current.SetControllerFactory(factory);
 

第二种方法

上文中继承的DefaultControllerFactory中,使用一个ControllerActivator的成员来实现对Controller的激活,如果创建对象中没有提供一个IControllerActivator对象,则提供一个默认实现了IControllerActivator的DefaultControllerActivator对象这个类型,这个接口中存在用于创建Controller对象的Create方法,在DefaultControllerFactory中有存在一个IControllerActivator类型的构造方法来制定它。所以我们可以使用一个自定义的实现自IControllerActivator借口的对象来进行依赖注入。

namespace UnitySample
{
public class UnityControllerActivator:IControllerActivator
{
private IUnityContainer container; public UnityControllerActivator(IUnityContainer container)
{
this.container = container;
}
public IController Create(RequestContext requestContext, Type controllerType)
{
return controllerType == null ? null : (IController)container.RegisterType(controllerType);
}
}
}

修改方法1中在App_Start中的代码,使用这个ControllerActivator:

IUnityContainer container = new UnityContainer();
container.RegisterType<IXXXRepository, XXXRepository>();
//UnityControllerFactory factory = new UnityControllerFactory(container);
IControllerActivator controllerActivator = new UnityControllerActivator(container);
DefaultControllerFactory defaultFactory = new DefaultControllerFactory(controllerActivator);
ControllerBuilder.Current.SetControllerFactory(defaultFactory);

第三种方法

如同DefaultControllerFactory类中一样,在DefaultControllerActivator中也存在一个包含一个参数(类型为IDependencyResolver)的构造方法和一个没有参数的构造方法,默认情况下DefaultControlerFactory使用无参构造函数实例化一个DefaultControllerActivator对象,这种情况下提供一个默认的IDependencyResolver对象。所以我们就同样可以使用一个自定义的IDependencyResolver类实现依赖注入。在IDependencyResolver接口中存在方法GetService和GetServices来对具体的类型进行解析

namespace UnitySample
{
public class UnityDependencyResolver:IDependencyResolver
{
private IUnityContainer container; public UnityDependencyResolver(IUnityContainer container)
{
this.container = container;
} public object GetService(Type serviceType)
{
return container.Resolve(serviceType);
} public IEnumerable<object> GetServices(Type serviceType)
{
return container.ResolveAll(serviceType);
}
}
}

修改App_Start中的方法,使用这个自定义的DependencyResolver:

IUnityContainer container = new UnityContainer();
container.RegisterType<IXXXRepository, XXXRepository>();
UnityDependencyResolver resolver = new UnityDependencyResolver(container);
DependencyResolver.SetResolver(resolver);
 
 
 

ASP.NET MVC中使用Unity进行依赖注入的三种方式的更多相关文章

  1. 在ASP.NET MVC中使用Unity进行依赖注入的三种方式

    在ASP.NET MVC4中,为了在解开Controller和Model的耦合,我们通常需要在Controller激活系统中引入IoC,用于处理用户请求的 Controller,让Controller ...

  2. Asp.net MVC 中使用 Ninject 实现依赖注入

    松耦合.针对抽象编程.不针对实现编程是面向对象设计的原则.依赖注入就是,在一个类的内部,不通过创建对象的实例而能够获得实现了某个公开接口的对象引用.所谓的控制反转也是相同的意思.把依赖的创建转移到了使 ...

  3. SSH深度历险记(八) 剖析SSH核心原则+Spring依赖注入的三种方式

           于java发育.一类程序猿必须依靠类的其他方法,它是通常new依赖类的方法,然后调用类的实例,这样的发展问题new良好的班统一管理的例子.spring提出了依赖注入的思想,即依赖类不由程 ...

  4. Spring注解依赖注入的三种方式的优缺点以及优先选择

    当我们在使用依赖注入的时候,通常有三种方式: 1.通过构造器来注入: 2.通过setter方法来注入: 3.通过filed变量来注入: 那么他们有什么区别吗?应该选择哪种方式更好? 三种方式的区别小结 ...

  5. SSH深度历险(八) 剖析SSH核心原理+Spring依赖注入的三种方式

           在java开发中,程序员在某个类中需要依赖其它类的方法,则通常是new一个依赖类再调用类实例的方法,这种开发存在的问题是new的类实例不好统一管理,spring提出了依赖注入的思想,即依 ...

  6. ASP.NET MVC2中Controller向View传递数据的三种方式

    转自:http://www.cnblogs.com/zhuqil/archive/2010/08/03/Passing-Data-from-Controllers-to-View.html 在Asp. ...

  7. Spring依赖注入的三种方式

    看过几篇关于Spring依赖注入的文章,自己简单总结了一下,大概有三种方式: 1.自动装配 通过配置applicationContext.xml中的标签的default-autowire属性,或者标签 ...

  8. spring4之依赖注入的三种方式

    1.Setter注入 <bean id="helloWorld" class="com.jdw.spring.beans.HelloWorld"> ...

  9. Spring基础05——Spring依赖注入的三种方式

    Spring支持3种依赖注入的方式:属性注入.构造器注入.工厂 1.属性注入 属性注入即通过setter方法注入Bean的属性或依赖的对象.使用<property>元素,使用name属性指 ...

随机推荐

  1. string.Format对C#字符串格式化

    String.Format 方法的几种定义: String.Format (String, Object) 将指定的 String 中的格式项替换为指定的 Object 实例的值的文本等效项.Stri ...

  2. sql server判断表是否存在

    1.判断数据表是否存在 方法一: use yourdb;go if object_id(N'tablename',N'U') is not nullprint '存在'else print '不存在' ...

  3. ssh 综合

    文件夹结构: 搭建项目: 1.创建web项目 2.创建各种包. com.atguigu.surveypark.dao.impl com.atguigu.surveypark.model com.atg ...

  4. hdu 2191 (多重背包+二进制优化)

    Problem Description 急!灾区的食物依然短缺!为了挽救灾区同胞的生命,心系灾区同胞的你准备自己采购一些粮食支援灾区,现在假设你一共有资金n元,而市场有m种大米,每种大米都是袋装产品, ...

  5. [Unity3D]Unity3D游戏开发之Unity与Android交互调用研究

    各位朋友,大家好,我是秦元培,欢迎大家关注我的博客,我的博客地址是blog.csdn.net/qinyuanpei.在前一篇文章中,我们研究了Android平台上Unity3D的手势操作并在之前的基础 ...

  6. 搭建一个三台服务器的Memcached集群

    关于memcached的基础知识可以查看博客其他博文,这里只记录了搭建的过程,谢谢! 1.分别在三台服务器上安装Memcached并启动 第一.由于memcached是基于libevent的事件处理, ...

  7. android studio 添加到项目库中的项目

    工程-对-new module-Android Library-module name和package name 它应该在同一个库被引入. 然后在该文件夹replace新的library 在gradl ...

  8. Cocos2d-x3.0之路--02(引擎文件夹分析和一些细节)

    关于怎么搭建好开发环境的我就不写了,网上非常多. 那么 我们来看看 引擎文件的文件夹 所谓知己知彼 百战不殆嘛 先说一下setup.py 这个文件是有关配置的python文件,比方我们在进行andro ...

  9. ArcGIS课程:表面数据转换成矢量数据

    虽然TIN (TIN) 和 terrain 数据收集被认为是载体表面.但它们实际上包括基于其他信息元素.并且该信息是在图象点.线或多边形原始格这可能是更实用的公式.在 ArcGIS 在,你可以很容易的 ...

  10. PHP 17: MySQL的简单介绍

    原文:PHP 17: MySQL的简单介绍 这一章将简单介绍MySQL的基本知识. 本文来自http://lib.hackbase.com/html/8/35125.htm. MySQL是最受欢迎的开 ...