【问题标题】:Ninject not binding object in BaseController in MVC3Ninject 未绑定 MVC3 中 BaseController 中的对象
【发布时间】:2010-11-10 20:33:11
【问题描述】:

我刚刚将我的 MVC2 项目升级到 MVC3 并使用 NuGet 库包引用来安装 ninject。这创建了一个 appstart 类,我使用以下代码注入了我的 IMembershipService 类。

public static void RegisterServices(IKernel kernel) {
        kernel.Bind<IMembershipService>().To<AccountMembershipService>();
    }

例如,这对我的 HomeController 非常有效。

public class HomeController : Controller
{
    public IMembershipService MembershipService { get; set; }

    public HomeController() : this(null) { }

    public HomeController(IMembershipService service)
    {
        MembershipService = service;
    }

但是,我使用的是 BaseController。基类中几乎相同的代码不再起作用。

public class BaseController : Controller
{
    public IMembershipService MembershipService { get; set; }
    public UserService UserService { get; set; }

    public BaseController() : this(null, null) { }

    public BaseController(IMembershipService service, UserService userService)
    {
        MembershipService = service;
        UserService = userService ?? new UserService();
    }

如果我中断基本控制器的构造函数,服务只是 NULL。我从未将 Ninject 用于 IOC,所以答案可能很明显,但为什么它不会像我想要的那样将我的 AccountMembershipController 注入基类?我看不出有什么不同,尽管我意识到额外的继承级别可能会以某种方式与 Ninject 混淆。

【问题讨论】:

    标签: asp.net-mvc ninject nuget


    【解决方案1】:

    您的 HomeController 来自 Controller,而不是 BaseController?此外,您有一个 BaseController 的默认构造函数,它将事物设置为 null。为什么你有这个?我将从摆脱那些默认构造函数开始。您不需要任何默认构造函数。

    【讨论】:

    • 我有默认的构造函数只是因为默认的单元测试项目没有它们就崩溃了。但是我尝试了有无,它似乎没有任何区别。在我将成员服务移至基类之后,HomeController 确实从 BaseController 派生。那是它破裂的时候。
    • 实际上,更准确地说,子控制器要求基本控制器中的默认构造函数。没有它就无法编译。 (尽管内置单元测试需要 HomeController 中的默认构造函数。)顺便说一句,你的 PDC 谈话让我陷入了困境。 (开玩笑……很棒的演示,绝对说服我进行升级。)
    【解决方案2】:

    我自己也遇到了同样的问题。假设您的代码如下所示:

    public HomeController : BaseController
    {
    
    }
    
    public BaseController : Controller
    {
        public IMembershipService MembershipService { get; set; }
    
        public MembershipService() { }
    
        public MembershipService(IMembershipService service)
        {
            MembershipService = service;
        }
    }
    

    出于某种原因,Ninject 认为HomeController 只有一个构造函数,即默认的无参数构造函数。当您将所有内容放入HomeController 时,它可以找到可注入构造函数,但将其分解到基类中,并且由于某种原因,它不会在基类中查看是否有任何重载的构造函数。对此有两个修复:

    1. 删除默认构造函数。这是我首选的解决方案,因为它强制注入构造函数(就像在单元测试时手动创建控制器时一样),但缺点是您必须在所有子类中实现构造函数。
    2. 保留默认构造函数,但将[Inject] 属性添加到所有可注入属性:

      public BaseController : Controller
      {
          [Inject] public IMembershipService MembershipService { get;set; }
          // rest is the same
      }
      

    Ninject 会以这种方式正确注入属性,但请注意 Ninject 将调用无参数构造函数。

    【讨论】:

    • 所以你基本上在每个子类中都这样做?公共 HomeController(IMembershipService 服务) : base(service) { }
    • 有趣,如果你有很多服务和控制器,这可能会有点草率,我可能暂时放弃 Ninject,或者使用不同的容器。谢谢。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-05-23
    • 1970-01-01
    相关资源
    最近更新 更多