【问题标题】:Filter constructor injection using Ninject使用 Ninject 过滤构造函数注入
【发布时间】:2013-09-25 20:24:47
【问题描述】:

我正在尝试找到一种方法来使用 Ninject 将构造函数依赖项注入过滤器。我发现许多描述属性注入的文章现在不建议使用,但其余文章涉及使用工厂、定位器、全局包装器或存根属性的复杂设置。

有了 MVC,您几乎可以覆盖其操作的任何部分

现在允许注入的正确方法是什么,或者如果您使用某些类型的过滤器与其他过滤器相比,它会变得更容易吗?

 public class UserValidationAttribute : ActionFilterAttribute
 {
    private IRepository repository;

    public UserValidationAttribute(IRepository repository)
    {
        this.repository = repository;
    }
}

【问题讨论】:

  • 请注意 - 普遍的共识似乎是属性注入应该用于可选依赖项,但构造函数注入用于必需的依赖项(哪种有意义 - 没有它就无法构造类型所需的依赖项,但可能不会根据容器可用的服务来注入属性)
  • 我现在已经实现了一个方法,你有一个全局过滤器,它通过查看是否存在令牌属性来检查它是否适用。目前我没有得到的是,当我在操作上使用令牌属性并使用filterContext.ActionDescriptor.IsDefined(typeof(MyTokenAttribute), true) 时,我得到true,但如果我只将令牌属性放在控制器上,我得到false。跨度>

标签: c# asp.net-mvc ninject


【解决方案1】:

有一种方法可以使用构造函数注入。

首先,您将属性替换为“空”属性,您将仅将其用作标记

public class UserValidationAttribute : Attribute { }

然后你创建一个过滤器类作为IActionFilter

public class UserValidationFilter : IActionFilter
{
    private readonly IRepository repository;

    public UserValidationFilter(IRepository repository)
    {
        this.repository = repository;
    }

    public void OnActionExecuting(ActionExecutingContext filterContext)
    {
        //do something
    }

    public void OnActionExecuted(ActionExecutedContext filterContext)
    {
        //do something
    }      
}

然后你可以用类似的东西注册它

private static void RegisterServices(IKernel kernel)
{
    kernel.BindFilter<UserValidationFilter>(FilterScope.Action, 0)
        .WhenActionMethodHas<UserValidationAttribute>();
}

如果你的属性本身有构造函数参数,你可以像传递一样

kernel.BindFilter<UserValidationFilter>(FilterScope.Action, 0)
    .WhenActionMethodHas<UserValidationAttribute>();
    .WithConstructorArgumentFromActionAttribute<UserValidationAttribute>("myParameter", attr => attr.MyParameter);

BindFilter 语法是 Ninject.Web.Mvc.FilterBindingSyntax 的一部分。

【讨论】:

    【解决方案2】:

    假设属性是元数据的一部分,这意味着它应该在编译时被实例化,任何ioc都不可能将存储库注入到属性中容器。容器在运行时运行。

    【讨论】:

      【解决方案3】:

      如果要将依赖项注入文件管理器,则需要使用属性注入而不是构造函数注入。

      public class UserValidationAttribute : ActionFilterAttribute
      {
          [Inject]
          private IRepository repository { get; set; }
      
          public UserValidationAttribute()
          {
          }
      }
      

      https://stackoverflow.com/a/7192754/296861

      【讨论】:

      • 他的依赖是一个似乎是必需的存储库,所以它应该通过构造函数注入。另外,我觉得在你的类中添加你的 IoC 魔法属性是一种糟糕的模式。目前大多数 IoC 容器都支持注入 MVC 过滤器,包括 Ninject、Unity v3 和 StructureMap
      猜你喜欢
      • 2023-03-07
      • 2018-03-27
      • 2012-02-27
      • 1970-01-01
      • 2017-02-23
      • 2012-06-19
      • 1970-01-01
      • 2011-08-29
      • 1970-01-01
      相关资源
      最近更新 更多