Commit 5a6b4fd4 authored by matevip's avatar matevip Committed by Gitee
Browse files

!3 同步1.3.8发布部分bug

Merge pull request !3 from matevip/dev
Showing with 587 additions and 547 deletions
+587 -547
This diff is collapsed.
package vip.mate.core.security.handle;
import com.fasterxml.jackson.databind.ObjectMapper;
import lombok.AllArgsConstructor;
import lombok.NonNull;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
......@@ -14,7 +13,6 @@ import org.springframework.security.oauth2.common.exceptions.UnapprovedClientAut
import org.springframework.security.oauth2.provider.*;
import org.springframework.security.oauth2.provider.token.AuthorizationServerTokenServices;
import org.springframework.security.web.authentication.AuthenticationSuccessHandler;
import org.springframework.stereotype.Component;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
......
......@@ -8,6 +8,7 @@ import org.aspectj.lang.annotation.Aspect;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.http.HttpMethod;
import org.springframework.stereotype.Component;
import org.springframework.util.AntPathMatcher;
import vip.mate.core.common.exception.PreviewException;
import vip.mate.core.common.util.RequestHolder;
import vip.mate.core.common.util.TraceUtil;
......@@ -24,7 +25,9 @@ import javax.servlet.http.HttpServletRequest;
public class PreviewAspect {
@Value("${mate.preview.enable}")
private boolean isPreview = false;
private final boolean isPreview = false;
private final AntPathMatcher antPathMatcher = new AntPathMatcher();
@Around(
"execution(static vip.mate.core.common.api.Result *(..)) || " +
......@@ -35,7 +38,7 @@ public class PreviewAspect {
// 获取request
HttpServletRequest request = RequestHolder.getHttpServletRequest();
if (StringUtils.equalsIgnoreCase(request.getMethod(), HttpMethod.POST.name()) && isPreview
&& !(StringUtils.equalsIgnoreCase(request.getRequestURI(), "/provider/log/save"))) {
&& !(antPathMatcher.match(request.getRequestURI(), "/provider/log/set"))) {
log.error("演示环境不能操作!");
throw new PreviewException("演示环境不能操作!");
}
......
......@@ -37,6 +37,8 @@ import vip.mate.uaa.service.impl.UserDetailsServiceImpl;
import vip.mate.uaa.sms.SmsCodeAuthenticationSecurityConfig;
import vip.mate.uaa.social.SocialAuthenticationSecurityConfig;
import javax.annotation.Resource;
/**
* 安全配置中心
*
......@@ -46,76 +48,77 @@ import vip.mate.uaa.social.SocialAuthenticationSecurityConfig;
@EnableWebSecurity
public class SecurityConfig extends WebSecurityConfigurerAdapter {
@Autowired
private IgnoreUrlPropsConfig ignoreUrlPropsConfig;
@Autowired
private IgnoreUrlPropsConfig ignoreUrlPropsConfig;
@Bean
public PasswordEncoder passwordEncoder() {
return PasswordEncoderFactories.createDelegatingPasswordEncoder();
}
@Bean
public PasswordEncoder passwordEncoder() {
return PasswordEncoderFactories.createDelegatingPasswordEncoder();
}
@Autowired
private SmsCodeAuthenticationSecurityConfig smsCodeAuthenticationSecurityConfig;
@Resource
private SmsCodeAuthenticationSecurityConfig smsCodeAuthenticationSecurityConfig;
@Autowired
private SocialAuthenticationSecurityConfig socialAuthenticationSecurityConfig;
@Resource
private SocialAuthenticationSecurityConfig socialAuthenticationSecurityConfig;
/**
* 必须要定义,否则不支持grant_type=password模式
* @return
*/
@Bean
@Override
@SneakyThrows
public AuthenticationManager authenticationManagerBean() {
return super.authenticationManagerBean();
}
/**
* 必须要定义,否则不支持grant_type=password模式
*
* @return AuthenticationManager
*/
@Bean
@Override
@SneakyThrows
public AuthenticationManager authenticationManagerBean() {
return super.authenticationManagerBean();
}
@Bean
public AuthenticationSuccessHandler mateAuthenticationSuccessHandler() {
return new MateAuthenticationSuccessHandler();
}
@Bean
public AuthenticationSuccessHandler mateAuthenticationSuccessHandler() {
return new MateAuthenticationSuccessHandler();
}
@Bean
public AuthenticationFailureHandler mateAuthenticationFailureHandler() {
return new MateAuthenticationFailureHandler();
}
@Bean
public AuthenticationFailureHandler mateAuthenticationFailureHandler() {
return new MateAuthenticationFailureHandler();
}
@Override
@Bean
public UserDetailsService userDetailsService() {
return new UserDetailsServiceImpl();
}
@Override
@Bean
public UserDetailsService userDetailsService() {
return new UserDetailsServiceImpl();
}
@Override
protected void configure(HttpSecurity http) throws Exception {
ExpressionUrlAuthorizationConfigurer<HttpSecurity>.ExpressionInterceptUrlRegistry config
= http.requestMatchers().anyRequest()
.and()
.apply(smsCodeAuthenticationSecurityConfig)
.and()
.apply(socialAuthenticationSecurityConfig)
.and()
.authorizeRequests();
ignoreUrlPropsConfig.getUrls().forEach(e -> {
config.antMatchers(e).permitAll();
});
config
.antMatchers("/auth/**").permitAll()
.antMatchers("/oauth/**").permitAll()
.antMatchers("/actuator/**").permitAll()
.antMatchers("/v2/api-docs").permitAll()
.antMatchers("/v2/api-docs-ext").permitAll()
.anyRequest().authenticated()
.and()
.csrf().disable();
}
@Override
protected void configure(HttpSecurity http) throws Exception {
ExpressionUrlAuthorizationConfigurer<HttpSecurity>.ExpressionInterceptUrlRegistry config
= http.requestMatchers().anyRequest()
.and()
.apply(smsCodeAuthenticationSecurityConfig)
.and()
.apply(socialAuthenticationSecurityConfig)
.and()
.authorizeRequests();
ignoreUrlPropsConfig.getUrls().forEach(e -> {
config.antMatchers(e).permitAll();
});
config
.antMatchers("/auth/**").permitAll()
.antMatchers("/oauth/**").permitAll()
.antMatchers("/actuator/**").permitAll()
.antMatchers("/v2/api-docs").permitAll()
.antMatchers("/v2/api-docs-ext").permitAll()
.anyRequest().authenticated()
.and()
.csrf().disable();
}
@Override
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
auth.
userDetailsService(userDetailsService())
.passwordEncoder(passwordEncoder());
}
@Override
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
auth.
userDetailsService(userDetailsService())
.passwordEncoder(passwordEncoder());
}
}
......@@ -137,7 +137,7 @@ public class AuthController {
*
* @param oauthType 第三方登录类型
* @param response response
* @throws IOException
* @throws IOException IO异常
*/
@Log(value = "第三方登录", exception = "第三方登录请求异常")
@ApiOperation(value = "第三方登录", notes = "第三方登录")
......@@ -152,7 +152,6 @@ public class AuthController {
*
* @param oauthType 第三方登录类型
* @param callback 携带返回的信息
* @return 登录成功后的信息
*/
@Log(value = "第三方登录回调", exception = "第三方登录回调请求异常")
@ApiOperation(value = "第三方登录回调", notes = "第三方登录回调")
......
......@@ -12,62 +12,68 @@ import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.util.Objects;
/**
* 短信验证码验证过滤器
*
* @author pangu
*/
public class SmsCodeAuthenticationFilter extends AbstractAuthenticationProcessingFilter {
/**
* 请求中的参数
*/
private String mobileParameter = Oauth2Constant.DEFAULT_PARAMETER_NAME_MOBILE;
/**
* 请求中的参数
*/
private String mobileParameter = Oauth2Constant.DEFAULT_PARAMETER_NAME_MOBILE;
private boolean postOnly = true;
private boolean postOnly = true;
public SmsCodeAuthenticationFilter() {
super(new AntPathRequestMatcher(Oauth2Constant.OAUTH_MOBILE, "POST"));
}
public SmsCodeAuthenticationFilter() {
super(new AntPathRequestMatcher(Oauth2Constant.OAUTH_MOBILE, "POST"));
}
public Authentication attemptAuthentication(HttpServletRequest request, HttpServletResponse response) throws AuthenticationException {
if (postOnly && !request.getMethod().equals("POST")) {
throw new AuthenticationServiceException("Authentication method not supported: " + request.getMethod());
}
@Override
public Authentication attemptAuthentication(HttpServletRequest request, HttpServletResponse response) throws AuthenticationException {
if (postOnly && !request.getMethod().equals("POST")) {
throw new AuthenticationServiceException("Authentication method not supported: " + request.getMethod());
}
// 获取请求中的参数值
String mobile = obtainMobile(request);
// 获取请求中的参数值
String mobile = obtainMobile(request);
if (Objects.isNull(mobile)) {
mobile = "";
}
if (Objects.isNull(mobile)) {
mobile = "";
}
mobile = mobile.trim();
mobile = mobile.trim();
SmsCodeAuthenticationToken authRequest = new SmsCodeAuthenticationToken(mobile);
SmsCodeAuthenticationToken authRequest = new SmsCodeAuthenticationToken(mobile);
// Allow subclasses to set the "details" property
setDetails(request, authRequest);
// Allow subclasses to set the "details" property
setDetails(request, authRequest);
return this.getAuthenticationManager().authenticate(authRequest);
}
return this.getAuthenticationManager().authenticate(authRequest);
}
/**
* 获取手机号
*/
protected String obtainMobile(HttpServletRequest request) {
return request.getParameter(mobileParameter);
}
/**
* 获取手机号
*/
protected String obtainMobile(HttpServletRequest request) {
return request.getParameter(mobileParameter);
}
protected void setDetails(HttpServletRequest request, SmsCodeAuthenticationToken authRequest) {
authRequest.setDetails(authenticationDetailsSource.buildDetails(request));
}
protected void setDetails(HttpServletRequest request, SmsCodeAuthenticationToken authRequest) {
authRequest.setDetails(authenticationDetailsSource.buildDetails(request));
}
public void setMobileParameter(String mobileParameter) {
Assert.hasText(mobileParameter, "Mobile parameter must not be empty or null");
this.mobileParameter = mobileParameter;
}
public void setMobileParameter(String mobileParameter) {
Assert.hasText(mobileParameter, "Mobile parameter must not be empty or null");
this.mobileParameter = mobileParameter;
}
public void setPostOnly(boolean postOnly) {
this.postOnly = postOnly;
}
public void setPostOnly(boolean postOnly) {
this.postOnly = postOnly;
}
public final String getMobileParameter() {
return mobileParameter;
}
public final String getMobileParameter() {
return mobileParameter;
}
}
......@@ -11,34 +11,39 @@ import vip.mate.core.security.userdetails.MateUserDetailsService;
import java.util.Objects;
/**
* 短信验证码验证提供者
*
* @author pangu
*/
@AllArgsConstructor
public class SmsCodeAuthenticationProvider implements AuthenticationProvider {
private final MateUserDetailsService userDetailsService;
private final MateUserDetailsService userDetailsService;
@Override
public Authentication authenticate(Authentication authentication) throws AuthenticationException {
SmsCodeAuthenticationToken authenticationToken = (SmsCodeAuthenticationToken) authentication;
@Override
public Authentication authenticate(Authentication authentication) throws AuthenticationException {
SmsCodeAuthenticationToken authenticationToken = (SmsCodeAuthenticationToken) authentication;
/**
* 调用 {@link UserDetailsService}
*/
UserDetails user = userDetailsService.loadUserByMobile((String)authenticationToken.getPrincipal());
/**
* 调用 {@link UserDetailsService}
*/
UserDetails user = userDetailsService.loadUserByMobile((String) authenticationToken.getPrincipal());
if (Objects.isNull(user)) {
throw new InternalAuthenticationServiceException("手机号或验证码错误");
}
if (Objects.isNull(user)) {
throw new InternalAuthenticationServiceException("手机号或验证码错误");
}
SmsCodeAuthenticationToken authenticationResult = new SmsCodeAuthenticationToken(user, user.getAuthorities());
SmsCodeAuthenticationToken authenticationResult = new SmsCodeAuthenticationToken(user, user.getAuthorities());
authenticationResult.setDetails(authenticationToken.getDetails());
authenticationResult.setDetails(authenticationToken.getDetails());
return authenticationResult;
return authenticationResult;
}
}
@Override
public boolean supports(Class<?> authentication) {
return SmsCodeAuthenticationToken.class.isAssignableFrom(authentication);
}
@Override
public boolean supports(Class<?> authentication) {
return SmsCodeAuthenticationToken.class.isAssignableFrom(authentication);
}
}
......@@ -21,26 +21,14 @@ public class SmsCodeAuthenticationSecurityConfig
extends SecurityConfigurerAdapter<DefaultSecurityFilterChain, HttpSecurity> {
@Autowired
@SuppressWarnings("all")
private MateUserDetailsService userDetailsService;
@Autowired
@SuppressWarnings("all")
public AuthenticationSuccessHandler mateAuthenticationSuccessHandler;
@Autowired
@SuppressWarnings("all")
public AuthenticationFailureHandler mateAuthenticationFailureHandler;
@Override
public void configure(HttpSecurity http) {
// 过滤器
SmsCodeAuthenticationFilter smsCodeAuthenticationFilter = new SmsCodeAuthenticationFilter();
smsCodeAuthenticationFilter.setAuthenticationManager(http.getSharedObject(AuthenticationManager.class));
smsCodeAuthenticationFilter.setAuthenticationSuccessHandler(mateAuthenticationSuccessHandler);
smsCodeAuthenticationFilter.setAuthenticationFailureHandler(mateAuthenticationFailureHandler);
// 获取验证码提供者
SmsCodeAuthenticationProvider smsCodeAuthenticationProvider = new SmsCodeAuthenticationProvider(userDetailsService);
......
......@@ -8,50 +8,51 @@ import java.util.Collection;
/**
* 手机号+验证码登录令牌获取
*
* @author pangu
* @since 2020-7-21
*/
public class SmsCodeAuthenticationToken extends AbstractAuthenticationToken {
private static final long serialVersionUID = -3629824093049247125L;
private final Object principal;
public SmsCodeAuthenticationToken(String mobile) {
super(null);
this.principal = mobile;
setAuthenticated(false);
}
public SmsCodeAuthenticationToken(Object principal, Collection<? extends GrantedAuthority> authorities) {
super(authorities);
this.principal = principal;
super.setAuthenticated(true);
}
@Override
public Object getCredentials() {
return this.principal;
}
@Override
public Object getPrincipal() {
return this.principal;
}
@Override
@SneakyThrows
public void setAuthenticated(boolean isAuthenticated) {
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();
}
private static final long serialVersionUID = -3629824093049247125L;
private final Object principal;
public SmsCodeAuthenticationToken(String mobile) {
super(null);
this.principal = mobile;
setAuthenticated(false);
}
public SmsCodeAuthenticationToken(Object principal, Collection<? extends GrantedAuthority> authorities) {
super(authorities);
this.principal = principal;
super.setAuthenticated(true);
}
@Override
public Object getCredentials() {
return this.principal;
}
@Override
public Object getPrincipal() {
return this.principal;
}
@Override
@SneakyThrows
public void setAuthenticated(boolean isAuthenticated) {
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();
}
}
......@@ -19,120 +19,125 @@ import vip.mate.core.common.constant.Oauth2Constant;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
/**
* 社交登录验证过滤器
*
* @author pangu
*/
@Slf4j
public class SocialAuthenticationFilter extends AbstractAuthenticationProcessingFilter {
public static String SOCIAL_LOGIN_URL = "/auth1/callback/**";
/**
* 请求中的参数
*/
private String socialParameter = Oauth2Constant.DEFAULT_PARAMETER_NAME_SOCIAL;
private AuthRequestFactory authRequestFactory;
private boolean postOnly = false;
/**
* 通过构造函数指定该 Filter 要拦截的 url 和 httpMethod
*/
protected SocialAuthenticationFilter() {
super(new AntPathRequestMatcher(SOCIAL_LOGIN_URL, null));
}
@Override
public Authentication attemptAuthentication(HttpServletRequest request, HttpServletResponse response) throws AuthenticationException {
if (postOnly && !request.getMethod().equals("POST")) {
throw new AuthenticationServiceException("Authentication method not supported: " + request.getMethod());
}
SocialAuthenticationToken token;
token = new SocialAuthenticationToken(obtainAuthUser(request));
this.setDetails(request, token);
// 3. 返回 authenticated 方法的返回值
return this.getAuthenticationManager().authenticate(token);
}
/**
* 获取手机号
*/
protected String obtainSocial(HttpServletRequest request) {
return request.getParameter(socialParameter);
}
protected void setDetails(HttpServletRequest request, SocialAuthenticationToken authRequest) {
authRequest.setDetails(authenticationDetailsSource.buildDetails(request));
}
public void setSocialParameter(String socialParameter) {
Assert.hasText(socialParameter, "Social parameter must not be empty or null");
this.socialParameter = socialParameter;
}
public void setPostOnly(boolean postOnly) {
this.postOnly = postOnly;
}
public final String getSocialParameter() {
return socialParameter;
}
/**
* 获取 justauth 登录后的用户信息
*/
protected AuthUser obtainAuthUser(HttpServletRequest request) {
String type = getCallbackType(request);
AuthRequest authRequest = authRequestFactory.get(type);
// 登录后,从第三方拿到用户信息
AuthResponse response = authRequest.login(getCallback(request));
log.info("【justauth 第三方登录 response】= {}", JSON.toJSON(response));
// 第三方登录成功
if (response.getCode() == AuthResponseStatus.SUCCESS.getCode()) {
AuthUser authUser = (AuthUser) response.getData();
return authUser;
}
return null;
}
/**
* 从请求中构建 AuthCallback
*/
private AuthCallback getCallback(HttpServletRequest request) {
AuthCallback authCallback = AuthCallback.builder()
.code(request.getParameter("code"))
.auth_code(request.getParameter("auth_code"))
.authorization_code(request.getParameter("authorization_code"))
.oauth_token(request.getParameter("oauth_token"))
.state(request.getParameter("state"))
.oauth_verifier(request.getParameter("oauth_verifier"))
.build();
return authCallback;
}
/**
* 获取路径参数:回调类型
*/
private String getCallbackType(HttpServletRequest request) {
// /context/open/oauth/callback/gitee
String uri = request.getRequestURI();
// "/open/oauth/callback/".length()
int common = SOCIAL_LOGIN_URL.length() - 2;
int start = uri.indexOf(SOCIAL_LOGIN_URL.substring(0, common));
if (start == -1) {
log.warn("【justauth 第三方登录 response】回调类型为空,uri={}", uri);
return null;
}
// gitee
return uri.substring(start + common);
}
public void setAuthRequestFactory(AuthRequestFactory authRequestFactory) {
this.authRequestFactory = authRequestFactory;
}
public static String SOCIAL_LOGIN_URL = "/auth1/callback/**";
/**
* 请求中的参数
*/
private String socialParameter = Oauth2Constant.DEFAULT_PARAMETER_NAME_SOCIAL;
private AuthRequestFactory authRequestFactory;
private boolean postOnly = false;
/**
* 通过构造函数指定该 Filter 要拦截的 url 和 httpMethod
*/
protected SocialAuthenticationFilter() {
super(new AntPathRequestMatcher(SOCIAL_LOGIN_URL, null));
}
@Override
public Authentication attemptAuthentication(HttpServletRequest request, HttpServletResponse response) throws AuthenticationException {
if (postOnly && !request.getMethod().equals("POST")) {
throw new AuthenticationServiceException("Authentication method not supported: " + request.getMethod());
}
SocialAuthenticationToken token;
token = new SocialAuthenticationToken(obtainAuthUser(request));
this.setDetails(request, token);
// 3. 返回 authenticated 方法的返回值
return this.getAuthenticationManager().authenticate(token);
}
/**
* 获取手机号
*/
protected String obtainSocial(HttpServletRequest request) {
return request.getParameter(socialParameter);
}
protected void setDetails(HttpServletRequest request, SocialAuthenticationToken authRequest) {
authRequest.setDetails(authenticationDetailsSource.buildDetails(request));
}
public void setSocialParameter(String socialParameter) {
Assert.hasText(socialParameter, "Social parameter must not be empty or null");
this.socialParameter = socialParameter;
}
public void setPostOnly(boolean postOnly) {
this.postOnly = postOnly;
}
public final String getSocialParameter() {
return socialParameter;
}
/**
* 获取 justauth 登录后的用户信息
*/
protected AuthUser obtainAuthUser(HttpServletRequest request) {
String type = getCallbackType(request);
AuthRequest authRequest = authRequestFactory.get(type);
// 登录后,从第三方拿到用户信息
AuthResponse response = authRequest.login(getCallback(request));
log.info("【justauth 第三方登录 response】= {}", JSON.toJSON(response));
// 第三方登录成功
if (response.getCode() == AuthResponseStatus.SUCCESS.getCode()) {
AuthUser authUser = (AuthUser) response.getData();
return authUser;
}
return null;
}
/**
* 从请求中构建 AuthCallback
*/
private AuthCallback getCallback(HttpServletRequest request) {
AuthCallback authCallback = AuthCallback.builder()
.code(request.getParameter("code"))
.auth_code(request.getParameter("auth_code"))
.authorization_code(request.getParameter("authorization_code"))
.oauth_token(request.getParameter("oauth_token"))
.state(request.getParameter("state"))
.oauth_verifier(request.getParameter("oauth_verifier"))
.build();
return authCallback;
}
/**
* 获取路径参数:回调类型
*/
private String getCallbackType(HttpServletRequest request) {
// /context/open/oauth/callback/gitee
String uri = request.getRequestURI();
// "/open/oauth/callback/".length()
int common = SOCIAL_LOGIN_URL.length() - 2;
int start = uri.indexOf(SOCIAL_LOGIN_URL.substring(0, common));
if (start == -1) {
log.warn("【justauth 第三方登录 response】回调类型为空,uri={}", uri);
return null;
}
// gitee
return uri.substring(start + common);
}
public void setAuthRequestFactory(AuthRequestFactory authRequestFactory) {
this.authRequestFactory = authRequestFactory;
}
}
......@@ -12,35 +12,40 @@ import vip.mate.core.security.userdetails.MateUserDetailsService;
import java.util.Objects;
/**
* 社交登录验证提供者
*
* @author pangu
*/
@AllArgsConstructor
public class SocialAuthenticationProvider implements AuthenticationProvider {
private final MateUserDetailsService userDetailsService;
private final MateUserDetailsService userDetailsService;
@Override
public Authentication authenticate(Authentication authentication) throws AuthenticationException {
SocialAuthenticationToken authenticationToken = (SocialAuthenticationToken) authentication;
@Override
public Authentication authenticate(Authentication authentication) throws AuthenticationException {
SocialAuthenticationToken authenticationToken = (SocialAuthenticationToken) authentication;
/**
* 调用 {@link UserDetailsService}
*/
UserDetails user = userDetailsService.loadUserBySocial(((AuthUser)authenticationToken.getPrincipal()).getUsername());
/**
* 调用 {@link UserDetailsService}
*/
UserDetails user = userDetailsService.loadUserBySocial(((AuthUser) authenticationToken.getPrincipal()).getUsername());
if (Objects.isNull(user)) {
throw new InternalAuthenticationServiceException("社交登录错误");
}
if (Objects.isNull(user)) {
throw new InternalAuthenticationServiceException("社交登录错误");
}
SocialAuthenticationToken authenticationResult = new SocialAuthenticationToken(user, user.getAuthorities());
SocialAuthenticationToken authenticationResult = new SocialAuthenticationToken(user, user.getAuthorities());
authenticationResult.setDetails(authenticationToken.getDetails());
authenticationResult.setDetails(authenticationToken.getDetails());
return authenticationResult;
return authenticationResult;
}
}
@Override
public boolean supports(Class<?> authentication) {
return SocialAuthenticationToken.class.isAssignableFrom(authentication);
}
@Override
public boolean supports(Class<?> authentication) {
return SocialAuthenticationToken.class.isAssignableFrom(authentication);
}
}
......@@ -12,37 +12,35 @@ import org.springframework.security.web.authentication.UsernamePasswordAuthentic
import org.springframework.stereotype.Component;
import vip.mate.core.security.userdetails.MateUserDetailsService;
/**
* 社交登录配置
*
* @author pangu
*/
@Slf4j
@Component
public class SocialAuthenticationSecurityConfig extends SecurityConfigurerAdapter<DefaultSecurityFilterChain, HttpSecurity> {
@Autowired
@SuppressWarnings("all")
private MateUserDetailsService userDetailsService;
@Autowired
private MateUserDetailsService userDetailsService;
@Autowired
@SuppressWarnings("all")
public AuthenticationSuccessHandler smsCodeSuccessHandler;
@Autowired
private AuthRequestFactory authRequestFactory;
@Autowired
@SuppressWarnings("all")
private AuthRequestFactory authRequestFactory;
@Override
public void configure(HttpSecurity http) {
@Override
public void configure(HttpSecurity http) {
// 过滤器
SocialAuthenticationFilter socialAuthenticationFilter = new SocialAuthenticationFilter();
socialAuthenticationFilter.setAuthenticationManager(http.getSharedObject(AuthenticationManager.class));
socialAuthenticationFilter.setAuthRequestFactory(authRequestFactory);
// 过滤器
SocialAuthenticationFilter socialAuthenticationFilter = new SocialAuthenticationFilter();
socialAuthenticationFilter.setAuthenticationManager(http.getSharedObject(AuthenticationManager.class));
socialAuthenticationFilter.setAuthenticationSuccessHandler(smsCodeSuccessHandler);
socialAuthenticationFilter.setAuthRequestFactory(authRequestFactory);
// 获取社交登录提供者
SocialAuthenticationProvider socialAuthenticationProvider = new SocialAuthenticationProvider(userDetailsService);
// 获取社交登录提供者
SocialAuthenticationProvider socialAuthenticationProvider = new SocialAuthenticationProvider(userDetailsService);
// 将社交登录校验器注册到 HttpSecurity, 并将社交登录过滤器添加在 UsernamePasswordAuthenticationFilter 之前
http.authenticationProvider(socialAuthenticationProvider)
.addFilterBefore(socialAuthenticationFilter, UsernamePasswordAuthenticationFilter.class);
}
// 将社交登录校验器注册到 HttpSecurity, 并将社交登录过滤器添加在 UsernamePasswordAuthenticationFilter 之前
http.authenticationProvider(socialAuthenticationProvider)
.addFilterBefore(socialAuthenticationFilter, UsernamePasswordAuthenticationFilter.class);
}
}
......@@ -6,59 +6,65 @@ import org.springframework.security.core.GrantedAuthority;
import java.util.Collection;
/**
* 社交验证token生成
*
* @author pangu
*/
public class SocialAuthenticationToken extends AbstractAuthenticationToken {
private static final long serialVersionUID = -3629824093049247125L;
private static final long serialVersionUID = -3629824093049247125L;
// ~ Instance fields
// ================================================================================================
// ~ Instance fields
// ================================================================================================
private final Object principal;
private Object credentials;
private final Object principal;
private Object credentials;
// ~ Constructors
// ===================================================================================================
/**
* justauth 使用
*/
public SocialAuthenticationToken(Object authUser) {
super(null);
this.principal = authUser;
setAuthenticated(false);
}
// ~ Constructors
// ===================================================================================================
public SocialAuthenticationToken(Object principal, Collection<? extends GrantedAuthority> authorities) {
super(authorities);
this.principal = principal;
super.setAuthenticated(true);
}
/**
* justauth 使用
*/
public SocialAuthenticationToken(Object authUser) {
super(null);
this.principal = authUser;
setAuthenticated(false);
}
// ~ Methods
// ========================================================================================================
public SocialAuthenticationToken(Object principal, Collection<? extends GrantedAuthority> authorities) {
super(authorities);
this.principal = principal;
super.setAuthenticated(true);
}
// ~ Methods
// ========================================================================================================
@Override
public Object getCredentials() {
return this.principal;
}
@Override
public Object getPrincipal() {
return this.principal;
}
@Override
public Object getCredentials() {
return this.principal;
}
@Override
@SneakyThrows
public void setAuthenticated(boolean isAuthenticated) {
if (isAuthenticated) {
throw new IllegalArgumentException(
"Cannot set this token to trusted - use constructor which takes a GrantedAuthority list instead");
}
@Override
public Object getPrincipal() {
return this.principal;
}
super.setAuthenticated(false);
}
@Override
@SneakyThrows
public void setAuthenticated(boolean isAuthenticated) {
if (isAuthenticated) {
throw new IllegalArgumentException(
"Cannot set this token to trusted - use constructor which takes a GrantedAuthority list instead");
}
@Override
public void eraseCredentials() {
super.eraseCredentials();
}
super.setAuthenticated(false);
}
@Override
public void eraseCredentials() {
super.eraseCredentials();
}
}
......@@ -10,53 +10,55 @@ import vip.mate.core.common.api.Result;
import vip.mate.core.common.api.ResultCode;
/**
* WEB响应异常处理类
*
* @author pangu
*/
@Slf4j
public class MateWebRespExceptionTranslator implements WebResponseExceptionTranslator {
@Override
public ResponseEntity<Result<?>> translate(Exception e) throws Exception {
ResponseEntity.BodyBuilder status = ResponseEntity.status(HttpStatus.UNAUTHORIZED);
String message = "认证失败";
log.error(message, e);
if (e instanceof UnsupportedGrantTypeException) {
message = "不支持该认证类型";
return status.body(apiResult(message));
}
if (e instanceof InvalidTokenException
&& StringUtils.containsIgnoreCase(e.getMessage(), "Invalid refresh token (expired)")) {
message = "刷新令牌已过期,请重新登录";
return status.body(apiResult(message));
}
if (e instanceof InvalidScopeException) {
message = "不是有效的scope值";
return status.body(apiResult(message));
}
if (e instanceof InvalidGrantException) {
if (StringUtils.containsIgnoreCase(e.getMessage(), "Invalid refresh token")) {
message = "refresh token无效";
return status.body(apiResult(message));
}
if (StringUtils.containsIgnoreCase(e.getMessage(), "Invalid authorization code")) {
message = "authorization code无效";
return status.body(apiResult(message));
}
if (StringUtils.containsIgnoreCase(e.getMessage(), "locked")) {
message = "用户已被锁定,请联系管理员";
return status.body(apiResult(message));
}
message = "用户名或密码错误";
return status.body(apiResult(message));
}
return status.body(apiResult(message));
}
private Result<?> apiResult (String message){
return Result.data(ResultCode.ERROR, message);
}
@Override
public ResponseEntity<Result<?>> translate(Exception e) throws Exception {
ResponseEntity.BodyBuilder status = ResponseEntity.status(HttpStatus.UNAUTHORIZED);
String message = "认证失败";
log.error(message, e);
if (e instanceof UnsupportedGrantTypeException) {
message = "不支持该认证类型";
return status.body(apiResult(message));
}
if (e instanceof InvalidTokenException
&& StringUtils.containsIgnoreCase(e.getMessage(), "Invalid refresh token (expired)")) {
message = "刷新令牌已过期,请重新登录";
return status.body(apiResult(message));
}
if (e instanceof InvalidScopeException) {
message = "不是有效的scope值";
return status.body(apiResult(message));
}
if (e instanceof InvalidGrantException) {
if (StringUtils.containsIgnoreCase(e.getMessage(), "Invalid refresh token")) {
message = "refresh token无效";
return status.body(apiResult(message));
}
if (StringUtils.containsIgnoreCase(e.getMessage(), "Invalid authorization code")) {
message = "authorization code无效";
return status.body(apiResult(message));
}
if (StringUtils.containsIgnoreCase(e.getMessage(), "locked")) {
message = "用户已被锁定,请联系管理员";
return status.body(apiResult(message));
}
message = "用户名或密码错误";
return status.body(apiResult(message));
}
return status.body(apiResult(message));
}
private Result<?> apiResult(String message) {
return Result.data(ResultCode.ERROR, message);
}
}
Supports Markdown
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment