在ASP.NET MVC中使用Castle Windsor

來源:互聯網
上載者:User

標籤:.config   sys   let   table   pac   contact   一個   routing   stc   

 

平常用Inject比較多,今天接觸到了Castle Windsor。本篇就來體驗其在ASP.NET MVC中的應用過程。

 

Visual Studio 2012建立一個ASP.NET MVC 4網站。

 

通過NuGet安裝Castle Windsor。

 

在當前項目下建立一個名稱為"IOC"的檔案夾。

 

在ASP.NET MVC中,每次請求,DefaultControllerFactory都會為我們建立controller執行個體,我們需要自訂一個派生自DefaultControllerFactory的類,讓Castle Windsor幫我們產生controller執行個體。

 

using System.Web;
using System.Web.Mvc;
using Castle.MicroKernel;

namespace MyCastleWindsor.IOC
{
    public class WindsorControllerFactory : DefaultControllerFactory
    {
        private readonly IKernel _kernel;

        public WindsorControllerFactory(IKernel kernel)
        {
            _kernel = kernel;
        }

        protected override IController GetControllerInstance(System.Web.Routing.RequestContext requestContext, System.Type controllerType)
        {
            if (controllerType == null)
            {
                throw  new HttpException(404,string.Format("當前對{0}的請求不存在",requestContext.HttpContext.Request.Path));
            }
            return (IController)_kernel.Resolve(controllerType);
        }

        public override void ReleaseController(IController controller)
        {
            _kernel.ReleaseComponent(controller);
            base.ReleaseController(controller);
        }
    }
}

 

現在需要在全域中產生Castle Windsor執行個體,賦值給自訂ControllerFactory的建構函式,並在Application結束時銷毀該Castle Windsor執行個體。

 

   public class MvcApplication : System.Web.HttpApplication
    {
        private IWindsorContainer _container;

        protected void Application_Start()
        {
            AreaRegistration.RegisterAllAreas();

            WebApiConfig.Register(GlobalConfiguration.Configuration);
            FilterConfig.RegisterGlobalFilters(GlobalFilters.Filters);
            RouteConfig.RegisterRoutes(RouteTable.Routes);
            BundleConfig.RegisterBundles(BundleTable.Bundles);

            //初始化一個IOC容器
            _container = new WindsorContainer().Install(FromAssembly.This());

            //完成IWindsorInstaller介面中的註冊
            ControllerBuilder.Current.SetControllerFactory(new WindsorControllerFactory(_container.Kernel));
        }

        protected void Application_End()
        {
            _container.Dispose();
        }
    }

 

現在,需要告訴Castle Windsor在何種條件下,以怎樣的方式註冊依賴。Castle Windsor提供了IWindsorInstaller介面。在IOC檔案夾下建立實現該介面的類。

 

using System.Web.Mvc;
using Castle.MicroKernel.Registration;
using MyCastleWindsor.Controllers;

namespace MyCastleWindsor.IOC
{
    public class ControllerInstaller : IWindsorInstaller
    {

        public void Install(Castle.Windsor.IWindsorContainer container, Castle.MicroKernel.SubSystems.Configuration.IConfigurationStore store)
        {
            container.Register(Classes.FromThisAssembly() //在哪裡找尋介面或類
                .BasedOn<IController>() //實現IController介面
                .If(Component.IsInSameNamespaceAs<HomeController>()) //與HomeController在同一個命名空間
                .If(t => t.Name.EndsWith("Controller")) //以"Controller"結尾
                .Configure(c => c.LifestylePerWebRequest()));//每次請求建立一個Controller執行個體
        }
    }
}

 

而實際上,在通用檔案中,當運行Install(FromAssembly.This())方法時,會執行 IWindsorInstaller的Install介面方法。

 

  舉例來說

 

假設有一個介面:

 

public interface IContactManager
{}

 

介面的實作類別:

 

public class ContactManager : IContactManager
{}

 

在某個控制器中,通過建構函式注入依賴,我們希望這樣寫:

 

private IContactManager contactManager;

public HomeController(IContactManager contactManager)
{
    this.contactManager = contactManager;
}

 

現在需要註冊IContactManager和ContactManager。可以通過反射方式註冊依賴。

 

using System.Web.Mvc;
using Castle.MicroKernel.Registration;
using MyCastleWindsor.Controllers;

namespace MyCastleWindsor.IOC
{
    public class ControllerInstaller : IWindsorInstaller
    {

        public void Install(Castle.Windsor.IWindsorContainer container, Castle.MicroKernel.SubSystems.Configuration.IConfigurationStore store)
        {

            container.Register(Classes.FromThisAssembly()
                .Where(t => t.Name.EndsWith("Manager"))
                .WithServiceDefaultInterfaces()
                .Configure(c => c.LifestyleTransient()));
        }
    }
}

 

 

關於Castle Windsor的應用大致如下:

 

→ 繼承ASP.NET MVC的ControllerFactory,通過建構函式傳入Castle Windsor的IKernel,讓其解析出IController類型控制器。

→ 通過實現Castle Windsor的IWindsorInstaller介面,通過反射註冊依賴關係。

→ 在通用檔案中初始化Castle Windsor的執行個體,並註冊自訂的ControllerFactory。

在ASP.NET MVC中使用Castle Windsor

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.