首页 星云 工具 资源 星选 资讯 热门工具
:

PDF转图片 完全免费 小红书视频下载 无水印 抖音视频下载 无水印 数字星空

Asp .Net Core 系列:详解授权以及实现角色、策略、自定义三种授权和自定义响应

编程知识
2024年07月26日 22:05

什么是授权(Authorization)?

在 ASP.NET Core 中,授权(Authorization)是控制对应用资源的访问的过程。它决定了哪些用户或用户组可以访问特定的资源或执行特定的操作。授权通常与身份验证(Authentication)一起使用,身份验证是验证用户身份的过程,授权与身份验证相互独立, 但是,授权需要一种身份验证机制。 身份验证是确定用户标识的一个过程。 身份验证可为当前用户创建一个或多个标识。

授权类型

  • 简单授权
  • 基于角色的授权
  • 基于策略的授权

简单的授权

配置身份验证中间件

            //鉴权 (核心源码就是AuthenticationMiddleware中间件)
            app.UseAuthentication();
            //授权
            app.UseAuthorization();

使用授权

ASP.NET Core 中的授权通过 [Authorize] 属性及其各种参数控制。 在其最基本的形式中,通过向控制器、操作或 Razor Page 应用 [Authorize]` 属性,可限制为仅允许经过身份验证的用户访问该组件。
要实现默认的授权行为,你可以简单地在需要限制访问的控制器或操作上使用 [Authorize] 属性,而不必指定任何特定的角色或策略。这样,只有经过身份验证的用户才能访问这些资源。

        [Authorize]
        public IActionResult Info()
        {
            return View();
        }
  • [AllowAnonymous] 绕过授权语句。 如果将 [AllowAnonymous] 和某个 [Authorize] 属性结合使用,系统将忽略 [Authorize] 属性。 例如,如果在控制器级别应用 [AllowAnonymous]
    • 将忽略来自同一控制器上的属性 [Authorize] 或控制器上的操作方法的任何授权要求。
    • 身份验证中间件不会短路,但不需要成功。

授权原理

https://github.com/dotnet/aspnetcore/blob/main/src/Security/Authorization/Core/src/DefaultAuthorizationService.cs

https://github.com/dotnet/aspnetcore/blob/main/src/Security/Authorization/Policy/src/PolicyEvaluator.cs

 static AuthenticateResult DefaultAuthenticateResult(HttpContext context)
        {
            return (context.User?.Identity?.IsAuthenticated ?? false)
                ? AuthenticateResult.Success(new AuthenticationTicket(context.User, "context.User"))
                : AuthenticateResult.NoResult();
        }

基于角色的授权

创建标识时,它可能属于一个或多个角色。 例如,Tracy 可能属于 AdminUser 角色,而 Scott 只属于 User 角色。 如何创建和管理这些角色取决于授权过程的后备存储。

配置身份验证中间件

            //鉴权 (核心源码就是AuthenticationMiddleware中间件)
            app.UseAuthentication();
            //授权
            app.UseAuthorization();

使用授权

仅当用户为 adminuser 角色成员时才可访问 Info

       [Authorize(Roles ="admin,user")]
        public IActionResult Info()
        {
            return View();
        }

基于声明策略的授权

创建标识后,可为其分配一个或多个由受信任方颁发的声明。 声明是一个名称值对,表示使用者是什么,而不是使用者可以做什么。

配置策略

            builder.Services.AddAuthorization(options =>
            {
                options.AddPolicy("AdminPolicy", policyBuilder =>
                {
                    policyBuilder.RequireRole("admin");
                });
            });

使用授权

        [Authorize(Policy = "AdminPolicy")]
        public IActionResult Info()
        {
            return View();
        }

基于自定义策略的授权

在底层,基于角色的授权基于声明的授权均使用要求、要求处理程序和预配置的策略。 这些构建基块支持代码中的授权评估的表达式。 其结果为一个更丰富、可重用且可测试的授权结构。

配置策略

            builder.Services.AddAuthorization(options =>
            {
                options.AddPolicy("PermissionPolicy", policyBuilder =>
                {
                    policyBuilder.Requirements.Add(new PermissionRequirement());
                });
            });

配置授权处理程序

IAuthorizationRequirement 是一项没有方法的标记服务以及用于跟踪授权是否成功的机制。

每个 IAuthorizationHandler 负责检查是否满足要求

    /// <summary>
    /// IAuthorizationRequirement的接口标识
    /// </summary>
    public class PermissionRequirement : IAuthorizationRequirement
    {

    }

    public class PermissionHandler : AuthorizationHandler<PermissionRequirement>
    {
        private readonly IHttpContextAccessor _accessor;
        public PermissionHandler(IHttpContextAccessor accessor)
        {
            _accessor = accessor;
        }
        protected override async Task HandleRequirementAsync(AuthorizationHandlerContext context, PermissionRequirement requirement)
        {
            if (context.User == null || context.User?.Identity?.IsAuthenticated == false)
            {
                //await _accessor.HttpContext.Response.WriteAsJsonAsync(new { code = 401, message = "请先登录" });
                context.Fail();
            }
            else
            {
                var role = context.User.Claims.Where(i => i.Type == ClaimTypes.Role).FirstOrDefault();
                //查数据库
                if (role != null && role.Value == "admin")
                {
                    context.Succeed(requirement);
                }
                else
                {
                    context.Fail();
                }
            }
            await Task.CompletedTask;
        }
    }

使用授权

        [Authorize(Policy= "TestPolicy")]
        public IActionResult Info()
        {
            return View();
        }

自定义响应

应用可以注册 IAuthorizationMiddlewareResultHandler,以自定义 AuthorizationMiddleware 处理授权结果的方式。 应用可将 IAuthorizationMiddlewareResultHandler 用于:

  • 返回自定义的响应。
  • 增强默认质询或禁止响应。
    public class PermissionResultHandler : IAuthorizationMiddlewareResultHandler
    {
        public async Task HandleAsync(RequestDelegate next, HttpContext context, AuthorizationPolicy policy, PolicyAuthorizationResult authorizeResult)
        {
            //var endPoint = context.GetEndpoint();

            //var controllerActionDescriptor = (ControllerActionDescriptor)endPoint.Metadata
            //  .ToList().FirstOrDefault(d => d is ControllerActionDescriptor);

            //var controllerName = controllerActionDescriptor.ControllerName;

            //var actionName = controllerActionDescriptor.ActionName;

            if (!context.User.Identity.IsAuthenticated)
            {
                context.Response.StatusCode = (int)HttpStatusCode.Unauthorized;
                await context.Response.WriteAsync("{\"data\":{\"succeeded\":false,\"code\":401,\"message\":\"登录已过期,请重新登录\"}}");
                return;
            }

            if (!authorizeResult.Succeeded)
            {
                await context.Response.WriteAsync("{\"data\":{\"succeeded\":false,\"code\":403,\"message\":\"您没有权限操作\"}}");
                return;
            }

            await next(context);
        }
    }

image

From:https://www.cnblogs.com/vic-tory/p/18326418
本文地址: http://shuzixingkong.net/article/468
0评论
提交 加载更多评论
其他文章 后端说,单页面SPA和前端路由是怎么回事
没有请求的路由 在传统开发中,浏览器点击一个超链接,就会像后端web服务器发送一个html文档请求,然后页面刷新。但开始单页面开发后,就完全不同了。 单页面?这个概念难以理解。我用一个js作为整个web应用,然后再这个js中操作dom变化,以此来实现页面变化。这不叫单页面吗?这叫!但不完善,因为这种
后端说,单页面SPA和前端路由是怎么回事
矩阵的奇异值分解(SVD)及其应用
该博客针对矩阵的奇异值分解(SVD)展开介绍,主要介绍了奇异值分解的计算及其几何意义,并基于C++编程语言举例说明了SVD分解的一些应用。
矩阵的奇异值分解(SVD)及其应用 矩阵的奇异值分解(SVD)及其应用 矩阵的奇异值分解(SVD)及其应用
微服务:解决复杂业务的妙方
1 微服务介绍 1)什么是微服务 ​ 微服务(Microservices)是一种软件架构风格,它将一个大型应用程序拆分成许多较小的、松散耦合的、独立运行的服务。这些服务通常围绕特定功能或业务领域组织,可以独立开发、部署、扩展和更新。微服务之间通过轻量级的通信协议(如HTTP/REST、消息队列等)相
微服务:解决复杂业务的妙方 微服务:解决复杂业务的妙方 微服务:解决复杂业务的妙方
.NET 控件转图片
Windows应用开发有很多场景需要动态获取控件显示的图像,即控件转图片,用于其它界面的显示、传输图片数据流、保存为本地图片等用途。 下面分别介绍下一些实现方式以及主要使用场景 RenderTargetBitmap 控件转图片BitmapImage/BitmapSource,在WPF中可以使用Ren
.NET 控件转图片 .NET 控件转图片
通过Jupyter Notebook+OpenAI+ollama简单的调用本地模型
通过Jupyter Notebook+OpenAI+ollama简单的调用本地模型 起因是收到了ollama的邮件,貌似支持使用openai来调用本地的ollama下载的模型为自己用 想了下正好试下,因为这几天正好在尝试用Jupyter Notebook来写点调用api的方式来使用大语言模型,看看后
通过Jupyter Notebook+OpenAI+ollama简单的调用本地模型 通过Jupyter Notebook+OpenAI+ollama简单的调用本地模型 通过Jupyter Notebook+OpenAI+ollama简单的调用本地模型
提高 C# 的生产力:C# 13 更新完全指南
前言 预计在 2024 年 11 月,C# 13 将与 .NET 9 一起正式发布。今年的 C# 更新主要集中在 ref struct 上进行了许多改进,并添加了许多有助于进一步提高生产力的便利功能。 本文将介绍预计将在 C# 13 中添加的功能。 注意:目前 C# 13 还未正式发布,因此以下内容
浅谈 I/O 与 I/O 多路复用
1.基础知识 网络编程里常听到阻塞IO、非阻塞IO、同步IO、异步IO等概念,总听别人聊不如自己下来钻研一下。不过,搞清楚这些概念之前,还得先回顾一些基础的概念。 下面说的都是Linux环境下,跟Windows环境不一样哈&#183;☺。 1.1 用户空间和内核空间 现在操作系统都采用虚拟寻址,处理
浅谈 I/O 与 I/O 多路复用 浅谈 I/O 与 I/O 多路复用 浅谈 I/O 与 I/O 多路复用
解锁 SQL Server 2022的时间序列数据功能
解锁 SQL Server 2022的时间序列数据功能 SQL Server2022在处理时间序列数据时,SQL Server 提供了一些优化和功能,比如 DATE_BUCKET 函数、窗口函数(如 FIRST_VALUE 和 LAST_VALUE)以及其他时间日期函数,以便更高效地处理时间序列数据
解锁 SQL Server 2022的时间序列数据功能 解锁 SQL Server 2022的时间序列数据功能 解锁 SQL Server 2022的时间序列数据功能