創建一個Spring Boot Starter風格的Basic認證SDK

文章目錄

    • 前言
    • 設計思路
    • SDK實現步驟
      • 1. 創建SDK Maven項目(sdk目錄)
      • 2. 實現配置類
      • 3. 實現認證邏輯
      • 4. 實現攔截器
      • 5. 實現自動配置
      • 6. 創建spring.factories文件
    • 使用方集成步驟
      • 1. 引入SDK依賴
      • 2. 配置Application屬性
      • 3. 創建測試接口
      • 4. 測試接口訪問
    • SDK擴展功能
    • 總結

前言

Spring Boot作為當前最流行的Java開發框架之一,其Starter機制為開發者提供了極大的便利,使得集成各種功能變得更加簡單。為了幫助開發者快速實現基于AppID和AppSecret的應用認證功能,我們設計并實現了這個認證SDK。該SDK遵循Spring Boot Starter的最佳實踐,可以無縫集成到Spring Boot應用中,提供開箱即用的Basic認證功能。

在這里插入圖片描述

設計思路

創建一個Spring Boot Starter風格的SDK,它會:
1.自動配置認證所需的組件
2.提供簡單的配置方式管理多個AppID/AppSecret
3.通過攔截器自動保護指定接口
4.提供統一的錯誤響應處理

下面是整個認證流程的示意圖:
在這里插入圖片描述

SDK實現步驟

1. 創建SDK Maven項目(sdk目錄)

創建sdk/pom.xml文件:

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd"><modelVersion>4.0.0</modelVersion><groupId>com.example</groupId><artifactId>java-basic-sdk</artifactId><version>0.0.1-SNAPSHOT</version><packaging>jar</packaging><name>java-basic-sdk</name><description>java-basic-sdk</description><properties><java.version>1.8</java.version><project.build.sourceEncoding>UTF-8</project.build.sourceEncoding><project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding><spring-boot.version>2.6.13</spring-boot.version></properties><dependencies><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-web</artifactId></dependency><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-test</artifactId><scope>test</scope></dependency></dependencies><dependencyManagement><dependencies><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-dependencies</artifactId><version>${spring-boot.version}</version><type>pom</type><scope>import</scope></dependency></dependencies></dependencyManagement><build><plugins><plugin><groupId>org.apache.maven.plugins</groupId><artifactId>maven-compiler-plugin</artifactId><configuration><source>${java.version}</source><target>${java.version}</target></configuration></plugin></plugins></build>
</project>

2. 實現配置類

創建配置屬性類AppAuthProperties.java:

/*** AppAuthProperties* @author senfel* @version 1.0* @date 2025/9/12 16:17*/
@ConfigurationProperties(prefix = "app.auth")
public class AppAuthProperties {/*** 是否啟用App認證*/private boolean enabled = true;/*** 需要認證的路徑模式(默認保護/test接口)*/private String[] includePatterns = new String[]{"/test/**"};/*** 排除的路徑模式*/private String[] excludePatterns = new String[]{};/*** 存儲有效的AppID和AppSecret鍵值對*/private Map<String, String> clients = new HashMap<>();public boolean isEnabled() {return enabled;}public void setEnabled(boolean enabled) {this.enabled = enabled;}public String[] getIncludePatterns() {return includePatterns;}public void setIncludePatterns(String[] includePatterns) {this.includePatterns = includePatterns;}public String[] getExcludePatterns() {return excludePatterns;}public void setExcludePatterns(String[] excludePatterns) {this.excludePatterns = excludePatterns;}public Map<String, String> getClients() {return clients;}public void setClients(Map<String, String> clients) {this.clients = clients;}
}

3. 實現認證邏輯

創建認證服務類AppAuthService.java:

/*** AppAuthService* @author senfel* @version 1.0* @date 2025/9/12 16:19*/
public class AppAuthService {private final AppAuthProperties properties;public AppAuthService(AppAuthProperties properties) {this.properties = properties;}/*** 驗證AppID和AppSecret是否有效*/public boolean validateCredentials(String appId, String appSecret) {if (!StringUtils.hasText(appId) || !StringUtils.hasText(appSecret)) {return false;}// 檢查配置中是否存在該AppID且AppSecret匹配return properties.getClients().containsKey(appId) &&properties.getClients().get(appId).equals(appSecret);}/*** 從HTTP Basic認證頭中提取憑證*/public String[] extractCredentials(String authorizationHeader) {if (!StringUtils.hasText(authorizationHeader) ||!authorizationHeader.startsWith("Basic ")) {return null;}try {String base64Credentials = authorizationHeader.substring(6);String credentials = new String(Base64.getDecoder().decode(base64Credentials));return credentials.split(":", 2);} catch (Exception e) {return null;}}
}

4. 實現攔截器

創建認證攔截器AppAuthInterceptor.java:

/*** AppAuthInterceptor* @author senfel* @version 1.0* @date 2025/9/12 16:20*/
public class AppAuthInterceptor implements HandlerInterceptor {private final AppAuthService appAuthService;public AppAuthInterceptor(AppAuthService appAuthService) {this.appAuthService = appAuthService;}@Overridepublic boolean preHandle(HttpServletRequest request, HttpServletResponse response,Object handler) throws Exception {// 從請求頭中獲取Authorization信息String authorizationHeader = request.getHeader("Authorization");// 提取AppID和AppSecretString[] credentials = appAuthService.extractCredentials(authorizationHeader);if (credentials == null || credentials.length != 2) {sendErrorResponse(response, "缺少有效的Authorization請求頭,請使用Basic認證格式");return false;}String appId = credentials[0];String appSecret = credentials[1];// 驗證憑證if (!appAuthService.validateCredentials(appId, appSecret)) {sendErrorResponse(response, "無效的AppID或AppSecret");return false;}return true;}private void sendErrorResponse(HttpServletResponse response, String message)throws Exception {response.setStatus(HttpServletResponse.SC_UNAUTHORIZED);response.setContentType("application/json;charset=UTF-8");response.getWriter().write("{\"code\": 401, \"message\": \"" + message + "\"}");}
}

5. 實現自動配置

創建自動配置類AppAuthAutoConfiguration.java:

/*** AppAuthAutoConfiguration* @author senfel* @version 1.0* @date 2025/9/12 16:22*/
@Configuration
@ConditionalOnWebApplication
@EnableConfigurationProperties(AppAuthProperties.class)
@ConditionalOnProperty(prefix = "app.auth", name = "enabled", havingValue = "true", matchIfMissing = true)
public class AppAuthAutoConfiguration implements WebMvcConfigurer {private final AppAuthProperties properties;public AppAuthAutoConfiguration(AppAuthProperties properties) {this.properties = properties;}@Beanpublic AppAuthService appAuthService() {return new AppAuthService(properties);}@Beanpublic AppAuthInterceptor appAuthInterceptor(AppAuthService appAuthService) {return new AppAuthInterceptor(appAuthService);}@Overridepublic void addInterceptors(InterceptorRegistry registry) {registry.addInterceptor(appAuthInterceptor(appAuthService())).addPathPatterns(properties.getIncludePatterns()).excludePathPatterns(properties.getExcludePatterns());}
}

6. 創建spring.factories文件

創建sdk/src/main/resources/META-INF/spring.factories文件:

org.springframework.boot.autoconfigure.EnableAutoConfiguration=\
com.example.javabasicsdk.config.AppAuthAutoConfiguration

使用方集成步驟

1. 引入SDK依賴

在使用方的項目中添加SDK依賴:

<!--java-basic-sdk-->
<dependency><groupId>com.example</groupId><artifactId>java-basic-sdk</artifactId><version>0.0.1-SNAPSHOT</version>
</dependency>

2. 配置Application屬性

在使用方的application.yml中配置允許訪問的AppID和AppSecret:

# App認證配置
app:auth:enabled: trueinclude-patterns:- /test/**# 配置允許訪問的AppID和AppSecretclients:appid1: "appsecret1"

3. 創建測試接口

創建測試ControllerTestBasicController.java:

/*** TestController* @author senfel* @version 1.0* @date 2025/9/12 16:33*/
@RestController
@RequestMapping("/test")
public class TestBasicController {@GetMappingpublic String test() {return "認證成功,可以訪問此接口";}@GetMapping("/sub")public String testSub() {return "認證成功,可以訪問子接口";}
}

4. 測試接口訪問

不帶basic請求頭,會提示認證失敗:
在這里插入圖片描述

帶錯誤的appId/appSecret,會提示驗證失敗:
在這里插入圖片描述

正確的認證信息可以訪問:
在這里插入圖片描述

SDK擴展功能

如果想進一步增強SDK的功能,可以考慮:
1.添加日志記錄:記錄認證成功和失敗的請求
2.限流功能:為每個AppID添加請求頻率限制
3.動態配置:支持從數據庫或配置中心動態加載AppID/AppSecret
4.管理接口:提供管理接口用于動態添加/刪除AppID和AppSecret
5.多種認證方式:除了Basic認證,支持自定義請求頭等方式

總結

通過以上實現,創建一個Spring Boot Starter風格的AppID/AppSecret認證SDK,使用方只需:
1.引入SDK依賴
2.在application.yml中配置允許訪問的AppID和AppSecret
3.創建需要保護的接口(如/test)
SDK會自動攔截配置的接口路徑,驗證請求中的AppID和AppSecret,只有憑證有效的請求才能訪問受保護的接口。這種設計提供了開箱即用的體驗,同時保持了足夠的靈活性,可以通過配置調整保護的范圍和允許的憑證。

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/diannao/98877.shtml
繁體地址,請注明出處:http://hk.pswp.cn/diannao/98877.shtml
英文地址,請注明出處:http://en.pswp.cn/diannao/98877.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

mybatis處理統計sql進度丟失問題

如何處理統計sql進度丟失 SELECT sum(decimal_column) AS sum_value FROM your_table如上sql執行時沒有問題&#xff0c;在數據庫可視工具可以正常顯示&#xff0c;但是在mybatis執行時&#xff0c;卻出現解決辦法 使用轉 decimal 控制精度 SELECT CAST(SUM(decimal_column) A…

全球首款!科聰控制器獲德國 TüV 萊茵功能安全認證

近日&#xff0c;浙江科聰控制技術有限公司&#xff08;以下簡稱"科聰"&#xff09;的安全移動機器人控制器MSC5000榮獲全球權威認證機構德國萊茵TV集團&#xff08;TV Rheinland&#xff09;頒發的功能安全認證證書。這款控制器是全球首款通過SIL3、PLe 認證的移動機…

pureadmin的動態路由和靜態路由

在 PureAdmin&#xff08;基于 Vue3 的后臺管理框架&#xff09;中&#xff0c;靜態路由和動態路由是實現路由管理的兩種方式&#xff0c;主要區別在于路由的定義時機、加載方式和靈活性&#xff0c;具體區別如下&#xff1a; 1. 靜態路由 定義方式&#xff1a;路由規則在代碼中…

第3章:CPU實戰

1. Linux操作系統CPU平均負載 以前我們總認為CPU使用率和CPU平均負載是一樣的&#xff0c;負載高了就是CPU使用率提高。但是到底是什么情況呢&#xff1f; 1.1. CPU的平均負載 單位時間內 系統處于 可運行狀態 和不可中斷狀態 的平均進程數&#xff0c;就是平均活躍進程數&a…

【Vue3】06-利用setup編寫vue(1)

其它篇章&#xff1a; 1.【Vue3】01-創建Vue3工程 2.【Vue3】02-Vue3工程目錄分析 3.【Vue3】03-編寫app組件——src 4.【Vue3】04-編寫vue實現一個簡單效果 5.【Vue3】05-Options API和Composition API的區別 6.【Vue3】06-利用setup編寫vue&#xff08;1&#xff09; 7.【Vue…

UDS NRC速查

目錄 NRC 一、通用NRC(0x10~0x5F) 二、數據相關NRC(0x70~0x8F) 三、會話與狀態NRC 注意事項 UDS中的NRC(Negative Response Code)即否定響應碼,用于在診斷通信中表示服務端無法成功執行客戶端請求的原因。以下是一些常用的UDS NRC碼及其含義: HEX Name Description 01 …

【AI論文】多模態大型語言模型的視覺表征對齊

摘要&#xff1a;通過視覺指令微調訓練的多模態大型語言模型&#xff08;MLLMs&#xff09;在各類任務中均取得了優異表現&#xff0c;然而在以視覺為中心的任務&#xff08;如物體計數或空間推理&#xff09;中&#xff0c;其性能仍存在局限。我們將這一差距歸因于當前主流的純…

SKywalking Agent配置+Oracle監控插件安裝指南

SKywalking Agent配置Oracle監控插件安裝指南前言&#xff1a; SkyWalking Elasticsearch8 容器化部署指南 Skywalking版本&#xff1a;V10.2.0 Skywalking Agent版本&#xff1a;V9.4.0 Skywalking Agent下載地址&#xff1a;Downloads | Apache SkyWalking 插件下載地址&…

ES相關問題匯總

問題一&#xff1a;關于【QueryBuilder對象】和【Query String語法】查詢時底層運行方式和結果的差異

5. STM32 時鐘系統分配

文章目錄下述將以stm32f407 為例1. 時鐘系統及頻率分析2. 時鐘配置下述將以stm32f407 為例 1. 時鐘系統及頻率分析 上述STM32F4時鐘系統圖解析入下&#xff1a; STM32F407 系列微控制器&#xff08;基于 Cortex-M4 內核&#xff0c;帶 FPU&#xff09;的工作頻率配置如下&…

《從 0 建立測試開發認知:先搞懂 “是什么”,再學 “怎么做”》

&#x1f525;個人主頁&#xff1a;草莓熊Lotso &#x1f3ac;作者簡介&#xff1a;C研發方向學習者 &#x1f4d6;個人專欄&#xff1a; 《C知識分享》《Linux 入門到實踐&#xff1a;零基礎也能懂》《數據結構與算法》《測試開發實戰指南》《算法題闖關指南》 ??人生格言&a…

net::ERR_EMPTY_RESPONSE

net::ERR_EMPTY_RESPONSE表現解決表現 Java后端封裝一個接口&#xff0c;透傳前端參數&#xff0c;請求到其他模塊服務 本地開發環境聯調時是沒有問題&#xff0c;測試環境上報錯 1.前端報錯&#xff0c;F12檢查&#xff0c;network上的請求&#xff0c;返回response選項中為空…

在線多功能環境音生成器

https://oltool.cc/toolbox/huanjingyins.html 關于環境音生成器介紹&#xff1a; 1、本工具可以混合各種聲音&#xff0c;比如下雨聲&#xff0c;打雷聲&#xff0c;海浪聲&#xff0c;鳥叫以及蟲鳴聲等&#xff0c;生成新的環境聲。 2、定時器&#xff1a;可以設置倒計時&…

本地電腦映射端口到外網訪問的開啟方法和注意事項,內網服務提供跨網使用簡單操作實現

在計算機網絡中&#xff0c;端口映射是一項重要的技術&#xff0c;它允許外網用戶訪問局域網內的特定設備或服務。當我們在本地電腦搭建部署項目應用后&#xff0c;就可以通過映射端口的方式&#xff0c;簡單快速穩定的提供互聯網訪問服務。以下將詳細介紹如何開啟電腦映射端口…

Java 大視界 -- Java 大數據在智能醫療健康檔案數據分析與個性化健康管理中的應用(410)

Java 大視界 -- Java 大數據在智能醫療健康檔案數據分析與個性化健康管理中的應用&#xff08;410&#xff09;引言&#xff1a;正文&#xff1a;一、2023 年 6 月智能醫療健康檔案的核心落地需求&#xff08;政策 業務雙驅動&#xff09;1.1 政策倒逼的數據應用痛點&#xff…

微服務架構的基石:Nacos全方位解析與Java實戰指南

引言在云原生與微服務浪潮席卷而來的今天&#xff0c;服務的治理與配置的管理變得前所未有的復雜。一個個單一的應用被拆分為數十甚至上百個微服務&#xff0c;如何讓這些服務輕松地發現彼此&#xff1f;如何在不重啟應用的情況下動態調整所有服務的參數&#xff1f;這些問題直…

IDA pro 生成idapro.hexlic

先安裝IDA pro&#xff0c;安裝好后&#xff0c;把根目錄中的 ida32.dll和ida.dll賦值到python文件腳本同目錄中&#xff0c;如圖。 直接運行py import json import hashlib import os from datetime import datetime, timedelta import platform import winregname input(&…

【ARMv7-M】復位向量與啟動過程

關于ARMv7上電復位后&#xff0c;通過復位向量初始化堆棧位置、PC指針&#xff0c;然后跳轉到匯編入口&#xff0c;開始執行系統初始化等等操作&#xff0c;熟悉了解這個過程&#xff0c;對于嵌入式系統軟件開發來說至關重要。不同的SOC在BootROM與Flash的地址分配上&#xff0…

【開發者導航】開源免費的金融數據量化與分析項目!

Hello大家好&#xff01;我是助你打破信息差的開發者導航。今天給大家分享的開源項目是OpenBB&#xff0c;一個面向量化與分析的開源金融數據平臺&#xff01; 金融分析和量化研究需要可靠的數據來源與靈活的分析工具。OpenBB 正是為金融分析師、量化研究員以及 AI 代理開發者…

如何使用 OCR 提取掃描件 PDF 的文本(Python 實現)

從 PDF 中提取文本一直是很多人的需求。市面上的工具雖然能處理大部分數字 PDF&#xff0c;但遇到掃描件 PDF 時往往無能為力&#xff0c;想要直接復制或獲取其中的文字并不容易。其實這個問題并不是沒有解法 —— 本文將帶你了解如何借助 Python OCR 技術&#xff0c;從掃描 …