热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

如何在.NetCoreActionFilterAttribute中使用依赖注入?

如何解决《如何在.NetCoreActionFilterAttribute中使用依赖注入?》经验,为你挑选了2个好方法。

AuthenticationRequiredAttribute类

public class AuthenticationRequiredAttribute : ActionFilterAttribute
{
    ILoginTokenKeyApi _loginTokenKeyApi;
    IMemoryCache _memoryCache;

    public AuthenticationRequiredAttribute(IMemoryCache memoryCache)
    {
        _memoryCache = memoryCache;

        _loginTokenKeyApi = new LoginTokenKeyController(new UnitOfWork());
    }

    public override void OnActionExecuting(ActionExecutingContext filterContext)
    {
        var memory = _memoryCache.Get(Constants.KEYNAME_FOR_AUTHENTICATED_PAGES);

        string requestedPath = filterContext.HttpContext.Request.Path;

        string tokenKey = filterContext.HttpContext.Session.GetString("TokenKey")?.ToString();

        bool? isLoggedIn = _loginTokenKeyApi.IsLoggedInByTokenKey(tokenKey).Data;

        if (isLoggedIn == null ||
            !((bool)isLoggedIn) ||
            !Constants.AUTHENTICATED_PAGES_FOR_NORMAL_USERS.Contains(requestedPath))
        {
            filterContext.Result = new JsonResult(new { HttpStatusCode.Unauthorized });
        }
    }
    public override void OnActionExecuted(ActionExecutedContext filterContext)
    {
    }
}

HomeController的

public class HomeController : Controller
{
    IUserApi _userApi;
    ILoginTokenKeyApi _loginTokenKey;
    IMemoryCache _memoryCache;

    public HomeController(IUserApi userApi, ILoginTokenKeyApi loginTokenKey, IMemoryCache memoryCache)
    {
        _loginTokenKey = loginTokenKey;
        _userApi = userApi;

        _memoryCache = memoryCache;
    }

    [AuthenticationRequired] // There is AN ERROR !!
    public IActionResult Example()
    {
        return View();
    }
}

错误:

错误CS7036没有给出的参数对应于'AuthenticationRequiredAttribute.AuthenticationRequiredAttribute(IMemoryCache)'Project.Ground.WebUI所需的形式参数'memoryCache'

我的问题实际上是:我不能在属性类中使用依赖注入.

我想在没有任何参数的情况下使用该属性.有什么解决方案可以解决吗?我使用依赖注入,但它不能用于属性.我该怎么用呢?



1> poke..:

根据文档,您可以在此处选择一些选项:

如果您的过滤器具有您需要从DI访问的依赖项,则有几种支持的方法.您可以使用以下方法之一将过滤器应用于类或操作方法:

ServiceFilterAttribute

TypeFilterAttribute

IFilterFactory 在您的属性上实现

ServiceFilter或TypeFilter属性

如果您只是想让它快速运行,您可以使用前两个选项之一将过滤器应用于控制器或控制器操作.执行此操作时,您的过滤器不需要是属性本身:

[TypeFilter(typeof(ExampleActionFilter))]
public IActionResult Example()
    => View();

然后ExampleActionFilter可以只实现eg IAsyncActionFilter,你可以使用构造函数注入直接依赖于事物:

public class ExampleActionFilter : IAsyncActionFilter
{
    private readonly IMemoryCache _memoryCache;
    public ExampleActionFilter(IMemoryCache memoryCache)
    {
        _memoryCache = memoryCache;
    }

    public async Task OnActionExecutionAsync(ActionExecutingContext context, ActionExecutionDelegate next)
    { … }
}

您也可以使用该[ServiceFilter]属性来获得相同的效果,但是您还需要在您ExampleActionFilter的注册表中注册依赖注入容器Startup.

过滤工厂

如果您需要更多灵活性,可以实施自己的过滤器工厂.这允许您编写工厂代码以自己创建实际的过滤器实例.上述可能的实现ExampleActionFilter可能如下所示:

[AttributeUsage(AttributeTargets.Class | AttributeTargets.Method)]
public class ExampleActionFilterAttribute : Attribute, IFilterFactory
{
    public bool IsReusable => false;

    public IFilterMetadata CreateInstance(IServiceProvider serviceProvider)
    {
        return serviceProvider.GetService();
    }
}

然后,您可以使用该[ExampleActionFilter]属性使MVC框架ExampleActionFilter使用DI容器为您创建一个实例.

请注意,此实现与基本相同ServiceFilterAttribute.只是自己实现它避免了必须ServiceFilterAttribute直接使用它并允许你拥有自己的属性.

使用服务定位器

最后,还有另一个快速选项,可以让您完全避免构造函数注入.当您的过滤器实际运行时,它使用服务定位器模式动态地解析服务.因此,不是直接注入依赖项并使用它,而是从上下文中显式检索它:

public class ExampleActionFilter : ActionFilterAttribute
{
    public async Task OnActionExecutionAsync(ActionExecutingContext context, ActionExecutionDelegate next)
    {
        var memoryCache = context.HttpContext.RequestServices.GetService();

        // …
    }
}



2> spender..:

除了在构造上解决问题外,ActionExecutingContext.HttpContext.RequestServices还应在请求时为您提供对请求服务容器的引用。

所以:

public override void OnActionExecuting(ActionExecutingContext filterContext)
{
    var svc = filterContext.HttpContext.RequestServices;
    var memCache = svc.GetService();
    //..etc


推荐阅读
  • iOS Swift中如何实现自动登录?
    本文介绍了在iOS Swift中如何实现自动登录的方法,包括使用故事板、SWRevealViewController等技术,以及解决用户注销后重新登录自动跳转到主页的问题。 ... [详细]
  • 在Android开发中,使用Picasso库可以实现对网络图片的等比例缩放。本文介绍了使用Picasso库进行图片缩放的方法,并提供了具体的代码实现。通过获取图片的宽高,计算目标宽度和高度,并创建新图实现等比例缩放。 ... [详细]
  • 本文讨论了如何在不使用SearchBar display controller的情况下,单独使用SearchBar并捕获其textChange事件。作者介绍了实际状况,即左侧SliderMenu中的SearchBar需要在主页TableView中显示搜索结果。然后,作者提供了解决方案和步骤,帮助读者实现这一功能。 ... [详细]
  • Todayatworksomeonetriedtoconvincemethat:今天在工作中有人试图说服我:{$obj->getTableInfo()}isfine ... [详细]
  • Asp.net Mvc Framework 七 (Filter及其执行顺序) 的应用示例
    本文介绍了在Asp.net Mvc中应用Filter功能进行登录判断、用户权限控制、输出缓存、防盗链、防蜘蛛、本地化设置等操作的示例,并解释了Filter的执行顺序。通过示例代码,详细说明了如何使用Filter来实现这些功能。 ... [详细]
  • 本文介绍了ASP.NET Core MVC的入门及基础使用教程,根据微软的文档学习,建议阅读英文文档以便更好理解,微软的工具化使用方便且开发速度快。通过vs2017新建项目,可以创建一个基础的ASP.NET网站,也可以实现动态网站开发。ASP.NET MVC框架及其工具简化了开发过程,包括建立业务的数据模型和控制器等步骤。 ... [详细]
  • 本文介绍了在C#中SByte类型的GetHashCode方法,该方法用于获取当前SByte实例的HashCode。给出了该方法的语法和返回值,并提供了一个示例程序演示了该方法的使用。 ... [详细]
  • 向QTextEdit拖放文件的方法及实现步骤
    本文介绍了在使用QTextEdit时如何实现拖放文件的功能,包括相关的方法和实现步骤。通过重写dragEnterEvent和dropEvent函数,并结合QMimeData和QUrl等类,可以轻松实现向QTextEdit拖放文件的功能。详细的代码实现和说明可以参考本文提供的示例代码。 ... [详细]
  • Linux重启网络命令实例及关机和重启示例教程
    本文介绍了Linux系统中重启网络命令的实例,以及使用不同方式关机和重启系统的示例教程。包括使用图形界面和控制台访问系统的方法,以及使用shutdown命令进行系统关机和重启的句法和用法。 ... [详细]
  • 后台获取视图对应的字符串
    1.帮助类后台获取视图对应的字符串publicclassViewHelper{将View输出为字符串(注:不会执行对应的ac ... [详细]
  • Google Play推出全新的应用内评价API,帮助开发者获取更多优质用户反馈。用户每天在Google Play上发表数百万条评论,这有助于开发者了解用户喜好和改进需求。开发者可以选择在适当的时间请求用户撰写评论,以获得全面而有用的反馈。全新应用内评价功能让用户无需返回应用详情页面即可发表评论,提升用户体验。 ... [详细]
  • 在springmvc框架中,前台ajax调用方法,对图片批量下载,如何弹出提示保存位置选框?Controller方法 ... [详细]
  • 海马s5近光灯能否直接更换为H7?
    本文主要介绍了海马s5车型的近光灯是否可以直接更换为H7灯泡,并提供了完整的教程下载地址。此外,还详细讲解了DSP功能函数中的数据拷贝、数据填充和浮点数转换为定点数的相关内容。 ... [详细]
  • ScrollView嵌套Collectionview无痕衔接四向滚动,支持自定义TitleView
    本文介绍了如何实现ScrollView嵌套Collectionview无痕衔接四向滚动,并支持自定义TitleView。通过使用MainScrollView作为最底层,headView作为上部分,TitleView作为中间部分,Collectionview作为下面部分,实现了滚动效果。同时还介绍了使用runtime拦截_notifyDidScroll方法来实现滚动代理的方法。具体实现代码可以在github地址中找到。 ... [详细]
  • IOS开发之短信发送与拨打电话的方法详解
    本文详细介绍了在IOS开发中实现短信发送和拨打电话的两种方式,一种是使用系统底层发送,虽然无法自定义短信内容和返回原应用,但是简单方便;另一种是使用第三方框架发送,需要导入MessageUI头文件,并遵守MFMessageComposeViewControllerDelegate协议,可以实现自定义短信内容和返回原应用的功能。 ... [详细]
author-avatar
多多之爱
这个家伙很懒,什么也没留下!
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有