From 98ed8009455f3e3f548a3c063a672f91e68817c9 Mon Sep 17 00:00:00 2001 From: YunaiV Date: Thu, 21 Aug 2025 12:58:10 +0800 Subject: [PATCH] =?UTF-8?q?feat=EF=BC=9A=E3=80=90system=20=E7=B3=BB?= =?UTF-8?q?=E7=BB=9F=E7=AE=A1=E7=90=86=E3=80=91oauth2=20=E6=94=AF=E6=8C=81?= =?UTF-8?q?=20ClientCredentials=20=E6=A8=A1=E5=BC=8F?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../admin/oauth2/OAuth2OpenController.http | 8 ++++++ .../admin/oauth2/OAuth2OpenController.java | 27 ++++++++++++------- .../oauth2/OAuth2GrantServiceImpl.java | 4 +-- .../oauth2/OAuth2TokenServiceImpl.java | 5 +++- 4 files changed, 32 insertions(+), 12 deletions(-) diff --git a/yudao-module-system/src/main/java/cn/iocoder/yudao/module/system/controller/admin/oauth2/OAuth2OpenController.http b/yudao-module-system/src/main/java/cn/iocoder/yudao/module/system/controller/admin/oauth2/OAuth2OpenController.http index f770ed91d7..cdcebbfb1c 100644 --- a/yudao-module-system/src/main/java/cn/iocoder/yudao/module/system/controller/admin/oauth2/OAuth2OpenController.http +++ b/yudao-module-system/src/main/java/cn/iocoder/yudao/module/system/controller/admin/oauth2/OAuth2OpenController.http @@ -35,6 +35,14 @@ tenant-id: {{adminTenantId}} grant_type=password&username=admin&password=admin123&scope=user.read +### 请求 /system/oauth2/token + client_credentials 接口 => 成功 +POST {{baseUrl}}/system/oauth2/token +Content-Type: application/x-www-form-urlencoded +Authorization: Basic ZGVmYXVsdDphZG1pbjEyMw== +tenant-id: {{adminTenantId}} + +grant_type=client_credentials&scope=user.read + ### 请求 /system/oauth2/token + refresh_token 接口 => 成功 POST {{baseUrl}}/system/oauth2/token Content-Type: application/x-www-form-urlencoded diff --git a/yudao-module-system/src/main/java/cn/iocoder/yudao/module/system/controller/admin/oauth2/OAuth2OpenController.java b/yudao-module-system/src/main/java/cn/iocoder/yudao/module/system/controller/admin/oauth2/OAuth2OpenController.java index d06523e9c0..067ab8aaf1 100644 --- a/yudao-module-system/src/main/java/cn/iocoder/yudao/module/system/controller/admin/oauth2/OAuth2OpenController.java +++ b/yudao-module-system/src/main/java/cn/iocoder/yudao/module/system/controller/admin/oauth2/OAuth2OpenController.java @@ -94,6 +94,7 @@ public class OAuth2OpenController { @Parameter(name = "scope", example = "user_info"), @Parameter(name = "refresh_token", example = "123424233"), }) + @SuppressWarnings("EnhancedSwitchMigration") public CommonResult postAccessToken(HttpServletRequest request, @RequestParam("grant_type") String grantType, @RequestParam(value = "code", required = false) String code, // 授权码模式 @@ -119,15 +120,23 @@ public class OAuth2OpenController { grantType, scopes, redirectUri); // 2. 根据授权模式,获取访问令牌 - OAuth2AccessTokenDO accessTokenDO = switch (grantTypeEnum) { - // TODO @xingyu:这里改了,可能会影响 jdk8 版本哈; - case AUTHORIZATION_CODE -> - oauth2GrantService.grantAuthorizationCodeForAccessToken(client.getClientId(), code, redirectUri, state); - case PASSWORD -> oauth2GrantService.grantPassword(username, password, client.getClientId(), scopes); - case CLIENT_CREDENTIALS -> oauth2GrantService.grantClientCredentials(client.getClientId(), scopes); - case REFRESH_TOKEN -> oauth2GrantService.grantRefreshToken(refreshToken, client.getClientId()); - default -> throw new IllegalArgumentException("未知授权类型:" + grantType); - }; + OAuth2AccessTokenDO accessTokenDO; + switch (grantTypeEnum) { + case AUTHORIZATION_CODE: + accessTokenDO = oauth2GrantService.grantAuthorizationCodeForAccessToken(client.getClientId(), code, redirectUri, state); + break; + case PASSWORD: + accessTokenDO = oauth2GrantService.grantPassword(username, password, client.getClientId(), scopes); + break; + case CLIENT_CREDENTIALS: + accessTokenDO = oauth2GrantService.grantClientCredentials(client.getClientId(), scopes); + break; + case REFRESH_TOKEN: + accessTokenDO = oauth2GrantService.grantRefreshToken(refreshToken, client.getClientId()); + break; + default: + throw new IllegalArgumentException("未知授权类型:" + grantType); + } Assert.notNull(accessTokenDO, "访问令牌不能为空"); // 防御性检查 return success(OAuth2OpenConvert.INSTANCE.convert(accessTokenDO)); } diff --git a/yudao-module-system/src/main/java/cn/iocoder/yudao/module/system/service/oauth2/OAuth2GrantServiceImpl.java b/yudao-module-system/src/main/java/cn/iocoder/yudao/module/system/service/oauth2/OAuth2GrantServiceImpl.java index e95fecccc6..56c980ab7b 100644 --- a/yudao-module-system/src/main/java/cn/iocoder/yudao/module/system/service/oauth2/OAuth2GrantServiceImpl.java +++ b/yudao-module-system/src/main/java/cn/iocoder/yudao/module/system/service/oauth2/OAuth2GrantServiceImpl.java @@ -86,8 +86,8 @@ public class OAuth2GrantServiceImpl implements OAuth2GrantService { @Override public OAuth2AccessTokenDO grantClientCredentials(String clientId, List scopes) { - // TODO 芋艿:项目中使用 OAuth2 解决的是三方应用的授权,内部的 SSO 等问题,所以暂时不考虑 client_credentials 这个场景 - throw new UnsupportedOperationException("暂时不支持 client_credentials 授权模式"); + // 特殊:https://yuanbao.tencent.com/bot/app/share/chat/wFj642xSZHHx + return oauth2TokenService.createAccessToken(0L, UserTypeEnum.ADMIN.getValue(), clientId, scopes); } @Override diff --git a/yudao-module-system/src/main/java/cn/iocoder/yudao/module/system/service/oauth2/OAuth2TokenServiceImpl.java b/yudao-module-system/src/main/java/cn/iocoder/yudao/module/system/service/oauth2/OAuth2TokenServiceImpl.java index fb0e756a20..5c628b8e1e 100644 --- a/yudao-module-system/src/main/java/cn/iocoder/yudao/module/system/service/oauth2/OAuth2TokenServiceImpl.java +++ b/yudao-module-system/src/main/java/cn/iocoder/yudao/module/system/service/oauth2/OAuth2TokenServiceImpl.java @@ -197,6 +197,9 @@ public class OAuth2TokenServiceImpl implements OAuth2TokenService { * @return 用户信息 */ private Map buildUserInfo(Long userId, Integer userType) { + if (userId == null || userId <= 0) { + return Collections.emptyMap(); + } if (userType.equals(UserTypeEnum.ADMIN.getValue())) { AdminUserDO user = adminUserService.getUser(userId); return MapUtil.builder(LoginUser.INFO_KEY_NICKNAME, user.getNickname()) @@ -205,7 +208,7 @@ public class OAuth2TokenServiceImpl implements OAuth2TokenService { // 注意:目前 Member 暂时不读取,可以按需实现 return Collections.emptyMap(); } - return null; + throw new IllegalArgumentException("未知用户类型:" + userType); } private static String generateAccessToken() {