在服务层使用 IHttpcontextAccessor 是否合适? 简单的解决方案有用的参考资料

问题描述

我可能在 .net 核心 Web 应用程序中有多个层。所以他们两个是;

  • App.WebApi
  • 应用服务

服务需要检查用户的角色或名称声明。所以我想我可以通过 IHttpcontextAccessor 层的依赖注入来使用 App.Services 接口。我正在使用扩展方法获取如下用户声明。

public static class ClaimsPrincipalExtensions
{
    public static string GetUserEmail(this ClaimsPrincipal principal)
    {
        return principal.FindFirstValue(ClaimTypes.Email);
    }

    public static string GetUserId(this ClaimsPrincipal principal)
    {
        return principal.FindFirstValue(ClaimTypes.NameIdentifier);
    }
}

服务层实现如下

public class ProductService: IProductService {
    IHttpcontextAccessor context;

    public ProductService(IHttpcontextAccessor context){
       context = context;
    }
    ....
    ....
    public IEnumerable<Product> Get(){
        var userRoles = context.HttpContext.User.GetUserEmail();
        ....
    }
}

所以我在服务层使用 IHttpcontextAccessor。但它是 web api 的一部分。这是否适合专业解决方案?或者有什么别的办法?

解决方法

根据我的经验,在 ASP.NET 中,开发人员往往不太担心这些隔离问题(也不担心例如贫血的域)。

在大多数系统中,尤其是较小的系统中,业务逻辑和 API 之间存在很多耦合;例如通过使用过滤器和中间件。

因此,从这个意义上说,它可以被视为“合适的”,只要它不妨碍您满足重要的项目要求,例如能够独立于 API 运行应用程序核心。

但如果您想以一种体面和现代的方式构建您的解决方案,避免做这样的事情是有意义的。

简单的解决方案

一个直接的解决方案是将给定的数据提取到一个单独的“服务”中,并在使用给定服务的层中定义一个接口。然后在WebApi项目中实现接口。

一个很好的例子是 Jason Taylor 的 Clean Architecture Template,其中定义了一个 ICurrentUserService 接口 in the Application layer,具体实现位于 in the WebUI layer

这也使用 IHttpContextAccessor 来提取有关登录用户的信息,因此它似乎是您想要执行的操作的一个很好的示例。

有用的参考资料

我知道在这里链接 YouTube 视频是不习惯的,但您的主要专业领域似乎不是 ASP.NET Core,所以我建议 Jimmy Bogard 的这个 Vertical Slice Architecture 演讲,以及这个 {{3 }} 来自 Jason Taylor 的演讲。他们描述了一种非常现代的 ASP.NET Core 工作方式,可以减轻开发人员以后在项目中遇到的许多结构性问题。当然,这也不是灵丹妙药。对于简单的 CRUD 应用,开销可能不值得。


如果您有其他疑虑或问题,请告诉我,以便我可以使此答案更有用。