IOC 容器在 ASP.NET MVC 中的应用

IOC:Inversion Of Control 翻译为控制反转,我们在面向对象软件开发过程中,一个应用程序它的底层结构可能由N种不同的构件来相互协作来完成我们定义的系统的业务逻辑。哪么每一个构件可能相互独立和相互依赖,如果相互依赖的构件中的某一个构件出现异常,就会影响到整个系统的稳定运行,对象之间的耦合关系是无法避免的,也是必要的,因为这是协同工作的基础。如何降低系统之间、模块之间和对象之间的耦合度,是软件工程永远追求的目标之一。为了解决对象之间的耦合度过高的问题,IOC 的理念被提出,并被成功地应用到实践当中。说直白一点,就是对象之间的创建与维护我们全权交给了外部容器来管理,这样就实现了所谓的反转。

.NET 体系下这些相对成熟轻量级的IOC 容器,Castle Windsor、Unity、Spring.NET、StructureMap和Ninject等,下面我们就开始演示IOC在ASP.NET MVC 下的应用,在这里我们选择 Castle 来做为 IOC 容器。ASP.NET MVC 的 Controller 激活是靠ControllerFactory来创建的Controller对象的,所以我们就直接创建一个WindsorControllerFactory类,通过继承自DefaultControllerFactory来实现Controller的实例创建解析和释放等功能。

 1 using Castle.Core.Resource;
2 using Castle.Windsor;
3 using Castle.Windsor.Configuration.Interpreters;
4 using System;
5 using System.Linq;
6 using System.Reflection;
7 using System.Web.Mvc;
8
9 namespace mvc_with_Castle.App_Start
10 {
11 public class WindsorControllerFactory : DefaultControllerFactory
12 {
13 private WindsorContainer container;
14 public WindsorControllerFactory()
15 {
16 container = new WindsorContainer(
17 new XmlInterpreter(new ConfigResource("castle"))
18 );
19
20 var controllerTypes = from t in Assembly.GetExecutingAssembly().GetTypes()
21 where typeof(IController).IsAssignableFrom(t)
22 select t;
23 foreach (Type t in controllerTypes)
24 container.AddComponentLifeStyle(t.FullName, t, Castle.Core.LifestyleType.Transient);
25 }
26
27 protected override IController GetControllerInstance(System.Web.Routing.RequestContext requestContext, Type controllerType)
28 {
29 return (IController)container.Resolve(controllerType);
30 }
31 }
32 }

一个自定义的WindsorControllerFactory就这么简单的创建完了,下一步创建一个基于 IWindsorInstaller 的对容器的安装类

using Castle.MicroKernel.Registration;
using Castle.MicroKernel.SubSystems.Configuration;
using System.Web.Mvc; namespace mvc_with_Castle.App_Start
{
public class ControllersInstaller : IWindsorInstaller
{
public void Install(Castle.Windsor.IWindsorContainer container, IConfigurationStore store)
{
container.Register(Classes.FromThisAssembly()
.BasedOn<IController>()
.LifestyleTransient().Configure(c => c.DependsOn()));
}
}
}

接下来我们对Global.asax做一些修改,注册我们默认的 WindsorControllerFactory 控制器工厂类。

 1 using Castle.Windsor;
2 using Castle.Windsor.Installer;
3 using mvc_with_Castle.App_Start;
4 using System.Web.Mvc;
5 using System.Web.Optimization;
6 using System.Web.Routing;
7
8 namespace mvc_with_Castle
9 {
10 public class MvcApplication : System.Web.HttpApplication
11 {
12 private static IWindsorContainer container;
13 private static void MyContainer()
14 {
15 container = new WindsorContainer().Install(FromAssembly.This());
16
17 var controllerFactory = new WindsorControllerFactory();
18 ControllerBuilder.Current.SetControllerFactory(controllerFactory);
19 }
20 protected void Application_Start()
21 {
22 AreaRegistration.RegisterAllAreas();
23 FilterConfig.RegisterGlobalFilters(GlobalFilters.Filters);
24 RouteConfig.RegisterRoutes(RouteTable.Routes);
25 BundleConfig.RegisterBundles(BundleTable.Bundles);
26
27 MyContainer();
28 }
29
30 protected void Application_End()
31 {
32 container.Dispose();
33 }
34 }
35 }

所有的准备工作差不多都准备完毕,接下来我们就来定义一个接口实现对人员的查询

 1 using System.Collections.Generic;
2
3 namespace mvc_with_Castle.Service
4 {
5 public class SysUser
6 {
7 public string Name { get; set; }
8
9 public string Sex { get; set; }
10
11 public string Phone { set; get; }
12
13 public string Address { get; set; }
14
15 public string Email { get; set; }
16 }
17
18 public interface IUsersSvr
19 {
20 IEnumerable<SysUser> QueryUsers();
21 }
22
23 public class UsersSvr : IUsersSvr
24 {
25 private static IList<SysUser> list;
26
27 static UsersSvr()
28 {
29 list = new List<SysUser>();
30 for (int i = 0; i < 10; i++)
31 {
32 list.Add(new SysUser()
33 {
34 Name = "如花" + i,
35 Sex = "男",
36 Phone = "13882880818",
37 Address = "皇后大道中段" + i + "号",
38 Email = "jack@gmail.com"
39 });
40 }
41 }
42
43 public IEnumerable<SysUser> QueryUsers()
44 {
45 return list;
46 }
47 }
48 }

再下来就是我们对Castle IOC的配置管理

 1  <configSections>
2 <section name="castle" type="Castle.Windsor.Configuration.AppDomain.CastleSectionHandler, Castle.Windsor"/>
3 </configSections>
4
5 <!--注册服务-->
6 <castle>
7 <components>
8 <component id="UsersSvr" type="mvc_with_Castle.Service.UsersSvr, mvc_with_Castle" service="mvc_with_Castle.Service.IUsersSvr, mvc_with_Castle" lifestyle="Singleton"/>
9 </components>
10 </castle>

最后调用我们定义的 IUserSvr 接口来实现查询数据

 1 using System.Collections.Generic;
2 using System.Web.Mvc;
3 using mvc_with_Castle.Service;
4
5 namespace mvc_with_Castle.Controllers
6 {
7 public class HomeController : Controller
8 {
9 public IUsersSvr _svr { get; set; }
10 public ActionResult Index()
11 {
12 IEnumerable<SysUser> list = _svr.QueryUsers();
13 return View(list);
14 }
15 }
16 }

人员信息显示效果如下 

在这里我们已经大概了解了什么是IOC容器,和在 ASP.NET MVC 下面我们怎样利用 IOC 容器来实现通过接口的方式来进行服务的调用的大致原理,在上面的HomeController里面,很明显我们不用担心接口怎么被实例化的,或者说我们没明白服务到底怎么被激活了,哪么再回头看看前面的代码是不是就一目了然了呢 ?

 
 

IOC 容器在 ASP.NET MVC 中的应用的更多相关文章

  1. Unity容器在asp.net mvc中的IOC应用及AOP应用

    <asp.net-mvc框架揭秘>一书中,有个示例,是使用unity容器来注入自定义的控制器工厂.代码示例可以自己去下载源码,在这里我就不说了.IOC容器的本质是解耦的实例化接口类,而如何 ...

  2. ADO.NET .net core2.0添加json文件并转化成类注入控制器使用 简单了解 iTextSharp实现HTML to PDF ASP.NET MVC 中 Autofac依赖注入DI 控制反转IOC 了解一下 C# AutoMapper 了解一下

    ADO.NET   一.ADO.NET概要 ADO.NET是.NET框架中的重要组件,主要用于完成C#应用程序访问数据库 二.ADO.NET的组成 ①System.Data  → DataTable, ...

  3. [转]ASP.NET MVC中你必须知道的13个扩展点

    本文转自:http://www.cnblogs.com/ejiyuan/archive/2010/03/09/1681442.html ScottGu在其最新的博文中推荐了Simone Chiaret ...

  4. Asp.net mvc 中Action 方法的执行(二)

    [toc] 前面介绍了 Action 执行过程中的几个基本的组件,这里介绍 Action 方法的参数绑定. 数据来源 为 Action 方法提供参数绑定的原始数据来源于当前的 Http 请求,可能包含 ...

  5. Asp.net mvc 中Action 方法的执行(一)

    [toc] 在 Aps.net mvc 应用中对请求的处理最终都是转换为对某个 Controller 中的某个 Action 方法的调用,因此,要对一个请求进行处理,第一步,需要根据请求解析出对应的 ...

  6. Asp.net mvc 中的 Controller 的激活

    Controller 激活是指根据路由系统解析出来的 Controller 的名称创建 控制器(Controller)的过程,这里的控制器泛指实现了 IController 接口的类型 激活过程中的核 ...

  7. Asp.net mvc 中View 的呈现(二)

    [toc] 上一节介绍了 Asp.net mvc 中除 ViewResult 外的所有的 ActionResult,这一节介绍 ViewResult. ViewResultBase ViewResul ...

  8. 在ASP.NET MVC中使用Castle Windsor

    平常用Inject比较多,今天接触到了Castle Windsor.本篇就来体验其在ASP.NET MVC中的应用过程. Visual Studio 2012创建一个ASP.NET MVC 4网站. ...

  9. ASP.NET MVC中你必须知道的13个扩展点

         ScottGu在其最新的博文中推荐了Simone Chiaretta的文章13 ASP.NET MVC extensibility points you have to know,该文章为我 ...

随机推荐

  1. 30分钟让你了解MongoDB基本操作(转)

    今天记录下MongoDB的基本操作,这只是最基本的,所以是应该掌握的. 数据库 数据库是一个物理容器集合.每个数据库都有自己的一套文件系统上的文件.一个单一的MongoDB服务器通常有多个数据库. 集 ...

  2. 【剑指offer】:Q44:直扑克

    def IsContinuous(seq, num = 5): zeros = 0; d = 0 seq = sorted(seq) for i in range(num - 1): if seq[i ...

  3. 3D数学学习笔记——笛卡尔坐标系

    本系列文章由birdlove1987编写.转载请注明出处. 文章链接: http://blog.csdn.net/zhurui_idea/article/details/24601215 1.3D数学 ...

  4. Angular规范

     只记录一些自己未曾用过,但觉得对以后的项目有帮助的规范 一 Javascript闭包 把Angular组件包装到一个立即调用函数表达式中(IIFE). 为什么?:把变量从全局作用域中删除了,这有助于 ...

  5. Android 滑动界面实现---Scroller类别 从源代码和开发文档了解(让你的移动布局)

    在android学习,行动互动是软件的重要组成部分,其中Scroller是提供了拖动效果的类,在网上.比方说一些Launcher实现滑屏都能够通过这个类去实现.. 样例相关博文:Android 仿 窗 ...

  6. cocos2dx 解释二具体的启动过程:内存管理和回调

    在上一篇的第二部分中.我们有一句代码待解释的: // Draw the Scene void CCDirector::drawScene(void) { -...     //tick before ...

  7. poj 2449 Remmarguts&#39; Date 【SPFA+Astar】【古典】

    称号:poj 2449 Remmarguts' Date 意甲冠军:给定一个图,乞讨k短路. 算法:SPFA求最短路 + AStar 以下引用大牛的分析: 首先,为了说话方便,列出一些术语: 在启示式 ...

  8. linux_shell_获取日期相关

    shell里直接调用系统变量 获取当天日期`date +%Y%m%d` 获取昨天日期`date -d yesterday +%Y%m%d` 获取前天日期`date -d -2day +%Y%m%d` ...

  9. win7安装ruby on rails开发环境

    前言 我们看到很多文章说ruby环境windows它是非常困难的基础上,这将是各种稀奇古怪的问题,因此,建议linux和mac发. 可是我依照教程搭了下,问题也不算太多.总过大概花费了2个半小时左右就 ...

  10. java传值和通过引用传递

    第一次使用int实验: public class TTEST { private static List<UserEntity> mList = new LinkedList<Use ...