zoukankan      html  css  js  c++  java
  • 在MVC项目中使用Ninject

    项目结构图:

          

    App_start文件夹中的文件是VS自己创建的,其中NinjectWebCommon类在创建之初并不存在。后面会再次提到!

    添加一个Home控制器。代码如下:

    using EssentialTools.Models;
    using Ninject;
    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Web;
    using System.Web.Mvc;
    
    namespace EssentialTools.Controllers
    {
        public class HomeController : Controller
        {
            private IValueCalculator calc;
            Product[] products ={
            new Product{Name="Kayak",Category="Watersports",Price=275M},
            new Product{Name="LifeJacket",Category="Watersports",Price=48.95M},
            new Product{Name="Soccer Ball",Category="Soccer",Price=19.50M},
            new Product{Name="Corner Flag",Category="Soccer",Price=34.95M}
            };
            public HomeController(IValueCalculator calcParam)
            {
                calc = calcParam;
            }
    
            public ActionResult Index()
            {              
                //IKernel ninjectKernel = new StandardKernel();
                //ninjectKernel.Bind<IValueCalculator>().To<LinqValueCalculator>();
                //LinqValueCalculator calc = new LinqValueCalculator();
                //return View(calc.ValueProducts(products));
                ShoppingCart cart = new ShoppingCart(calc) { Products = products };
                decimal totalValue = cart.CalculateProductTotal();
                return View(totalValue);
            }
           
        }
    }
    HomeController.cs

    为控制器中的Index方法添加视图。代码如下:

    @model decimal
    @{
        ViewBag.Title = "Index";
        Layout = null;
    }
    
    <div> Total value is $@Model</div>
    Index.cshtml

    创建Infrastructure文件夹,在该文件夹下创建Ninject的依赖解析器。代码如下:

    using EssentialTools.Models;
    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Web;
    using System.Web.Mvc;
    using Ninject;
    
    namespace EssentialTools.Infrastructure
    {
        public class NinjectDependencyResolver : IDependencyResolver
        {
            private IKernel kernel;
            public NinjectDependencyResolver(IKernel knernelParam)
            {
                kernel = knernelParam;
                AddBindings();
            }
    
            public object GetService(Type serviceType)
            {
                return kernel.TryGet(serviceType);
            }
            public IEnumerable<object> GetServices(Type serviceType)
            {
                return kernel.GetAll(serviceType);
            }
            private void AddBindings()
            {
                kernel.Bind<IValueCalculator>().To<LinqValueCalculator>();
            }
        }
    }
    NinjectDependencyResolver.cs

    在Models文件夹中攒关键1个接口,3个类。代码如下:

    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Web;
    
    namespace EssentialTools.Models
    {
        public interface IValueCalculator
        {
            decimal ValueProducts(IEnumerable<Product> products);
        }
    }
    IValueCalculator.cs
    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Web;
    
    namespace EssentialTools.Models
    {
        public class LinqValueCalculator : IValueCalculator
        {
            public decimal ValueProducts(IEnumerable<Product> products)
            {
                return products.Sum(p => p.Price);
            }
        }
    }
    LinqValueCalculator.cs
    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Web;
    
    namespace EssentialTools.Models
    {
        public class Product
        {
            public int ProductID { get; set; }
            public string Name { get; set; }
            public string Description { get; set; }
            public decimal Price { get; set; }
            public string Category { get; set; }
        }
    }
    Product.cs
    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Web;
    
    namespace EssentialTools.Models
    {
        public class ShoppingCart
        {
            IValueCalculator calc;
            public ShoppingCart(IValueCalculator calcParam)
            {
                calc = calcParam;
            }
            public IEnumerable<Product> Products { get; set; }
            public decimal CalculateProductTotal()
            {
                return calc.ValueProducts(Products);
            }
        }
    }
    ShoppingCart.cs

    使用nuget安装Ninject

    工具→库程序包管理器→程序包管理器控制台

    安装ninject内核包:
    install-package Ninject -version 3.0.1.10
    安装ninject内核包的拓展包:
    install-package Ninject.Web.Common -version 3.0.0.7
    对MVC3的引用(在mvc5中仍能用到)
    install-package ninject.mvc3 -version 3.0.0.6

    版本号最好带上,不带版本号,可能会出错!

    安装好了之后NinjectWebCommon.cs文件就会出现。这时候需要为该类中的RegisterServices方法添加代码(注册依赖解析器)

    RegisterServices方法代码如下:

    private static void RegisterServices(IKernel kernel)
            {
                System.Web.Mvc.DependencyResolver.SetResolver(
                    new EssentialTools.Infrastructure.NinjectDependencyResolver(kernel));
            }
    RegisterServices方法代码

    对浏览器发出请求到控制器处理请求这段时间发生的事!

    1、浏览器向MVC框架发送一个请求Home的URL,MVC框架推测出该请求意指Home控制器,于是会创建HomeController类实例。

    2、MVC框架在创建HomeController类实例过程中会发现其构造器有一个对IValueCalculator接口的依赖项,于是会要求依赖项解析器对此依赖项进行解析, 将该接口指定为依赖项解析器中的GetService方法所使用的类型参数。

    3、依赖项解析器会将传递过来的类型参数交给TryGet方法,要求Ninject创建一个新的HomeController接口实例。

    4、Ninect会检测到HomeController构造器与其实现类LilnqValueCalculator具有绑定关系,于是为该接口创建一个LinqValueCalculator类实例,并将其回递给依赖项解析器。

    5、依赖项解析器将Ninject所返回的LilnqValueCalculator类作为IValueCalculator接口实现类实例回递给MVC框架

    6、MVC框架利用依赖项解析器返回的接口类实例创建HomeController控制器实例,并使用该控制器实例对请求进行服务。

    为已经能够正常运行的程序添加功能:为购物车内的东西打折。

    在Models文件夹内添加一个叫做Discount的类

    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Web;
    
    namespace EssentialTools.Models
    {
        public interface IDiscountHelper
        {
            decimal ApplyDiscount(decimal totalParam);
        }
        public class DefaultDiscounter : IDiscountHelper
        {
            public decimal DiscountSize { get; set; }
            public decimal ApplyDiscount(decimal totalParam)
            {
                return (totalParam - (DiscountSize / 100m * totalParam));
            }
        }
    }
    Discount.cs

    这个类里面包涵了一个接口,没有让接口和类进行分离(当然,这不是重点)。

    更改后的计算价格的类LinqValueCalculator

    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Web;
    
    namespace EssentialTools.Models
    {
        public class LinqValueCalculator : IValueCalculator
        {
            private IDiscountHelper discounter;
    
            public LinqValueCalculator(IDiscountHelper discountParam)
            {
                discounter = discountParam;
            }
            public decimal ValueProducts(IEnumerable<Product> products)
            {
                return discounter.ApplyDiscount(products.Sum(p => p.Price));
            }
        }
    }
    LinqValueCalculator.cs

    最后更改依赖项解析器类中的AddBindings方法

    private void AddBindings()
            {
                kernel.Bind<IValueCalculator>().To<LinqValueCalculator>();
                kernel.Bind<IDiscountHelper>().To<DefaultDiscounter>().WithPropertyValue("DiscountSize", 50M);
            }

    在Discount类中,有一个DiscountSize的属性,上面方法中使用了WithPropertyValue方法为这个属性赋了初始值。

  • 相关阅读:
    CSS font-family 字体名称一览表
    jQuery动态追加移除CSS样式
    Java中super关键字的作用与用法
    I Have a Dream(我有一个梦想)
    再读《诫子书》
    世间谤我、欺我、辱我、笑我,为之奈何?
    英语句型:我除了音乐一无所能
    H5 iphoneX适配方案
    对象序列化成字符串,拼接在请求url后面
    React 60s倒计时
  • 原文地址:https://www.cnblogs.com/vichin/p/8595371.html
Copyright © 2011-2022 走看看