今天有一个需求,要求验证用户的密码是否为弱密码,如果是则强制跳转到某页面
前端用的是vue
后台java使用拦截器
@Log4j2
@Component("verifyPasswordFilter")
public class VerifyPasswordFilter extends AbstractSecurityInterceptor implements Filter {
@Autowired
private AuthenticationManager authenticationManager;
@Autowired
private WebAccessDecisionManager accessDecisionManager;
@Autowired
private SecurityMetadataSource securityMetadataSource;
@Autowired
private AuthUtils authUtils;
@Autowired
private AuthConfig authConfig;
@PostConstruct
public void init() {
super.setAuthenticationManager(authenticationManager);
super.setAccessDecisionManager(accessDecisionManager);
}
@Override
public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
FilterInvocation fi = new FilterInvocation(request, response, chain);
List<String> extUrls = CollUtil.newArrayList();
// extUrls.add("/api/v1/auth/getCurrentResourceList");//后台菜单
extUrls.add("/api/v1/user/changePassword");//提交密码
if (checkIgnores(fi.getHttpRequest(),extUrls)) {
fi.getChain().doFilter(fi.getRequest(), fi.getResponse());
return;
}
String jwt = authUtils.getJwtFromRequest(fi.getHttpRequest());
if (StrUtil.isNotBlank(jwt)) {
String id = authUtils.getUserIdFromJWT(jwt);
LoginUser loginUser = authUtils.getLoginUserCache(id);
String passwordPlain = loginUser.getPasswordPlain();
String defaultPaaWord = "";
if(loginUser.getUsername().length() >= 6){
defaultPaaWord = loginUser.getUsername().substring(loginUser.getUsername().length() - 6) + "@Gd";
}else{
defaultPaaWord = loginUser.getUsername() + "@Gd";
}
if ((!StrUtil.equals(passwordPlain,defaultPaaWord)) && authUtils.checkPasswordStrong(passwordPlain)){
// 拦截放行
fi.getChain().doFilter(fi.getRequest(), fi.getResponse());
}else {
// 弱密码,拦截请求并返回response
ResponseUtils.renderJson(fi.getResponse(), R.fail(AuthResultCode.WEAK_PASSWORD));
return;
}
} else {
// 未登录,拦截请求并返回response
ResponseUtils.renderJson(fi.getResponse(), R.fail(AuthResultCode.UNAUTHORIZED));
}
}
@Override
public void init(FilterConfig arg0) throws ServletException {
}
@Override
public void destroy() {
// User user=AccessUtils.getCurrentUser();
// logger.info("======> User Log Out! username:"+user.getUsername()+" realname:"+ user.getRealName());
}
@Override
public Class<?> getSecureObjectClass() {
return FilterInvocation.class;
}
@Override
public SecurityMetadataSource obtainSecurityMetadataSource() {
return this.securityMetadataSource;
}
@Override
public WebAccessDecisionManager getAccessDecisionManager() {
return accessDecisionManager;
}
@Override
public AuthenticationManager getAuthenticationManager() {
return authenticationManager;
}
@Override
public void setAuthenticationManager(AuthenticationManager authenticationManager) {
this.authenticationManager = authenticationManager;
}
public void setAccessDecisionManager(WebAccessDecisionManager accessDecisionManager) {
this.accessDecisionManager = accessDecisionManager;
}
public SecurityMetadataSource getSecurityMetadataSource() {
return securityMetadataSource;
}
public void setSecurityMetadataSource(SecurityMetadataSource securityMetadataSource) {
this.securityMetadataSource = securityMetadataSource;
}
/**
* 请求是否不需要进行权限拦截
*
* @param request 当前请求
* @param extUrls 自定义扩展忽略url
* @return true - 忽略,false - 不忽略
*/
private boolean checkIgnores(HttpServletRequest request, List<String> extUrls) {
String method = request.getMethod();
HttpMethod httpMethod = HttpMethod.resolve(method);
if (ObjectUtil.isNull(httpMethod)) {
httpMethod = HttpMethod.GET;
}
Set<String> ignores = Sets.newHashSet();
switch (httpMethod) {
case GET:
ignores.addAll(authConfig.getIgnores().getGet());
break;
case PUT:
ignores.addAll(authConfig.getIgnores().getPut());
break;
case HEAD:
ignores.addAll(authConfig.getIgnores().getHead());
break;
case POST:
ignores.addAll(authConfig.getIgnores().getPost());
break;
case PATCH:
ignores.addAll(authConfig.getIgnores().getPatch());
break;
case TRACE:
ignores.addAll(authConfig.getIgnores().getTrace());
break;
case DELETE:
ignores.addAll(authConfig.getIgnores().getDelete());
break;
case OPTIONS:
ignores.addAll(authConfig.getIgnores().getOptions());
break;
default:
break;
}
ignores.addAll(authConfig.getIgnores().getPattern());
ignores.addAll(extUrls);
if (CollUtil.isNotEmpty(ignores)) {
for (String ignore : ignores) {
AntPathRequestMatcher matcher = new AntPathRequestMatcher(ignore, method);
if (matcher.matches(request)) {
return true;
}
}
}
return false;
}
}
配置文件配置不需要拦截的请求
auth:
config:
ignores:
get:
- "/cms/api/v1/**"
- "/api/v1/auth/captcha"
# 不需要过滤的 post 请求
post:
- "/cms/api/v1/file/fileInfo/download/byUrl"
- "/api/v1/auth/login"
put:
- "/cms/api/v1/systemConfig/systemConfig/operationCofing"
# 不需要过滤的请求,不限方法
pattern:
- "/cms/api/v1/user/**"
- "/api/v1/file/fileInfo/download/*"
- "/test/*"
xss:
- "/druid/**"
前端的reponse请求拦截,如果弱密码则跳转修改密码页面
// response 拦截器中, 隐藏进度条NProgress.done()
axios.interceptors.response.use(config => {
NProgress.done();
store.commit('setLoading', false);
if (config.data.code == 200 || config.data.code == 400 || config.data.type == 'multipart/form-data') {
setAuthTokenFromResponse(config);
return config;
} else {
const data = config.data;
// 从 localstorage 获取 token
const token = getAuthToken();
if (data.code !== 200) {
message.error(data.msg);
}
if(data.code === 5005){
//接口返回弱密码code,强制跳转修改密码页面
window.location.href = store.getters.userClientDomain + '#/editPassword'
}
// return Promise.reject(config);
}
}, errorHandler);
最后自己设计修改密码的组件以及接口,在路由表中配置vue组件即可
可选:
页面隐藏侧边栏,以及隐藏导航条
1、隐藏导航条:一般在AppMain.vue里
<a-layout-content :style="{'margin': $route.name != 'index' ? '30px':'0',minHeight: '280px'}">
<Breadcrumb v-if="$route.name != 'index' && $route.name != 'editPassword'"/>
<router-view :key="key"/>
a-layout-content>
2、隐藏侧边栏:一般在layout/index.vue里
computed: {
showSider() {
const showSider = this.$route.name;
return (showSider === 'index' || showSider === 'editPassword') ? false : true
},
...mapGetters([
'app'
]),
},
效果: