zoukankan      html  css  js  c++  java
  • (原)NET CORE3.1自定义JWT授权验证

    原文链接地址:https://www.cnblogs.com/ruyun/p/12134290.html
    

    登录获取JWT

        [ApiController]
        public class LoginController : ControllerBase
        {
            private readonly IOptions<JwtOption> options;
    
        public LoginController(IOptions&lt;JwtOption&gt; options)
        {
            this.options = options;
        }
    
        [HttpGet("/login")]
        [AllowAnonymous]
        public IActionResult Login([FromQuery]string username)
        {
            string roleType = username == "admin" ? "Administrator" : "Other";
    
            var claims = new Claim[]
            {
                new Claim("Role",roleType),
            };
            var token = new JwtToken(options.Value).GenerateToken(claims);
            return Ok(token);
        }
    }
    

    在初始控制器WeatherForecastController中Get上添加[Authorize]

    自定义token的生成帮助类

        public class JwtToken
        {
            private readonly byte[] secret;
            private readonly string audience;
            private readonly string issuer;
            private readonly int expiresMinute;
    
        public JwtToken(JwtOption options)
        {
            secret = Encoding.ASCII.GetBytes(options.Secret);
            audience = options.Audience;
            issuer = options.Issuer;
            expiresMinute = options.ExpirationMinutes;
        }
        ///生成JWT
        public JwtResult GenerateToken(Claim[] claims)
        {
            var authTime = DateTime.UtcNow;
            var expiresAt = authTime.AddMinutes(expiresMinute);
    
            var tokenDescriptor = new SecurityTokenDescriptor
            {
                Audience = audience,
                Issuer = issuer,
                Subject = new ClaimsIdentity(claims),
                Expires = expiresAt,
                SigningCredentials = new SigningCredentials(
                    new SymmetricSecurityKey(secret), SecurityAlgorithms.HmacSha256Signature)
            };
            var tokenHandler = new JwtSecurityTokenHandler();
            var token = tokenHandler.CreateToken(tokenDescriptor);
            var tokenString = tokenHandler.WriteToken(token);
            return new JwtResult
            {
                access_token = tokenString,
                token_type = "Bearer",
                auth_time = new DateTimeOffset(authTime).ToUnixTimeSeconds(),
                expires_at = new DateTimeOffset(expiresAt).ToUnixTimeSeconds()
            };
        }
    }
    public class JwtResult
    {
        /// &lt;summary&gt;
        /// access token
        /// &lt;/summary&gt;
        public string access_token { get; set; }
        /// &lt;summary&gt;
        /// token type
        /// &lt;/summary&gt;
        public string token_type { get; set; }
        /// &lt;summary&gt;
        /// 授权时间
        /// &lt;/summary&gt;
        public long auth_time { get; set; }
        /// &lt;summary&gt;
        /// 过期时间
        /// &lt;/summary&gt;
        public long expires_at { get; set; }
    }
        public class JwtOption
    {
        public string Secret { get; set; }
        public string Issuer { get; set; }
        public string Audience { get; set; }
        public int ExpirationMinutes { get; set; }
    }
    

    在Appsettings中添加

      "Authorization": {
        "Secret": "qtiOLpT7mJQx239e2kgMheAH7B9lGQJnoxYRCb7KX3x1ogDEd55I7dJ1ziYptiTF",
        "Issuer": "https://www.cnblogs.com/ruyun/",
        "Audience": "https://www.cnblogs.com/ruyun/",
        "ExpirationMinutes": "2000"
      }
    

    自定义授权类

        public class PermissionRequirement : IAuthorizationRequirement
        {
            public string PermissionName { get; }
    
        public PermissionRequirement(string PermissionName)
        {
            this.PermissionName = PermissionName;
        }
    }
    public class PermissionRequirementHandler : AuthorizationHandler&lt;PermissionRequirement&gt;
    {
        private readonly IHttpContextAccessor httpContextAccessor;
    
        public PermissionRequirementHandler(IHttpContextAccessor httpContextAccessor)
        {
            this.httpContextAccessor = httpContextAccessor;
        }
    
        protected override async Task HandleRequirementAsync(AuthorizationHandlerContext context, PermissionRequirement requirement)
        {
            var result = await httpContextAccessor.HttpContext.AuthenticateAsync(JwtBearerDefaults.AuthenticationScheme);
            if (!result.Succeeded)
            {
                context.Fail();
                return;
            }
            httpContextAccessor.HttpContext.User = result.Principal;
            var role = httpContextAccessor.HttpContext.User.FindFirst(c =&gt; c.Type == "Role");
    
            if (role != null)
            {
                var roleValue = role.Value;
                var permissions = RolePermissionCache.GetPermissions(role.Value);
                if (permissions.Contains(requirement.PermissionName))
                {
                    context.Succeed(requirement);
                }
            }
            return;
        }
    }
    
    //权限动态缓存类 临时替代数据库
    public class RolePermissionCache
    {
        //实际在数据库获取与配置
        public static List&lt;string&gt; GetPermissions(string role)
        {
            switch (role)
            {
                case "Administrator":
                    return new List&lt;string&gt;() { "Index", "CustomPermission" };
                case "Custom":
                    return new List&lt;string&gt;() { "Index" };
            }
            return new List&lt;string&gt;();
        }
    }
    internal class PermissionPolicyProvider : IAuthorizationPolicyProvider
    {
        //这里默认使用自定义的授权模式
        public Task&lt;AuthorizationPolicy&gt; GetDefaultPolicyAsync()
        {
            var policy = new AuthorizationPolicyBuilder();
            policy.AddRequirements(new PermissionRequirement("CustomPermission"));
            return Task.FromResult(policy.Build());
        }
    
        public Task&lt;AuthorizationPolicy&gt; GetFallbackPolicyAsync()
        {
            return Task.FromResult(new AuthorizationPolicyBuilder().RequireAuthenticatedUser().Build());
        }
    
        public Task&lt;AuthorizationPolicy&gt; GetPolicyAsync(string policyName)
        {
            var policy = new AuthorizationPolicyBuilder();
            policy.AddRequirements(new PermissionRequirement(policyName));
            return Task.FromResult(policy.Build());
        }
    }
    

  • 相关阅读:
    linux 查看磁盘空间大小
    linux查看防火墙状态及开启关闭命令
    运行安装mysql 报错 [root@localhost mysql-mult]# ./scripts/mysql_install_db  --defaults-file=conf/3306my.cnf FATAL ERROR: please install the following Perl modules before executing ./scripts/mysql_install_
    linux lsof命令详解
    centos6下无法使用lsof命令"-bash: lsof: command not found"
    服务器创建好后怎样使用远程连接工具链接的一些问题
    mysql在linux下的安装
    jmeter-linux下运行
    【WPF】一组CheckBox的全选/全不选功能
    【WPF】TabControl垂直分页栏/选项卡
  • 原文地址:https://www.cnblogs.com/ruyun/p/12134290.html
Copyright © 2011-2022 走看看