当前位置: 首页 > news >正文

【框架】参考 Spring Security 安全框架设计出,轻量化高可扩展的身份认证与授权架构

关键字:AOP、JWT、自定义注解、责任链模式

一、Spring Security

Spring Security 想必大家并不陌生,是 Spring 家族里的一个安全框架,特别完善,但学习成本比较大,不少开发者都觉得,这个框架“很重”

他的认证授权的过程时使用的 api 和组件比较复杂,但这不是主要的顾虑

并且,他是基于过滤器实现的,其过程抛出的异常并不会被全局异常处理器拦截,通过 SpringSecurity 认证授权的请求,才算进入我们的 Spring 环境下

但不得不说他确实有优点

  1. 对请求的一个 AOP 的统一处理(但是好像没有专门的后置处理器)
  2. 可以通过添加过滤器的方式增加认证过程,也对某些路由可添加授权过程
  3. 框架的一些注解,例如 @PreAuthorize,可以很方便的进行接口权限的设置

虽然它封装了很多现成的东西,但其实一些自己去写也没什么大不了的,还可以按照自己的想法去定制

我们可以学习它的优点去优化一下我们原本的认证授权架构

二、AOP + JWT

通过全局拦截器,拦截所有的请求,请求携带访问令牌 JWT,这里就不必多说了

三、自定义注解

自定义一个可以 Retention 为 Runtime,Target 为 TYPE 或 METHOD 的注解:

  1. 允许访问的角色
  2. 是否需要认证
  3. 是否需要授权

标注在 Controller 类才有用,若加在类上,则作用于所有方法,若标注在方法上,则以方法上的为准

意为此接口的拦截参数

/*** Created With Intellij IDEA* User: 马拉圈* Date: 2024-08-08* Time: 12:50* <br />* permit: 用户必须是列表中的角色才能访问 <br />* authenticate: 用户需不需要通过认证 <br />* authorize: 用户需不需要通过授权 <br />* 注意: <br />* permit 若为 {},则代表谁都不能访问,除非 authorize 为 false <br />* 1. 不需要认证、不需要授权 ✅ <br />* 2. 需要认证、需要授权 ✅ <br />* 3. 需要认证、不需要授权 ✅ <br />* 4. 不需要认证、需要授权 ❌(必然失败) <br />*/
@Documented
@Target({ElementType.TYPE, ElementType.METHOD})
@Retention(RetentionPolicy.RUNTIME)
public @interface Intercept {UserType[] permit() default {UserType.NORMAL_USER, UserType.MANAGER};boolean authenticate() default true; // 默认需要认证boolean authorize() default true; // 默认需要授权}
@Slf4j
public class InterceptHelper {public static Intercept getIntercept(Class<?> clazz) {// 类上的 Intercept 为初步结果return clazz.isAnnotationPresent(Intercept.class) ? clazz.getAnnotation(Intercept.class) : null;}public static Intercept getIntercept(Method targetMethod) {// 获取目标方法所在的类Class<?> declaringClass = targetMethod.getDeclaringClass();// 类上的 Intercept 为初步结果Intercept intercept = getIntercept(declaringClass);// 方法上的 Intercept 为最终结果return targetMethod.isAnnotationPresent(Intercept.class) ? targetMethod.getAnnotation(Intercept.class) : intercept;}}

四、责任链模式

责任链:

  1. 抽象处理者
  2. 具体处理者
  3. 客户端(我习惯是责任链的链头)

设计出以下架构:

  1. 前置初始化链
    1. 初始化日志变量、设置请求 id、请求 uri、请求方法,便于全链路追踪
    2. 根据配置文件对特定接口设置的拦截参数,判断当前请求的接口是否被设置了特殊的拦截参数
    3. 请求的接口如果存在目标方法,则判断其方法上或者类上是否存在 @Intercept 注解,若存在则初始化拦截参数

若不存在拦截参数,则代表该资源没有被开发者专门进行拦截的管理,直接返回错误:api 访问失败

  1. 前置认证链
    1. 是否忽略,若 authenticate 参数为 false,则直接忽略
    2. 若认证未成功且未获取 jwt,则尝试从 header 里获取 jwt
    3. 若认证未成功且未获取 jwt,则此时从 queryString 里获取 jwt
    4. 若认证未成功,则解析 jwt,若成功解析出用户信息,则存储到本地线程变量里(若令牌即将过期,则返回一个新的 jwt)

若未认证成功,则返回错误:认证失败

  1. 前置授权链
    1. 是否武略
    2. 是否强制拦截
    3. 若未授权成功,则获取当前用户的角色,判断是否存在于拦截参数的允许访问的角色列表,若存在则授权成功

若未授权成功,则返回错误:授权失败

  1. 后置链
    1. 清除日志变量、本地线程变量

在这里插入图片描述

在我们的架构中而一个责任链节点应该包含:

  1. 拦截的路由
  2. 执行的前置条件
  3. 执行的代码

具体代码参考:OKR-System4.0/src/main/java/cn/bitterfree/api/interceptor at main · CarefreeState/OKR-System4.0

相关文章:

【框架】参考 Spring Security 安全框架设计出,轻量化高可扩展的身份认证与授权架构

关键字&#xff1a;AOP、JWT、自定义注解、责任链模式 一、Spring Security Spring Security 想必大家并不陌生&#xff0c;是 Spring 家族里的一个安全框架&#xff0c;特别完善&#xff0c;但学习成本比较大&#xff0c;不少开发者都觉得&#xff0c;这个框架“很重” 他的…...

【Git 学习笔记_27】DIY 实战篇:利用 DeepSeek 实现 GitHub 的 GPG 密钥创建与配置

文章目录 1 前言2 准备工作3 具体配置过程3.1. 本地生成 GPG 密钥3.2. 导出 GPG 密钥3.3. 将密钥配置到 Git 中3.4. 测试提交 4 问题排查记录5 小结与复盘 1 前言 昨天在更新我的第二个 Vim 专栏《Mastering Vim (2nd Ed.)》时遇到一个经典的 Git 操作问题&#xff1a;如何在 …...

微信小程序地图map全方位解析

微信小程序地图map全方位解析 微信小程序的 <map> 组件是一个功能强大的工具&#xff0c;可以实现地图展示、定位、标注、路径规划等多种功能。以下是全方位解析微信小程序地图组件的知识点&#xff1a; 一、地图组件基础 1. 引入 <map> 组件 在页面的 .wxml 文…...

调试无痛入手

在调试过程中&#xff0c;Step In、Step Over 和 Step Out 是控制代码执行流程的常用操作&#xff0c;帮助开发者逐行或逐块检查代码行为。以下是它们的详细介绍及使用方法&#xff1a; 1. Step In 功能&#xff1a;进入当前行的函数或方法内部&#xff0c;逐行执行其代码。使…...

【蓝桥杯集训·每日一题2025】 AcWing 6135. 奶牛体检 python

6135. 奶牛体检 Week 1 2月21日 农夫约翰的 N N N 头奶牛站成一行&#xff0c;奶牛 1 1 1 在队伍的最前面&#xff0c;奶牛 N N N 在队伍的最后面。 农夫约翰的奶牛也有许多不同的品种。 他用从 1 1 1 到 N N N 的整数来表示每一品种。 队伍从前到后第 i i i 头奶牛的…...

AI发展迅速,是否还有学习前端的必要性?

今天有个小伙伴跟我讨论&#xff1a;“现在 AI 发展迅速&#xff0c;是否还有学习 JS 或者 TS 及前端知识的必要&#xff1f;” 我非常肯定地说&#xff1a; 是的&#xff0c;学习 JavaScript/TypeScript 以及前端知识仍然非常必要&#xff0c;而且在可预见的未来&#xff0c;…...

【数据标准】数据标准化是数据治理的基础

导读&#xff1a;数据标准化是数据治理的基石&#xff0c;它通过统一数据格式、编码、命名与语义等&#xff0c;全方位提升数据质量&#xff0c;确保准确性、完整性与一致性&#xff0c;从源头上杜绝错误与冲突。这不仅打破部门及系统间的数据壁垒&#xff0c;极大促进数据共享…...

VS2022配置FFMPEG库基础教程

1 简介 1.1 起源与发展历程 FFmpeg诞生于2000年&#xff0c;由法国工程师Fabrice Bellard主导开发&#xff0c;其名称源自"Fast Forward MPEG"&#xff0c;初期定位为多媒体编解码工具。2004年后由Michael Niedermayer接任维护&#xff0c;逐步发展成为包含音视频采…...

three.js之特殊材质效果

*案例42 创建一个透明的立方体 <template><div ref"container" className"container"></div> </template><script setup> import * as THREE from three; import WebGL from three/examples/jsm/capabilities/WebGL.js // 引…...

Qt常用控件之日历QCalendarWidget

日历QCalendarWidget QCalendarWidget 是一个日历控件。 QCalendarWidget属性 属性说明selectDate当前选中日期。minimumDate最小日期。maximumDate最大日期。firstDayOfWeek设置每周的第一天是周几&#xff08;影响日历的第一列是周几&#xff09;。gridVisible是否显示日历…...

vxe-table 如何实现跟 Excel 一样的数值或金额的负数自动显示红色字体

vxe-table 如何实现跟 Excel 一样的数值或金额的负数自动显示红色字体&#xff0c;当输入的值为负数时&#xff0c;会自动显示红色字体&#xff0c;对于数值或者金额输入时该功能就非常有用了。 查看官网&#xff1a;https://vxetable.cn gitbub&#xff1a;https://github.co…...

DINOv2 + yolov8 + opencv 检测卡车的可拉拽雨覆是否完全覆盖

最近是接了一个需求咨询图像处理类的&#xff0c;甲方要在卡车过磅的地方装一个摄像头用检测卡车的车斗雨覆是否完全&#xff0c; 让我大致理了下需求并对技术核心做下预研究 开发一套图像处理软件&#xff0c;能够实时监控经过的卡车并判断其车斗的雨覆状态。 系统需具备以下…...

算法日记27:完全背包(DFS->记忆化搜索->倒叙DP->顺序DP->空间优化)

一、暴力搜索&#xff08;DFS&#xff09; O ( n 2 ) O(n^2) O(n2) 1.1&#xff09;思路解析 1、注意和01背包的区别在于每个物品可以无限次选择 注意在完全背包中&#xff0c;当一个物品被选择过一次&#xff0c;我们仍然需要考虑是否继续选择这个物品 01背包&#xff1a; …...

Linux 命令大全完整版(14)

5. 文件管理命令 chgrp(change group) 功能说明&#xff1a;变更文件或目录的所属群组。语  法&#xff1a;chgrp [-cfhRv][–help][–version][所属群组][文件或目录…] 或 chgrp [-cfhRv][–help][–version][–reference<参考文件或目录>][文件或目录…]补充说明&…...

基于 DeepSeek LLM 本地知识库搭建开源方案(AnythingLLM、Cherry、Ragflow、Dify)认知

写在前面 博文内容涉及 基于 Deepseek LLM 的本地知识库搭建使用 ollama 部署 Deepseek-R1 LLM知识库能力通过 Ragflow、Dify 、AnythingLLM、Cherry 提供理解不足小伙伴帮忙指正 &#x1f603;,生活加油 我站在人潮中央&#xff0c;思考这日日重复的生活。我突然想&#xff0c…...

Could not initialize class io.netty.util.internal.Platfor...

异常信息&#xff1a; Exception in thread "main" java.lang.NoClassDefFoundError: Could not initialize class io.netty.util.internal.PlatformDependent0 Caused by: java.lang.ExceptionInInitializerError: Exception java.lang.reflect.InaccessibleObjec…...

【书生大模型实战营】玩转HF/魔搭/魔乐社区-L0G4000

本文是书生大模型实战营系列的第4篇&#xff0c;本文的主题是&#xff1a;玩转HF/魔搭/魔乐社区。 1.开源大模型社区总览 开源不仅仅是一种技术模式&#xff0c;更是一种精神的体现。它打破了知识的壁垒&#xff0c;让技术平权成为可能。近年来&#xff0c;开源大模型社区蓬勃…...

2025年华为手机解锁BL的方法

注&#xff1a;本文是我用老机型测试的&#xff0c;新机型可能不适用 背景 华为官方已经在2018年关闭了申请BL解锁码的通道&#xff0c;所以华为手机已经无法通过官方获取解锁码。最近翻出了一部家里的老手机华为畅玩5X&#xff0c;想着能不能刷个系统玩玩&#xff0c;但是卡…...

了解 RAG 第二部分:经典 RAG 的工作原理

在本系列的第一篇文章中&#xff0c;我们介绍了检索增强生成 (RAG) &#xff0c;解释了扩展传统大型语言模型 (LLM)功能的必要性。我们还简要概述了 RAG 的核心思想&#xff1a;从外部知识库检索上下文相关的信息&#xff0c;以确保 LLM 生成准确且最新的信息&#xff0c;而不会…...

50周学习go语言:第四周 函数与错误处理深度解析

第四周 函数与错误处理深度解析 以下是第4周函数基础的深度教程&#xff0c;包含两个完整案例和详细实现细节&#xff1a; 第四周&#xff1a;函数与错误处理深度解析 一、函数定义与参数传递 1. 基础函数结构 // 基本语法 func 函数名(参数列表) 返回值类型 {// 函数体 }// …...

SolidWorks模型转URDF避坑指南:从零搭建ROS巡线小车的完整流程(含常见报错解决)

SolidWorks模型转URDF避坑指南&#xff1a;从零搭建ROS巡线小车的完整流程 在机器人开发领域&#xff0c;将SolidWorks设计的3D模型转换为ROS可用的URDF格式是一个关键但充满挑战的环节。许多开发者在初次尝试时都会遇到各种意料之外的问题&#xff0c;从坐标系混乱到关节定义错…...

Dev-CPP技术架构深度解析:为什么它成为轻量级C/C++开发者的首选

Dev-CPP技术架构深度解析&#xff1a;为什么它成为轻量级C/C开发者的首选 【免费下载链接】Dev-CPP A greatly improved Dev-Cpp 项目地址: https://gitcode.com/gh_mirrors/dev/Dev-CPP Dev-CPP是一款专注于C/C语言开发的轻量级集成开发环境&#xff0c;通过优化的架构…...

单级式三相光伏并网逆变器 图一单级式光伏并网逆变器整体波形 图二并网电流跟踪电网电压波形

单级式三相光伏并网逆变器 图一单级式光伏并网逆变器整体波形 图二并网电流跟踪电网电压波形 图三直流母线电压波形光伏逆变器的调试现场永远不缺意外。去年给某工业园区做单级式三相并网系统时&#xff0c;示波器上跳动的波形差点让我把保温杯里的枸杞茶洒在键盘上——图一里那…...

免费小说下载器终极指南:如何轻松保存你喜欢的网络小说

免费小说下载器终极指南&#xff1a;如何轻松保存你喜欢的网络小说 【免费下载链接】novel-downloader 一个可扩展的通用型小说下载器。 项目地址: https://gitcode.com/gh_mirrors/no/novel-downloader 你是否曾经遇到过这样的情况&#xff1a;正在追更的小说突然被网站…...

网络舆情监控中的情感分析与事件检测

网络舆情监控中的情感分析与事件检测 在信息爆炸的时代&#xff0c;社交媒体、新闻平台和论坛等渠道每天产生海量数据&#xff0c;如何从中提取有价值的信息成为企业和政府的重要课题。网络舆情监控通过情感分析与事件检测技术&#xff0c;帮助管理者洞察公众情绪、发现潜在危…...

掌握BigImageViewer:自定义图像加载器与工厂模式的完整指南

掌握BigImageViewer&#xff1a;自定义图像加载器与工厂模式的完整指南 【免费下载链接】BigImageViewer Big image viewer supporting pan and zoom, with very little memory usage and full featured image loading choices. Powered by Subsampling Scale Image View, Fres…...

网络七层到底怎么落到一次前端请求上:从浏览器到网卡,再到远端服务器

我以前老把 fetch 当成 HTTP 的别名。 代码里一句&#xff1a; const res await fetch(https://api.example.com/user/profile); const data await res.json();直觉上很容易脑补成一句话&#xff1a;浏览器把一个 HTTP 请求发出去&#xff0c;服务端回一段 JSON&#xff0c;结…...

**点云处理新范式:基于Python的高效三维数据滤波与分割实战**在自动驾

点云处理新范式&#xff1a;基于Python的高效三维数据滤波与分割实战 在自动驾驶、机器人导航和工业质检等前沿领域&#xff0c;点云数据已成为关键输入信息。它由成千上万甚至百万级的三维坐标&#xff08;x, y, z&#xff09;组成&#xff0c;常来自激光雷达&#xff08;LiD…...

Open UI5 源代码解析之1106:MenuTextFieldItem.js

源代码仓库: https://github.com/SAP/openui5 源代码位置:src\sap.ui.commons\src\sap\ui\commons\MenuTextFieldItem.js MenuTextFieldItem.js 文件深度分析 这不是普通菜单项,而是把输入能力塞进菜单体系的特殊桥接点 MenuTextFieldItem.js 这个文件和前面那些 commo…...

【反蒸馏实战 14】BI工程师:从报表开发者到数据架构师@BI工程师反蒸馏进化论(附 Python/SQL 完整代码)

摘要:2026年Agentic BI全面爆发,业务人员借助AI问数工具3分钟即可完成传统BI工程师半天的工作,报表开发、SQL取数等基础岗位需求同比下降26%,但具备数据架构设计、数据治理能力的BI工程师薪资高达18.2K/月(较纯报表工程师溢价30%)。本文基于真实企业场景,通过3个完整实战…...