Skip to content
Projects
Groups
Snippets
Help
This project
Loading...
Sign in / Register
Toggle navigation
Y
yd-cloud-core
Overview
Overview
Details
Activity
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Snippets
Snippets
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
xingmin
yd-cloud-core
Commits
de57dff1
Commit
de57dff1
authored
Aug 01, 2025
by
zhangxingmin
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
微服务核心组件
parent
345cdf96
Hide whitespace changes
Inline
Side-by-side
Showing
35 changed files
with
580 additions
and
775 deletions
+580
-775
yd-auth-core/pom.xml
+18
-15
yd-auth-core/src/main/java/com/yd/auth/core/config/SecurityConfig.java
+3
-2
yd-auth-core/src/main/java/com/yd/auth/core/controller/AuthController.java
+15
-20
yd-auth-core/src/main/java/com/yd/auth/core/dto/AuthPermissionDto.java
+15
-0
yd-auth-core/src/main/java/com/yd/auth/core/dto/AuthRoleDto.java
+10
-0
yd-auth-core/src/main/java/com/yd/auth/core/dto/AuthUserDto.java
+122
-0
yd-auth-core/src/main/java/com/yd/auth/core/dto/LoginRequest.java
+0
-23
yd-auth-core/src/main/java/com/yd/auth/core/dto/LoginResponse.java
+0
-32
yd-auth-core/src/main/java/com/yd/auth/core/exception/GlobalExceptionHandler.java
+25
-25
yd-auth-core/src/main/java/com/yd/auth/core/request/LoginRequest.java
+22
-0
yd-auth-core/src/main/java/com/yd/auth/core/response/LoginResponse.java
+11
-0
yd-auth-core/src/main/java/com/yd/auth/core/security/DummyAuthenticationManager.java
+0
-66
yd-auth-core/src/main/java/com/yd/auth/core/security/JwtAuthenticationEntryPoint.java
+7
-1
yd-auth-core/src/main/java/com/yd/auth/core/security/JwtAuthenticationFilter.java
+50
-9
yd-auth-core/src/main/java/com/yd/auth/core/security/JwtAuthenticationProvider.java
+0
-66
yd-auth-core/src/main/java/com/yd/auth/core/security/JwtAuthenticationToken.java
+0
-60
yd-auth-core/src/main/java/com/yd/auth/core/security/JwtTokenProvider.java
+11
-3
yd-auth-core/src/main/java/com/yd/auth/core/service/AuthService.java
+2
-5
yd-auth-core/src/main/java/com/yd/auth/core/service/AuthUserDetailsService.java
+0
-43
yd-auth-core/src/main/java/com/yd/auth/core/service/UserService.java
+0
-25
yd-auth-core/src/main/java/com/yd/auth/core/service/impl/AuthServiceImpl.java
+32
-30
yd-auth-core/src/main/java/com/yd/auth/core/service/impl/AuthUserDetailsService.java
+42
-0
yd-auth-core/src/main/java/com/yd/auth/core/utils/JwtUtils.java
+0
-141
yd-common/pom.xml
+8
-5
yd-common/src/main/java/com/yd/common/dto/PageDto.java
+11
-0
yd-common/src/main/java/com/yd/common/enums/CommonEnum.java
+35
-0
yd-common/src/main/java/com/yd/common/enums/ResultCode.java
+44
-0
yd-common/src/main/java/com/yd/common/result/Result.java
+11
-1
yd-common/src/main/java/com/yd/common/utils/RandomStringGenerator.java
+63
-0
yd-feign/pom.xml
+0
-16
yd-feign/src/main/java/com/yd/feign/client/UserFeignClient.java
+0
-21
yd-feign/src/main/java/com/yd/feign/client/fallback/UserFeignFallbackFactory.java
+0
-26
yd-framework/src/main/java/com/yd/framework/handler/GlobalExceptionHandler.java
+23
-2
yd-gateway/src/main/java/com/yd/gateway/config/GatewayConfig.java
+0
-28
yd-gateway/src/main/java/com/yd/gateway/filter/AuthenticationFilter.java
+0
-110
No files found.
yd-auth-core/pom.xml
View file @
de57dff1
...
...
@@ -53,18 +53,6 @@
<artifactId>
jjwt-jackson
</artifactId>
</dependency>
<!-- yd-user-service 模块 -->
<dependency>
<groupId>
com.yd
</groupId>
<artifactId>
yd-user-service
</artifactId>
<version>
${project.version}
</version>
</dependency>
<dependency>
<groupId>
com.yd
</groupId>
<artifactId>
yd-common
</artifactId>
<version>
${project.version}
</version>
</dependency>
<dependency>
<groupId>
io.projectreactor
</groupId>
<artifactId>
reactor-core
</artifactId>
...
...
@@ -92,12 +80,27 @@
<artifactId>
p6spy
</artifactId>
</dependency>
<!-- 用户API模块 -->
<dependency>
<groupId>
org.springframework.cloud
</groupId>
<artifactId>
spring-cloud-starter-loadbalancer
</artifactId>
<version>
3.1.1
</version>
<!-- 与您的Spring Cloud版本匹配 -->
</dependency>
<!-- yd-user-service 模块 -->
<dependency>
<groupId>
com.yd
</groupId>
<artifactId>
yd-user-api
</artifactId>
<artifactId>
yd-user-service
</artifactId>
<version>
${project.version}
</version>
</dependency>
<dependency>
<groupId>
com.yd
</groupId>
<artifactId>
yd-common
</artifactId>
<version>
${project.version}
</version>
</dependency>
<dependency>
<groupId>
com.yd
</groupId>
<artifactId>
yd-framework
</artifactId>
<version>
${project.version}
</version>
</dependency>
</dependencies>
</project>
yd-auth-core/src/main/java/com/yd/auth/core/config/SecurityConfig.java
View file @
de57dff1
...
...
@@ -2,7 +2,7 @@ package com.yd.auth.core.config;
import
com.yd.auth.core.security.JwtAuthenticationEntryPoint
;
import
com.yd.auth.core.security.JwtAuthenticationFilter
;
import
com.yd.auth.core.service.AuthUserDetailsService
;
import
com.yd.auth.core.service.
impl.
AuthUserDetailsService
;
import
org.springframework.beans.factory.annotation.Autowired
;
import
org.springframework.context.annotation.Bean
;
import
org.springframework.context.annotation.Configuration
;
...
...
@@ -62,7 +62,8 @@ public class SecurityConfig extends WebSecurityConfigurerAdapter {
"/auth/login"
,
"/auth/register"
,
"/swagger-ui/**"
,
"/v3/api-docs/**"
"/v3/api-docs/**"
,
"/scrm/test"
).
permitAll
()
.
anyRequest
().
authenticated
()
.
and
()
...
...
yd-auth-core/src/main/java/com/yd/auth/core/controller/AuthController.java
View file @
de57dff1
package
com
.
yd
.
auth
.
core
.
controller
;
import
com.yd.auth.core.
dto
.LoginRequest
;
import
com.yd.auth.core.
dto
.LoginResponse
;
import
com.yd.auth.core.
request
.LoginRequest
;
import
com.yd.auth.core.
response
.LoginResponse
;
import
com.yd.auth.core.service.AuthService
;
import
com.yd.common.result.Result
;
import
org.springframework.beans.factory.annotation.Autowired
;
import
org.springframework.web.bind.annotation.PostMapping
;
import
org.springframework.web.bind.annotation.RequestBody
;
import
org.springframework.web.bind.annotation.RequestMapping
;
import
org.springframework.web.bind.annotation.RestController
;
import
javax.validation.Valid
;
import
org.springframework.validation.annotation.Validated
;
import
org.springframework.web.bind.annotation.*
;
/**
* 认证信息
*/
@RestController
@RequestMapping
(
"/auth"
)
@Validated
public
class
AuthController
{
private
final
AuthService
authService
;
@Autowired
public
AuthController
(
AuthService
authService
)
{
this
.
authService
=
authService
;
}
private
AuthService
authService
;
/**
* 登录(spring security登录认证)
* @param loginRequest
* @return
*/
@PostMapping
(
"/login"
)
public
Result
<
LoginResponse
>
login
(
@
Valid
@
RequestBody
LoginRequest
loginRequest
)
{
public
Result
<
LoginResponse
>
login
(
@RequestBody
LoginRequest
loginRequest
)
{
LoginResponse
response
=
authService
.
login
(
loginRequest
);
return
Result
.
success
(
response
);
}
// @PostMapping("/logout")
// public Result<Void> logout() {
// // 实际实现需要前端传递token
// // 这里简化处理
// return R.success("登出成功");
// }
}
yd-auth-core/src/main/java/com/yd/auth/core/dto/AuthPermissionDto.java
0 → 100644
View file @
de57dff1
package
com
.
yd
.
auth
.
core
.
dto
;
import
com.baomidou.mybatisplus.annotation.IdType
;
import
com.baomidou.mybatisplus.annotation.TableId
;
import
com.baomidou.mybatisplus.annotation.TableName
;
import
lombok.Data
;
@Data
public
class
AuthPermissionDto
{
private
Long
id
;
private
String
name
;
private
String
description
;
private
String
url
;
private
String
method
;
}
yd-auth-core/src/main/java/com/yd/auth/core/dto/AuthRoleDto.java
0 → 100644
View file @
de57dff1
package
com
.
yd
.
auth
.
core
.
dto
;
import
lombok.Data
;
@Data
public
class
AuthRoleDto
{
private
Long
id
;
private
String
name
;
private
String
description
;
}
yd-auth-core/src/main/java/com/yd/auth/core/dto/AuthUserDto.java
0 → 100644
View file @
de57dff1
package
com
.
yd
.
auth
.
core
.
dto
;
import
lombok.Data
;
import
org.springframework.security.core.GrantedAuthority
;
import
org.springframework.security.core.authority.SimpleGrantedAuthority
;
import
org.springframework.security.core.userdetails.UserDetails
;
import
java.util.ArrayList
;
import
java.util.Collection
;
import
java.util.List
;
/**
* 用户认证信息数据传输对象
* 实现Spring Security的UserDetails接口,用于封装用户认证信息
*/
@Data
public
class
AuthUserDto
implements
UserDetails
{
/**
* 系统用户主键id(数据库唯一标识)
*/
private
Long
id
;
/**
* 用户唯一标识(业务ID),用于业务层面的用户识别
*/
private
String
userUid
;
/**
* 登录账号(实现UserDetails接口必需)
*/
private
String
username
;
/**
* 加密后的密码(实现UserDetails接口必需)
*/
private
String
password
;
// ============== Spring Security账户状态属性 ==============
/**
* 账户是否启用(默认true启用)
*/
private
Boolean
enabled
=
true
;
/**
* 账户是否未过期(默认true未过期)
*/
private
Boolean
accountNonExpired
=
true
;
/**
* 凭证(密码)是否未过期(默认true未过期)
*/
private
Boolean
credentialsNonExpired
=
true
;
/**
* 账户是否未锁定(默认true未锁定)
*/
private
Boolean
accountNonLocked
=
true
;
/**
* 用户关联的角色列表
*/
private
List
<
AuthRoleDto
>
roles
;
/**
* 获取用户权限集合(实现UserDetails接口必需)
* Spring Security通过此方法获取用户的权限/角色信息
*
* @return 权限集合,每个权限以GrantedAuthority对象表示
*/
@Override
public
Collection
<?
extends
GrantedAuthority
>
getAuthorities
()
{
// 创建权限集合
List
<
GrantedAuthority
>
authorities
=
new
ArrayList
<
GrantedAuthority
>();
// 检查角色列表是否有效
if
(
roles
!=
null
&&
!
roles
.
isEmpty
())
{
// 遍历所有角色
for
(
AuthRoleDto
role
:
roles
)
{
// 将角色名转换为Spring Security认可的权限标识(添加ROLE_前缀)
authorities
.
add
(
new
SimpleGrantedAuthority
(
"ROLE_"
+
role
.
getName
()));
}
}
return
authorities
;
}
/**
* 检查账户是否未过期
* @return true=未过期,false=已过期
*/
@Override
public
boolean
isAccountNonExpired
()
{
return
accountNonExpired
;
}
/**
* 检查账户是否未锁定
* @return true=未锁定,false=已锁定
*/
@Override
public
boolean
isAccountNonLocked
()
{
return
accountNonLocked
;
}
/**
* 检查凭证(密码)是否未过期
* @return true=未过期,false=已过期
*/
@Override
public
boolean
isCredentialsNonExpired
()
{
return
credentialsNonExpired
;
}
/**
* 检查账户是否启用
* @return true=启用,false=禁用
*/
@Override
public
boolean
isEnabled
()
{
return
enabled
;
}
}
yd-auth-core/src/main/java/com/yd/auth/core/dto/LoginRequest.java
deleted
100644 → 0
View file @
345cdf96
package
com
.
yd
.
auth
.
core
.
dto
;
public
class
LoginRequest
{
private
String
username
;
private
String
password
;
// Getters and Setters
public
String
getUsername
()
{
return
username
;
}
public
void
setUsername
(
String
username
)
{
this
.
username
=
username
;
}
public
String
getPassword
()
{
return
password
;
}
public
void
setPassword
(
String
password
)
{
this
.
password
=
password
;
}
}
yd-auth-core/src/main/java/com/yd/auth/core/dto/LoginResponse.java
deleted
100644 → 0
View file @
345cdf96
package
com
.
yd
.
auth
.
core
.
dto
;
public
class
LoginResponse
{
private
String
token
;
private
String
tokenType
=
"Bearer"
;
private
long
expiresIn
;
// Getters and Setters
public
String
getToken
()
{
return
token
;
}
public
void
setToken
(
String
token
)
{
this
.
token
=
token
;
}
public
String
getTokenType
()
{
return
tokenType
;
}
public
void
setTokenType
(
String
tokenType
)
{
this
.
tokenType
=
tokenType
;
}
public
long
getExpiresIn
()
{
return
expiresIn
;
}
public
void
setExpiresIn
(
long
expiresIn
)
{
this
.
expiresIn
=
expiresIn
;
}
}
yd-auth-core/src/main/java/com/yd/auth/core/exception/GlobalExceptionHandler.java
View file @
de57dff1
package
com
.
yd
.
auth
.
core
.
exception
;
import
com.yd.auth.core.security.JwtTokenProvider
;
import
com.yd.common.result.Result
;
import
org.springframework.http.HttpStatus
;
import
org.springframework.security.authentication.BadCredentialsException
;
import
org.springframework.web.bind.annotation.ExceptionHandler
;
import
org.springframework.web.bind.annotation.ResponseStatus
;
import
org.springframework.web.bind.annotation.RestControllerAdvice
;
@RestControllerAdvice
public
class
GlobalExceptionHandler
{
@ExceptionHandler
(
BadCredentialsException
.
class
)
@ResponseStatus
(
HttpStatus
.
UNAUTHORIZED
)
public
Result
<?>
handleBadCredentialsException
(
BadCredentialsException
e
)
{
return
Result
.
fail
(
401
,
"用户名或密码错误"
);
}
@ExceptionHandler
(
JwtTokenProvider
.
JwtAuthenticationException
.
class
)
@ResponseStatus
(
HttpStatus
.
UNAUTHORIZED
)
public
Result
<?>
handleJwtAuthenticationException
(
JwtTokenProvider
.
JwtAuthenticationException
e
)
{
return
Result
.
fail
(
401
,
e
.
getMessage
());
}
}
//
package com.yd.auth.core.exception;
//
//
import com.yd.auth.core.security.JwtTokenProvider;
//
import com.yd.common.result.Result;
//
import org.springframework.http.HttpStatus;
//
import org.springframework.security.authentication.BadCredentialsException;
//
import org.springframework.web.bind.annotation.ExceptionHandler;
//
import org.springframework.web.bind.annotation.ResponseStatus;
//
import org.springframework.web.bind.annotation.RestControllerAdvice;
//
//
@RestControllerAdvice
//
public class GlobalExceptionHandler {
//
//
@ExceptionHandler(BadCredentialsException.class)
//
@ResponseStatus(HttpStatus.UNAUTHORIZED)
//
public Result<?> handleBadCredentialsException(BadCredentialsException e) {
//
return Result.fail(401, "用户名或密码错误");
//
}
//
//
@ExceptionHandler(JwtTokenProvider.JwtAuthenticationException.class)
//
@ResponseStatus(HttpStatus.UNAUTHORIZED)
//
public Result<?> handleJwtAuthenticationException(JwtTokenProvider.JwtAuthenticationException e) {
//
return Result.fail(401, e.getMessage());
//
}
//
}
yd-auth-core/src/main/java/com/yd/auth/core/request/LoginRequest.java
0 → 100644
View file @
de57dff1
package
com
.
yd
.
auth
.
core
.
request
;
import
lombok.Data
;
import
javax.validation.constraints.NotBlank
;
@Data
public
class
LoginRequest
{
/**
* 用户登录账号
*/
@NotBlank
(
message
=
"用户登录账号不能为空"
)
private
String
username
;
/**
* 明文密码
*/
@NotBlank
(
message
=
"密码不能为空"
)
private
String
password
;
}
yd-auth-core/src/main/java/com/yd/auth/core/response/LoginResponse.java
0 → 100644
View file @
de57dff1
package
com
.
yd
.
auth
.
core
.
response
;
import
lombok.Data
;
@Data
public
class
LoginResponse
{
private
String
token
;
private
String
tokenType
=
"Bearer"
;
private
long
expiresIn
;
}
yd-auth-core/src/main/java/com/yd/auth/core/security/DummyAuthenticationManager.java
deleted
100644 → 0
View file @
345cdf96
package
com
.
yd
.
auth
.
core
.
security
;
import
com.yd.auth.core.security.JwtAuthenticationToken
;
import
org.springframework.security.authentication.ReactiveAuthenticationManager
;
import
org.springframework.security.core.Authentication
;
import
org.springframework.security.core.GrantedAuthority
;
import
org.springframework.security.core.authority.SimpleGrantedAuthority
;
import
org.springframework.stereotype.Component
;
import
reactor.core.publisher.Mono
;
import
java.util.ArrayList
;
import
java.util.List
;
@Component
public
class
DummyAuthenticationManager
implements
ReactiveAuthenticationManager
{
@Override
public
Mono
<
Authentication
>
authenticate
(
Authentication
authentication
)
{
// 检查是否为 JwtAuthenticationToken 类型
if
(
authentication
instanceof
JwtAuthenticationToken
)
{
String
token
=
(
String
)
authentication
.
getCredentials
();
try
{
// 验证令牌有效性(实际项目中应调用 JwtUtils 验证)
if
(
isValidToken
(
token
))
{
// 从令牌中提取用户名和权限信息
String
username
=
extractUsernameFromToken
(
token
);
List
<
GrantedAuthority
>
authorities
=
extractAuthoritiesFromToken
(
token
);
// 创建已认证的令牌
JwtAuthenticationToken
authenticatedToken
=
new
JwtAuthenticationToken
(
username
,
authorities
);
authenticatedToken
.
setDetails
(
authentication
.
getDetails
());
// return Mono.just(authenticatedToken);
return
null
;
}
}
catch
(
Exception
e
)
{
return
Mono
.
error
(
e
);
}
}
// 非 JWT 认证请求,返回空
return
Mono
.
empty
();
}
// 实际项目中应调用 JwtUtils 验证令牌
private
boolean
isValidToken
(
String
token
)
{
// 示例实现,实际应调用 JwtUtils.validateToken(token)
return
token
!=
null
&&
!
token
.
isEmpty
();
}
// 实际项目中应从令牌中解析用户名
private
String
extractUsernameFromToken
(
String
token
)
{
// 示例实现,实际应调用 JwtUtils.getUsernameFromToken(token)
return
"test-user"
;
}
// 实际项目中应从令牌中解析权限
private
List
<
GrantedAuthority
>
extractAuthoritiesFromToken
(
String
token
)
{
// 示例实现,实际应调用 JwtUtils.getRolesFromToken(token)
List
<
GrantedAuthority
>
authorities
=
new
ArrayList
<
GrantedAuthority
>();
authorities
.
add
(
new
SimpleGrantedAuthority
(
"ROLE_USER"
));
return
authorities
;
}
}
yd-auth-core/src/main/java/com/yd/auth/core/security/JwtAuthenticationEntryPoint.java
View file @
de57dff1
...
...
@@ -15,6 +15,12 @@ public class JwtAuthenticationEntryPoint implements AuthenticationEntryPoint {
public
void
commence
(
HttpServletRequest
request
,
HttpServletResponse
response
,
AuthenticationException
authException
)
throws
IOException
{
response
.
sendError
(
HttpServletResponse
.
SC_UNAUTHORIZED
,
"未经授权的访问"
);
// 设置响应类型为JSON
response
.
setContentType
(
"application/json;charset=UTF-8"
);
// 直接设置401状态码
response
.
setStatus
(
HttpServletResponse
.
SC_UNAUTHORIZED
);
// 返回JSON格式的错误信息
response
.
getWriter
().
write
(
"{\"code\":401,\"message\":\"未经授权的访问\"}"
);
}
}
yd-auth-core/src/main/java/com/yd/auth/core/security/JwtAuthenticationFilter.java
View file @
de57dff1
package
com
.
yd
.
auth
.
core
.
security
;
import
com.yd.auth.core.dto.AuthUserDto
;
import
com.yd.user.service.model.SysUser
;
import
com.yd.user.service.service.ISysUserService
;
import
org.springframework.beans.BeanUtils
;
import
org.springframework.beans.factory.annotation.Autowired
;
import
org.springframework.security.authentication.UsernamePasswordAuthenticationToken
;
import
org.springframework.security.core.context.SecurityContextHolder
;
import
org.springframework.security.core.userdetails.UserDetails
;
import
org.springframework.security.core.userdetails.User
DetailsService
;
import
org.springframework.security.core.userdetails.User
nameNotFoundException
;
import
org.springframework.stereotype.Component
;
import
org.springframework.util.StringUtils
;
import
org.springframework.web.filter.OncePerRequestFilter
;
import
javax.servlet.FilterChain
;
import
javax.servlet.ServletException
;
import
javax.servlet.http.HttpServletRequest
;
import
javax.servlet.http.HttpServletResponse
;
import
java.io.IOException
;
import
java.util.Objects
;
@Component
public
class
JwtAuthenticationFilter
extends
OncePerRequestFilter
{
@Autowired
private
ISysUserService
iSysUserService
;
private
final
JwtTokenProvider
tokenProvider
;
private
final
UserDetailsService
userDetailsService
;
public
JwtAuthenticationFilter
(
JwtTokenProvider
tokenProvider
,
UserDetailsService
userDetailsService
)
{
public
JwtAuthenticationFilter
(
JwtTokenProvider
tokenProvider
)
{
this
.
tokenProvider
=
tokenProvider
;
this
.
userDetailsService
=
userDetailsService
;
}
@Override
protected
void
doFilterInternal
(
HttpServletRequest
request
,
HttpServletResponse
response
,
FilterChain
filterChain
)
throws
ServletException
,
IOException
{
// 1. 从HTTP请求中解析JWT令牌(通常从Authorization头获取)
String
token
=
resolveToken
(
request
);
// 2. 检查令牌是否存在且有效
if
(
token
!=
null
&&
tokenProvider
.
validateToken
(
token
))
{
String
username
=
tokenProvider
.
getUsernameFromToken
(
token
);
// 从数据库加载用户信息
UserDetails
userDetails
=
userDetailsService
.
loadUserByUsername
(
username
);
// 3. 从JWT令牌中提取用户唯一标识(业务ID)
String
userUid
=
tokenProvider
.
getUserUidFromToken
(
token
);
// 4. 根据用户唯一标识查询用户详细信息(包括权限信息)
UserDetails
userDetails
=
queryUserDetails
(
userUid
);
// 5. 创建Spring Security认证对象
// - userDetails: 包含用户身份和权限信息
// - null: 凭证(密码),JWT认证中不需要
// - userDetails.getAuthorities(): 用户的权限集合
UsernamePasswordAuthenticationToken
authentication
=
new
UsernamePasswordAuthenticationToken
(
userDetails
,
null
,
userDetails
.
getAuthorities
());
// 6. 将认证对象设置到SecurityContext中,表示用户已认证,这里设置后续接口能直接拿到登录用户信息
SecurityContextHolder
.
getContext
().
setAuthentication
(
authentication
);
}
// 7. 继续执行后续过滤器链(无论是否认证都要继续处理请求)
filterChain
.
doFilter
(
request
,
response
);
}
/**
* 查询用户信息返回spring security认证对象UserDetails
* @param userUid
* @return spring security认证对象UserDetails
*/
public
UserDetails
queryUserDetails
(
String
userUid
)
{
AuthUserDto
authUserDto
=
null
;
SysUser
sysUser
=
iSysUserService
.
queryOne
(
userUid
);
if
(
Objects
.
isNull
(
sysUser
))
{
throw
new
UsernameNotFoundException
(
"用户不存在:"
);
}
authUserDto
=
new
AuthUserDto
();
BeanUtils
.
copyProperties
(
sysUser
,
authUserDto
);
// 查询用户角色 TODO
// authUserDto.setRoles(roles);
return
authUserDto
;
}
private
String
resolveToken
(
HttpServletRequest
request
)
{
String
bearerToken
=
request
.
getHeader
(
"Authorization"
);
if
(
StringUtils
.
hasText
(
bearerToken
)
&&
bearerToken
.
startsWith
(
"Bearer "
))
{
...
...
yd-auth-core/src/main/java/com/yd/auth/core/security/JwtAuthenticationProvider.java
deleted
100644 → 0
View file @
345cdf96
package
com
.
yd
.
auth
.
core
.
security
;
import
com.yd.auth.core.utils.JwtUtils
;
import
org.springframework.beans.factory.annotation.Autowired
;
import
org.springframework.security.authentication.AuthenticationProvider
;
import
org.springframework.security.authentication.BadCredentialsException
;
import
org.springframework.security.core.Authentication
;
import
org.springframework.security.core.AuthenticationException
;
import
org.springframework.security.core.GrantedAuthority
;
import
org.springframework.security.core.authority.SimpleGrantedAuthority
;
import
org.springframework.security.core.userdetails.UserDetails
;
import
org.springframework.security.core.userdetails.UserDetailsService
;
import
org.springframework.stereotype.Component
;
import
java.util.ArrayList
;
import
java.util.List
;
@Component
public
class
JwtAuthenticationProvider
implements
AuthenticationProvider
{
@Autowired
private
JwtUtils
jwtUtils
;
@Autowired
private
UserDetailsService
userDetailsService
;
@Override
public
Authentication
authenticate
(
Authentication
authentication
)
throws
AuthenticationException
{
String
token
=
(
String
)
authentication
.
getCredentials
();
try
{
// 验证JWT令牌
if
(!
jwtUtils
.
validateToken
(
token
))
{
throw
new
BadCredentialsException
(
"无效的令牌"
);
}
// 从令牌中获取用户名
String
username
=
jwtUtils
.
getUsernameFromToken
(
token
);
// 加载用户详情
UserDetails
userDetails
=
userDetailsService
.
loadUserByUsername
(
username
);
// 从令牌中获取角色
List
<
String
>
roles
=
jwtUtils
.
getRolesFromToken
(
token
);
List
<
GrantedAuthority
>
authorities
=
new
ArrayList
<
GrantedAuthority
>();
for
(
String
role
:
roles
)
{
authorities
.
add
(
new
SimpleGrantedAuthority
(
role
));
}
// 创建已认证的令牌
JwtAuthenticationToken
authenticatedToken
=
new
JwtAuthenticationToken
(
userDetails
,
authorities
);
authenticatedToken
.
setDetails
(
authentication
.
getDetails
());
return
authenticatedToken
;
}
catch
(
Exception
e
)
{
throw
new
BadCredentialsException
(
"认证失败"
,
e
);
}
}
@Override
public
boolean
supports
(
Class
<?>
authentication
)
{
return
JwtAuthenticationToken
.
class
.
isAssignableFrom
(
authentication
);
}
}
yd-auth-core/src/main/java/com/yd/auth/core/security/JwtAuthenticationToken.java
deleted
100644 → 0
View file @
345cdf96
package
com
.
yd
.
auth
.
core
.
security
;
import
org.springframework.security.authentication.AbstractAuthenticationToken
;
import
org.springframework.security.core.GrantedAuthority
;
import
org.springframework.security.core.SpringSecurityCoreVersion
;
import
java.util.Collection
;
public
class
JwtAuthenticationToken
extends
AbstractAuthenticationToken
{
private
static
final
long
serialVersionUID
=
SpringSecurityCoreVersion
.
SERIAL_VERSION_UID
;
private
final
Object
principal
;
private
String
credentials
;
/**
* 用于未认证的令牌
*/
public
JwtAuthenticationToken
(
String
token
)
{
super
(
null
);
this
.
principal
=
token
;
this
.
credentials
=
token
;
setAuthenticated
(
false
);
}
/**
* 用于已认证的令牌
*/
public
JwtAuthenticationToken
(
Object
principal
,
Collection
<?
extends
GrantedAuthority
>
authorities
)
{
super
(
authorities
);
this
.
principal
=
principal
;
super
.
setAuthenticated
(
true
);
// must use super, as we override
}
@Override
public
Object
getCredentials
()
{
return
this
.
credentials
;
}
@Override
public
Object
getPrincipal
()
{
return
this
.
principal
;
}
@Override
public
void
setAuthenticated
(
boolean
isAuthenticated
)
throws
IllegalArgumentException
{
if
(
isAuthenticated
)
{
throw
new
IllegalArgumentException
(
"Cannot set this token to trusted - use constructor which takes a GrantedAuthority list instead"
);
}
super
.
setAuthenticated
(
false
);
}
@Override
public
void
eraseCredentials
()
{
super
.
eraseCredentials
();
credentials
=
null
;
}
}
yd-auth-core/src/main/java/com/yd/auth/core/security/JwtTokenProvider.java
View file @
de57dff1
...
...
@@ -8,7 +8,6 @@ import org.springframework.security.core.Authentication;
import
org.springframework.security.core.GrantedAuthority
;
import
org.springframework.security.core.userdetails.UserDetails
;
import
org.springframework.stereotype.Component
;
import
javax.crypto.SecretKey
;
import
java.util.Collection
;
import
java.util.Date
;
...
...
@@ -17,10 +16,10 @@ import java.util.stream.Collectors;
@Component
public
class
JwtTokenProvider
{
@Value
(
"${jwt.secret}"
)
@Value
(
"${jwt.secret
:1
}"
)
private
String
jwtSecret
;
@Value
(
"${jwt.expiration}"
)
@Value
(
"${jwt.expiration
:1
}"
)
private
int
jwtExpiration
;
public
String
generateToken
(
Authentication
authentication
)
{
...
...
@@ -41,6 +40,15 @@ public class JwtTokenProvider {
.
collect
(
Collectors
.
toList
());
}
public
String
getUserUidFromToken
(
String
token
)
{
return
Jwts
.
parserBuilder
()
.
setSigningKey
(
getSigningKey
())
.
build
()
.
parseClaimsJws
(
token
)
.
getBody
()
.
getSubject
();
}
public
String
getUsernameFromToken
(
String
token
)
{
return
Jwts
.
parserBuilder
()
.
setSigningKey
(
getSigningKey
())
...
...
yd-auth-core/src/main/java/com/yd/auth/core/service/AuthService.java
View file @
de57dff1
package
com
.
yd
.
auth
.
core
.
service
;
import
com.yd.auth.core.dto.LoginRequest
;
import
com.yd.auth.core.dto.LoginResponse
;
import
org.springframework.security.core.Authentication
;
import
com.yd.auth.core.request.LoginRequest
;
import
com.yd.auth.core.response.LoginResponse
;
public
interface
AuthService
{
LoginResponse
login
(
LoginRequest
loginRequest
);
void
logout
(
String
token
);
Authentication
getAuthentication
(
String
token
);
}
yd-auth-core/src/main/java/com/yd/auth/core/service/AuthUserDetailsService.java
deleted
100644 → 0
View file @
345cdf96
package
com
.
yd
.
auth
.
core
.
service
;
import
com.yd.auth.core.model.AuthUser
;
import
com.yd.user.api.dto.UserDTO
;
import
com.yd.user.api.feign.UserFeignClient
;
import
org.springframework.beans.factory.annotation.Autowired
;
import
org.springframework.security.core.authority.SimpleGrantedAuthority
;
import
org.springframework.security.core.userdetails.UserDetails
;
import
org.springframework.security.core.userdetails.UserDetailsService
;
import
org.springframework.security.core.userdetails.UsernameNotFoundException
;
import
org.springframework.stereotype.Service
;
import
java.util.stream.Collectors
;
@Service
public
class
AuthUserDetailsService
implements
UserDetailsService
{
private
final
UserFeignClient
userFeignClient
;
@Autowired
public
AuthUserDetailsService
(
UserFeignClient
userFeignClient
)
{
this
.
userFeignClient
=
userFeignClient
;
}
@Override
public
UserDetails
loadUserByUsername
(
String
username
)
throws
UsernameNotFoundException
{
// 通过Feign调用yd-user服务获取用户信息
UserDTO
user
=
userFeignClient
.
findByUsername
(
username
);
if
(
user
==
null
)
{
throw
new
UsernameNotFoundException
(
"用户不存在:"
+
username
);
}
// 转换为Spring Security用户对象
return
new
AuthUser
(
user
.
getId
(),
user
.
getUsername
(),
user
.
getPassword
(),
user
.
getRoles
().
stream
()
.
map
(
role
->
new
SimpleGrantedAuthority
(
role
))
// 修正类名
.
collect
(
Collectors
.
toList
())
);
}
}
yd-auth-core/src/main/java/com/yd/auth/core/service/UserService.java
deleted
100644 → 0
View file @
345cdf96
package
com
.
yd
.
auth
.
core
.
service
;
import
com.yd.user.service.entity.User
;
import
org.springframework.security.core.userdetails.UserDetails
;
import
org.springframework.security.core.userdetails.UserDetailsService
;
import
org.springframework.security.core.userdetails.UsernameNotFoundException
;
public
interface
UserService
extends
UserDetailsService
{
/**
* 根据用户名加载用户详情
*/
@Override
UserDetails
loadUserByUsername
(
String
username
)
throws
UsernameNotFoundException
;
/**
* 根据用户名查找用户
*/
User
findByUsername
(
String
username
);
/**
* 注册新用户
*/
User
register
(
User
user
);
}
yd-auth-core/src/main/java/com/yd/auth/core/service/impl/AuthServiceImpl.java
View file @
de57dff1
package
com
.
yd
.
auth
.
core
.
service
.
impl
;
import
com.yd.auth.core.
dto
.LoginRequest
;
import
com.yd.auth.core.
dto
.LoginResponse
;
import
com.yd.auth.core.
request
.LoginRequest
;
import
com.yd.auth.core.
response
.LoginResponse
;
import
com.yd.auth.core.security.JwtTokenProvider
;
import
com.yd.auth.core.service.AuthService
;
import
org.springframework.beans.factory.annotation.Autowired
;
...
...
@@ -24,43 +24,45 @@ public class AuthServiceImpl implements AuthService {
this
.
jwtTokenProvider
=
jwtTokenProvider
;
}
/**
* 用户登录认证方法(基于Spring Security的认证流程)
*
* @param loginRequest 登录请求对象(包含用户名和密码)
* @return 登录响应对象(包含JWT令牌和过期时间)
*/
@Override
public
LoginResponse
login
(
LoginRequest
loginRequest
)
{
// 1. 创建认证对象
// 1. 创建未认证的Authentication对象
// - 第一个参数:用户名(作为身份主体)
// - 第二个参数:原始密码(作为凭证)
Authentication
authentication
=
new
UsernamePasswordAuthenticationToken
(
loginRequest
.
getUsername
(),
loginRequest
.
getPassword
()
loginRequest
.
getUsername
(),
loginRequest
.
getPassword
()
);
// 2. 进行认证
// 2. 执行Spring Security认证流程(核心步骤)
// - 触发AuthUserDetailsService.loadUserByUsername()方法
// - 自动进行密码比对(使用配置的PasswordEncoder)
// - 成功返回已认证的Authentication对象,失败抛出AuthenticationException
Authentication
authenticated
=
authenticationManager
.
authenticate
(
authentication
);
// 3. 设置安全上下文
// 3. 将认证信息设置到SecurityContext
// - 使当前请求线程具有认证上下文
// - 后续操作可通过SecurityContextHolder获取当前用户
SecurityContextHolder
.
getContext
().
setAuthentication
(
authenticated
);
// 4. 生成令牌
// 4. 生成JWT令牌
// - 基于认证对象中的用户信息生成令牌
// - 令牌中包含用户标识和权限信息
String
token
=
jwtTokenProvider
.
generateToken
(
authenticated
);
// 5.
创建
响应对象
// 5.
构建登录
响应对象
LoginResponse
response
=
new
LoginResponse
();
response
.
setToken
(
token
);
response
.
setExpiresIn
(
jwtTokenProvider
.
getJwtExpiration
());
return
response
;
}
response
.
setToken
(
token
);
// 设置生成的JWT令牌
response
.
setExpiresIn
(
jwtTokenProvider
.
getJwtExpiration
());
// 设置令牌过期时间
@Override
public
void
logout
(
String
token
)
{
// 实现令牌失效逻辑(可选)
// 实际应用中可能需要将令牌加入黑名单
SecurityContextHolder
.
clearContext
();
return
response
;
}
@Override
public
Authentication
getAuthentication
(
String
token
)
{
if
(
jwtTokenProvider
.
validateToken
(
token
))
{
return
jwtTokenProvider
.
getAuthentication
(
token
);
}
return
null
;
}
}
yd-auth-core/src/main/java/com/yd/auth/core/service/impl/AuthUserDetailsService.java
0 → 100644
View file @
de57dff1
package
com
.
yd
.
auth
.
core
.
service
.
impl
;
import
com.yd.auth.core.dto.AuthUserDto
;
import
com.yd.user.service.model.SysUser
;
import
com.yd.user.service.service.ISysUserService
;
import
org.springframework.beans.BeanUtils
;
import
org.springframework.beans.factory.annotation.Autowired
;
import
org.springframework.security.core.userdetails.UserDetails
;
import
org.springframework.security.core.userdetails.UserDetailsService
;
import
org.springframework.security.core.userdetails.UsernameNotFoundException
;
import
org.springframework.stereotype.Service
;
import
java.util.Objects
;
/**
* authenticationManager.authenticate(authentication) -->进行spring security 登录认证
* --> spring security 登录认证会走到这里去获取用户表的数据进行用户名和密码对比返回最后认证是否成功的结果
*/
@Service
public
class
AuthUserDetailsService
implements
UserDetailsService
{
@Autowired
private
ISysUserService
iSysUserService
;
@Override
public
UserDetails
loadUserByUsername
(
String
username
)
throws
UsernameNotFoundException
{
//Spring Security用户认证对象
AuthUserDto
authUserDto
=
null
;
// 通过Feign调用yd-user-service服务获取用户信息
SysUser
sysUser
=
iSysUserService
.
queryOneByName
(
username
);
if
(
Objects
.
isNull
(
sysUser
))
{
throw
new
UsernameNotFoundException
(
"用户不存在"
);
}
authUserDto
=
new
AuthUserDto
();
BeanUtils
.
copyProperties
(
sysUser
,
authUserDto
);
// 查询用户角色 TODO
// authUserDto.setRoles(roles);
return
authUserDto
;
}
}
yd-auth-core/src/main/java/com/yd/auth/core/utils/JwtUtils.java
deleted
100644 → 0
View file @
345cdf96
package
com
.
yd
.
auth
.
core
.
utils
;
import
io.jsonwebtoken.*
;
import
io.jsonwebtoken.security.Keys
;
import
org.springframework.beans.factory.annotation.Value
;
import
org.springframework.security.core.GrantedAuthority
;
import
org.springframework.security.core.userdetails.UserDetails
;
import
org.springframework.stereotype.Component
;
import
javax.crypto.SecretKey
;
import
java.nio.charset.StandardCharsets
;
import
java.util.*
;
import
java.util.function.Function
;
import
java.util.stream.Collectors
;
@Component
public
class
JwtUtils
{
@Value
(
"${jwt.secret}"
)
private
String
secret
;
@Value
(
"${jwt.expiration}"
)
private
Long
expiration
;
@Value
(
"${jwt.refresh-expiration}"
)
private
Long
refreshExpiration
;
/**
* 生成JWT令牌
*/
public
String
generateToken
(
UserDetails
userDetails
)
{
Map
<
String
,
Object
>
claims
=
new
HashMap
<
String
,
Object
>();
// 添加用户角色
claims
.
put
(
"roles"
,
userDetails
.
getAuthorities
().
stream
()
.
map
(
GrantedAuthority:
:
getAuthority
)
.
collect
(
Collectors
.
toList
()));
return
createToken
(
claims
,
userDetails
.
getUsername
(),
expiration
);
}
/**
* 生成刷新令牌
*/
public
String
generateRefreshToken
(
UserDetails
userDetails
)
{
Map
<
String
,
Object
>
claims
=
new
HashMap
<>();
return
createToken
(
claims
,
userDetails
.
getUsername
(),
refreshExpiration
);
}
/**
* 创建JWT令牌
*/
private
String
createToken
(
Map
<
String
,
Object
>
claims
,
String
subject
,
Long
expirationTime
)
{
SecretKey
key
=
Keys
.
hmacShaKeyFor
(
secret
.
getBytes
(
StandardCharsets
.
UTF_8
));
return
Jwts
.
builder
()
.
setClaims
(
claims
)
.
setSubject
(
subject
)
.
setIssuedAt
(
new
Date
(
System
.
currentTimeMillis
()))
.
setExpiration
(
new
Date
(
System
.
currentTimeMillis
()
+
expirationTime
*
1000
))
.
signWith
(
key
,
SignatureAlgorithm
.
HS256
)
.
compact
();
}
/**
* 解析JWT令牌
*/
public
Claims
parseToken
(
String
token
)
{
SecretKey
key
=
Keys
.
hmacShaKeyFor
(
secret
.
getBytes
(
StandardCharsets
.
UTF_8
));
try
{
return
Jwts
.
parserBuilder
()
.
setSigningKey
(
key
)
.
build
()
.
parseClaimsJws
(
token
)
.
getBody
();
}
catch
(
ExpiredJwtException
e
)
{
throw
new
RuntimeException
(
"令牌已过期"
,
e
);
}
catch
(
UnsupportedJwtException
e
)
{
throw
new
RuntimeException
(
"不支持的令牌"
,
e
);
}
catch
(
MalformedJwtException
e
)
{
throw
new
RuntimeException
(
"无效的令牌"
,
e
);
}
catch
(
SignatureException
e
)
{
throw
new
RuntimeException
(
"签名验证失败"
,
e
);
}
catch
(
IllegalArgumentException
e
)
{
throw
new
RuntimeException
(
"令牌参数错误"
,
e
);
}
}
/**
* 从令牌中获取用户名
*/
public
String
getUsernameFromToken
(
String
token
)
{
return
parseToken
(
token
).
getSubject
();
}
/**
* 从令牌中获取过期时间
*/
public
Date
getExpirationDateFromToken
(
String
token
)
{
return
parseToken
(
token
).
getExpiration
();
}
/**
* 检查令牌是否过期
*/
public
Boolean
isTokenExpired
(
String
token
)
{
final
Date
expiration
=
getExpirationDateFromToken
(
token
);
return
expiration
.
before
(
new
Date
());
}
/**
* 验证令牌
*/
public
Boolean
validateToken
(
String
token
,
UserDetails
userDetails
)
{
final
String
username
=
getUsernameFromToken
(
token
);
return
(
username
.
equals
(
userDetails
.
getUsername
())
&&
!
isTokenExpired
(
token
));
}
public
Boolean
validateToken
(
String
token
)
{
try
{
// 解析token
Claims
claims
=
parseToken
(
token
);
// 检查是否过期
return
!
isTokenExpired
(
token
);
}
catch
(
Exception
e
)
{
return
false
;
}
}
/**
* 从令牌中获取角色
*/
public
List
<
String
>
getRolesFromToken
(
String
token
)
{
Claims
claims
=
parseToken
(
token
);
return
claims
.
get
(
"roles"
,
List
.
class
);
}
/**
* 从令牌中获取指定的声明
*/
public
<
T
>
T
getClaimFromToken
(
String
token
,
Function
<
Claims
,
T
>
claimsResolver
)
{
final
Claims
claims
=
parseToken
(
token
);
return
claimsResolver
.
apply
(
claims
);
}
}
yd-common/pom.xml
View file @
de57dff1
...
...
@@ -14,11 +14,6 @@
<description>
公共组件模块
</description>
<dependencies>
<!-- SpringCloud Openfeign -->
<dependency>
<groupId>
org.springframework.cloud
</groupId>
<artifactId>
spring-cloud-starter-openfeign
</artifactId>
</dependency>
<!-- 测试 -->
<dependency>
<groupId>
org.springframework.boot
</groupId>
...
...
@@ -37,5 +32,13 @@
<groupId>
org.springframework.boot
</groupId>
<artifactId>
spring-boot-starter-validation
</artifactId>
</dependency>
<dependency>
<groupId>
org.springframework.cloud
</groupId>
<artifactId>
spring-cloud-starter-openfeign
</artifactId>
</dependency>
<dependency>
<groupId>
org.apache.commons
</groupId>
<artifactId>
commons-lang3
</artifactId>
</dependency>
</dependencies>
</project>
yd-common/src/main/java/com/yd/common/dto/PageDto.java
0 → 100644
View file @
de57dff1
package
com
.
yd
.
common
.
dto
;
import
lombok.Data
;
@Data
public
class
PageDto
{
private
Integer
pageNo
=
1
;
private
Integer
pageSize
=
10
;
}
yd-common/src/main/java/com/yd/common/enums/CommonEnum.java
0 → 100644
View file @
de57dff1
package
com
.
yd
.
common
.
enums
;
/**
* 公共枚举
*/
public
enum
CommonEnum
{
//业务唯一标识id的类型
UID_TYPE_TENANT
(
"tenant"
,
"租户"
),
UID_TYPE_PROJECT
(
"project"
,
"项目"
),
UID_TYPE_USER
(
"user"
,
"用户"
),
UID_TYPE_ROLE
(
"role"
,
"角色"
),
UID_TYPE_MENU
(
"menu"
,
"菜单"
),
;
//编码
private
String
code
;
//名称
private
String
name
;
//构造函数
CommonEnum
(
String
code
,
String
name
)
{
this
.
code
=
code
;
this
.
name
=
name
;
}
public
String
getCode
()
{
return
code
;
}
public
String
getName
()
{
return
name
;
}
}
yd-common/src/main/java/com/yd/common/enums/ResultCode.java
0 → 100644
View file @
de57dff1
package
com
.
yd
.
common
.
enums
;
/**
* 返回码
*
* @author zxm
*/
public
enum
ResultCode
{
SUCCESS
(
200
,
"操作成功"
,
""
)
,
FAIL
(
500
,
"操作失败"
,
""
)
,
NULL_ERROR
(
201
,
"数据不存在"
,
""
)
,
TENANT_NAME_EXISTS
(
202
,
"租户名称已存在"
,
""
)
,
PARAM_CHECK_ERROR
(
4001
,
"参数校验异常"
,
""
),
;
//返回码
private
final
int
code
;
//操作响应信息
private
final
String
message
;
//响应信息的详细描述
private
final
String
description
;
//构造函数
ResultCode
(
int
code
,
String
message
,
String
description
)
{
this
.
code
=
code
;
this
.
message
=
message
;
this
.
description
=
description
;
}
//get方法
public
int
getCode
()
{
return
code
;
}
public
String
getMessage
()
{
return
message
;
}
public
String
getDescription
()
{
return
description
;
}
}
yd-common/src/main/java/com/yd/common/result/Result.java
View file @
de57dff1
...
...
@@ -17,7 +17,17 @@ public class Result<T> implements Serializable {
private
Result
()
{}
/**
* 成功返回
* 成功返回(不带上数据)
*/
public
static
<
T
>
Result
<
T
>
success
()
{
Result
<
T
>
result
=
new
Result
<
T
>();
result
.
setCode
(
200
);
result
.
setMsg
(
"操作成功"
);
return
result
;
}
/**
* 成功返回(带上数据)
*/
public
static
<
T
>
Result
<
T
>
success
(
T
data
)
{
Result
<
T
>
result
=
new
Result
<
T
>();
...
...
yd-common/src/main/java/com/yd/common/utils/RandomStringGenerator.java
0 → 100644
View file @
de57dff1
package
com
.
yd
.
common
.
utils
;
import
com.yd.common.enums.CommonEnum
;
import
java.security.SecureRandom
;
import
java.util.Random
;
public
class
RandomStringGenerator
{
// 包含所有数字和字母(大小写)的字符池
private
static
final
String
CHAR_POOL
=
"0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz"
;
private
static
final
SecureRandom
secureRandom
=
new
SecureRandom
();
private
static
final
Random
random
=
new
Random
();
/**
* 生成随机字符串
* @param length 字符串长度
* @param useSecureRandom 是否使用安全随机生成器
* @return 随机字符串
*/
public
static
String
generate
(
int
length
,
boolean
useSecureRandom
)
{
StringBuilder
sb
=
new
StringBuilder
(
length
);
Random
rand
=
useSecureRandom
?
secureRandom
:
random
;
for
(
int
i
=
0
;
i
<
length
;
i
++)
{
// 从字符池中随机选取字符
int
randomIndex
=
rand
.
nextInt
(
CHAR_POOL
.
length
());
sb
.
append
(
CHAR_POOL
.
charAt
(
randomIndex
));
}
return
sb
.
toString
();
}
/**
* 生成(业务标识类型+32位随机字符串)业务唯一标识id
* @param uidType 业务标识类型
* @return 业务标识类型+32位随机字符串
*/
public
static
String
generateUid32
(
String
uidType
)
{
return
uidType
+
"_"
+
generate
(
32
,
true
);
}
/**
* 生成(业务标识类型+16位随机字符串)业务唯一标识id
* @param uidType 业务标识类型
* @return 业务标识类型+16位随机字符串
*/
public
static
String
generateUid16
(
String
uidType
)
{
return
uidType
+
"_"
+
generate
(
16
,
true
);
}
public
static
void
main
(
String
[]
args
)
{
// 生成16位随机字符串(使用安全随机)
String
random16
=
generate
(
16
,
true
);
System
.
out
.
println
(
"16位: "
+
random16
);
// 生成32位随机字符串(使用普通随机)
String
random32
=
generate
(
32
,
false
);
System
.
out
.
println
(
"32位: "
+
random32
);
System
.
out
.
println
(
generateUid16
(
CommonEnum
.
UID_TYPE_USER
.
getCode
()));
}
}
yd-feign/pom.xml
View file @
de57dff1
...
...
@@ -12,18 +12,6 @@
<artifactId>
yd-feign
</artifactId>
<name>
yd-feign
</name>
<description>
Feign组件模块
</description>
<build>
<plugins>
<plugin>
<groupId>
org.apache.maven.plugins
</groupId>
<artifactId>
maven-compiler-plugin
</artifactId>
<configuration>
<source>
8
</source>
<target>
8
</target>
</configuration>
</plugin>
</plugins>
</build>
<dependencies>
<dependency>
...
...
@@ -31,10 +19,6 @@
<artifactId>
spring-cloud-starter-openfeign
</artifactId>
</dependency>
<dependency>
<groupId>
com.yd
</groupId>
<artifactId>
yd-common
</artifactId>
</dependency>
<dependency>
<groupId>
org.springframework.boot
</groupId>
<artifactId>
spring-boot-starter-web
</artifactId>
<optional>
true
</optional>
...
...
yd-feign/src/main/java/com/yd/feign/client/UserFeignClient.java
deleted
100644 → 0
View file @
345cdf96
package
com
.
yd
.
feign
.
client
;
import
com.yd.common.entity.UserDetails
;
import
com.yd.common.result.Result
;
import
com.yd.feign.client.fallback.UserFeignFallbackFactory
;
import
org.springframework.cloud.openfeign.FeignClient
;
import
org.springframework.web.bind.annotation.GetMapping
;
import
org.springframework.web.bind.annotation.RequestParam
;
/**
* 用户服务Feign客户端
*/
@FeignClient
(
name
=
"yd-user-service"
,
fallbackFactory
=
UserFeignFallbackFactory
.
class
)
public
interface
UserFeignClient
{
/**
* 根据用户名获取用户信息
*/
@GetMapping
(
"/user/getByUsername"
)
Result
<
UserDetails
>
getByUsername
(
@RequestParam
(
"username"
)
String
username
);
}
yd-feign/src/main/java/com/yd/feign/client/fallback/UserFeignFallbackFactory.java
deleted
100644 → 0
View file @
345cdf96
package
com
.
yd
.
feign
.
client
.
fallback
;
import
com.yd.common.entity.UserDetails
;
import
com.yd.common.exception.BusinessException
;
import
com.yd.common.result.Result
;
import
com.yd.feign.client.UserFeignClient
;
import
lombok.extern.slf4j.Slf4j
;
import
org.springframework.cloud.openfeign.FallbackFactory
;
import
org.springframework.stereotype.Component
;
/**
* 用户服务Feign降级处理
*/
@Slf4j
@Component
public
class
UserFeignFallbackFactory
implements
FallbackFactory
<
UserFeignClient
>
{
public
UserFeignClient
create
(
final
Throwable
cause
)
{
return
new
UserFeignClient
()
{
public
Result
<
UserDetails
>
getByUsername
(
String
username
)
{
log
.
error
(
"调用用户服务失败: {}"
,
cause
.
getMessage
());
throw
new
BusinessException
(
"获取用户信息失败,请稍后重试"
);
}
};
}
}
yd-framework/src/main/java/com/yd/framework/handler/GlobalExceptionHandler.java
View file @
de57dff1
package
com
.
yd
.
framework
.
handler
;
import
com.yd.common.enums.ResultCode
;
import
com.yd.common.exception.BusinessException
;
import
com.yd.common.result.Result
;
import
lombok.extern.slf4j.Slf4j
;
...
...
@@ -9,6 +10,9 @@ import org.springframework.web.bind.MethodArgumentNotValidException;
import
org.springframework.web.bind.annotation.ExceptionHandler
;
import
org.springframework.web.bind.annotation.RestControllerAdvice
;
import
javax.validation.ConstraintViolationException
;
import
java.util.stream.Collectors
;
//import com.yd.common.model.R;
//import org.springframework.http.HttpStatus;
//import org.springframework.security.authentication.BadCredentialsException;
...
...
@@ -33,6 +37,7 @@ public class GlobalExceptionHandler {
}
/**
* @Validated校验器触发的异常 @RequestBody对象校验
* 处理参数校验异常
*/
@ExceptionHandler
(
MethodArgumentNotValidException
.
class
)
...
...
@@ -40,8 +45,21 @@ public class GlobalExceptionHandler {
BindingResult
bindingResult
=
e
.
getBindingResult
();
FieldError
fieldError
=
bindingResult
.
getFieldError
();
String
message
=
fieldError
!=
null
?
fieldError
.
getDefaultMessage
()
:
"参数校验失败"
;
log
.
error
(
"参数校验异常: {}"
,
message
);
return
Result
.
fail
(
400
,
message
);
log
.
error
(
"RequestBody参数校验异常: {}"
,
message
);
return
Result
.
fail
(
ResultCode
.
PARAM_CHECK_ERROR
.
getCode
(),
message
);
}
/**
* @Validated校验器触发的异常 RequestParam 参数校验
* @param e
* @return
*/
@ExceptionHandler
(
ConstraintViolationException
.
class
)
public
Result
<?>
constraintViolationExceptionHandler
(
ConstraintViolationException
e
){
String
message
=
e
.
getConstraintViolations
().
stream
().
collect
(
Collectors
.
toList
()).
get
(
0
).
getMessage
();
log
.
error
(
"RequestParam参数校验异常:{}"
,
e
);
return
Result
.
fail
(
ResultCode
.
PARAM_CHECK_ERROR
.
getCode
(),
message
);
}
/**
...
...
@@ -53,6 +71,9 @@ public class GlobalExceptionHandler {
return
Result
.
fail
(
"系统异常,请联系管理员"
);
}
// @ExceptionHandler(BadCredentialsException.class)
// @ResponseStatus(HttpStatus.UNAUTHORIZED)
// public R<?> handleBadCredentialsException(BadCredentialsException e) {
...
...
yd-gateway/src/main/java/com/yd/gateway/config/GatewayConfig.java
deleted
100644 → 0
View file @
345cdf96
package
com
.
yd
.
gateway
.
config
;
import
org.springframework.cloud.gateway.route.RouteLocator
;
import
org.springframework.cloud.gateway.route.builder.RouteLocatorBuilder
;
import
org.springframework.context.annotation.Bean
;
import
org.springframework.context.annotation.Configuration
;
/**
* 网关路由配置
*/
@Configuration
public
class
GatewayConfig
{
@Bean
public
RouteLocator
customRouteLocator
(
RouteLocatorBuilder
builder
)
{
return
builder
.
routes
()
// 认证服务路由
.
route
(
"yd-auth-service"
,
r
->
r
.
path
(
"/auth/**"
)
.
uri
(
"lb://yd-auth-service"
))
// 用户服务路由
.
route
(
"yd-user-service"
,
r
->
r
.
path
(
"/user/**"
)
.
uri
(
"lb://yd-user-service"
))
// SCRM服务路由
.
route
(
"yd-scrm-service"
,
r
->
r
.
path
(
"/scrm/**"
)
.
uri
(
"lb://yd-scrm-service"
))
.
build
();
}
}
yd-gateway/src/main/java/com/yd/gateway/filter/AuthenticationFilter.java
deleted
100644 → 0
View file @
345cdf96
package
com
.
yd
.
gateway
.
filter
;
import
com.yd.auth.core.security.DummyAuthenticationManager
;
import
com.yd.auth.core.utils.JwtUtils
;
import
com.yd.common.exception.BusinessException
;
import
com.yd.common.result.Result
;
import
io.jsonwebtoken.Claims
;
import
org.springframework.core.io.buffer.DataBuffer
;
import
org.springframework.http.HttpHeaders
;
import
org.springframework.http.HttpStatus
;
import
org.springframework.http.MediaType
;
import
org.springframework.http.server.reactive.ServerHttpRequest
;
import
org.springframework.security.authentication.UsernamePasswordAuthenticationToken
;
import
org.springframework.security.core.AuthenticationException
;
import
org.springframework.security.core.authority.SimpleGrantedAuthority
;
import
org.springframework.security.web.server.WebFilterExchange
;
import
org.springframework.security.web.server.authentication.AuthenticationWebFilter
;
import
org.springframework.security.web.server.authentication.ServerAuthenticationConverter
;
import
org.springframework.stereotype.Component
;
import
org.springframework.web.server.ServerWebExchange
;
import
reactor.core.publisher.Mono
;
import
com.alibaba.fastjson.JSON
;
import
java.nio.charset.StandardCharsets
;
import
java.util.ArrayList
;
import
java.util.List
;
import
java.util.stream.Collectors
;
/**
* 网关认证过滤器
*/
@Component
public
class
AuthenticationFilter
extends
AuthenticationWebFilter
{
private
final
JwtUtils
jwtUtils
;
public
AuthenticationFilter
(
JwtUtils
jwtUtils
)
{
super
(
new
DummyAuthenticationManager
());
this
.
jwtUtils
=
jwtUtils
;
setServerAuthenticationConverter
(
jwtAuthenticationConverter
());
}
/**
* JWT认证转换器
*/
private
ServerAuthenticationConverter
jwtAuthenticationConverter
()
{
return
exchange
->
{
ServerHttpRequest
request
=
exchange
.
getRequest
();
String
token
=
getTokenFromRequest
(
request
);
if
(
token
==
null
)
{
return
Mono
.
error
(
new
BusinessException
(
"未提供令牌"
));
}
try
{
// 验证令牌
if
(!
jwtUtils
.
validateToken
(
token
))
{
return
Mono
.
error
(
new
BusinessException
(
"无效的令牌"
));
}
// 解析令牌
Claims
claims
=
jwtUtils
.
parseToken
(
token
);
String
username
=
claims
.
getSubject
();
// 获取角色信息
List
<
String
>
roles
=
(
List
<
String
>)
claims
.
get
(
"roles"
);
List
<
SimpleGrantedAuthority
>
authorities
=
new
ArrayList
<>();
if
(
roles
!=
null
&&
!
roles
.
isEmpty
())
{
authorities
=
roles
.
stream
()
.
map
(
role
->
new
SimpleGrantedAuthority
(
"ROLE_"
+
role
))
.
collect
(
Collectors
.
toList
());
}
// 设置认证信息
UsernamePasswordAuthenticationToken
authentication
=
new
UsernamePasswordAuthenticationToken
(
username
,
null
,
authorities
);
return
Mono
.
just
(
authentication
);
}
catch
(
Exception
e
)
{
return
Mono
.
error
(
new
BusinessException
(
e
.
getMessage
()));
}
};
}
/**
* 从请求头中获取令牌
*/
private
String
getTokenFromRequest
(
ServerHttpRequest
request
)
{
String
bearerToken
=
request
.
getHeaders
().
getFirst
(
HttpHeaders
.
AUTHORIZATION
);
if
(
bearerToken
!=
null
&&
bearerToken
.
startsWith
(
"Bearer "
))
{
return
bearerToken
.
substring
(
7
);
}
return
null
;
}
/**
* 处理认证失败
*/
protected
Mono
<
Void
>
onAuthenticationFailure
(
WebFilterExchange
webFilterExchange
,
AuthenticationException
exception
)
{
ServerWebExchange
exchange
=
webFilterExchange
.
getExchange
();
exchange
.
getResponse
().
setStatusCode
(
HttpStatus
.
UNAUTHORIZED
);
exchange
.
getResponse
().
getHeaders
().
setContentType
(
MediaType
.
APPLICATION_JSON
);
Result
<?>
result
=
Result
.
fail
(
401
,
exception
.
getMessage
());
byte
[]
bytes
=
JSON
.
toJSONString
(
result
).
getBytes
(
StandardCharsets
.
UTF_8
);
DataBuffer
buffer
=
exchange
.
getResponse
().
bufferFactory
().
wrap
(
bytes
);
return
exchange
.
getResponse
().
writeWith
(
Mono
.
just
(
buffer
));
}
}
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment