JAVA实现用户登录错误N次后,账户暂时锁定
前言
本次要实现的需求是,用户登录错误,输入密码错误N次后,实现用户锁定,让用户等待一段时间后重新登录,目的是为了防止黑客暴力破解用户密码 。下面上代码教程,觉得不错的客官请点赞评论支持一下,让鄙人有继续创作的动力!
教程
1.原理
功能实现的原理,是记录用户连续输入密码错误的次数,达到某个错误次数以后,比如说是5次以后,就锁定用户,暂时不让用户登录。等锁定时限以后,用户又有5次重新输入密码的机会。代码实现原理是将用户名和输入错误的密码错误的次数记录到reids里,当用户登录成功后,清除该用户的登录错误的次数,重新计算。
2.代码教程
1.代码实现的核心类
-
-
import org.springblade.core.redis.cache.RedisUtil;
-
import org.springblade.core.tool.utils.SpringUtil;
-
-
import java.util.Set;
-
import java.util.concurrent.atomic.AtomicInteger;
-
import java.util.stream.Collectors;
-
-
/**
-
* 重试限制缓存
-
*
-
* @author tarzan
-
* @version 1.0
-
* @company 北斗天地股份有限公司
-
* @copyright (c) 2022 BEIDOU TIANDI CO.,LTD.All rights reserved.
-
* @date 2022年12月01日 17:13:14
-
* @since JDK1.8
-
*/
-
public class RetryLimitCache {
-
-
private static final RedisUtil REDIS_UTIL;
-
-
private static final String PASSWORD_RETRY_CACHE="password_retry_cache:";
-
-
static {
-
REDIS_UTIL = SpringUtil.getBean(RedisUtil.class);
-
}
-
-
/**
-
* 是否超过限制
-
*/
-
public static boolean isOverLimit(String username, Integer limit) {
-
//设置次数
-
AtomicInteger retryCount = RetryLimitCache.get(username);
-
if (retryCount == null) {
-
retryCount = new AtomicInteger(0);
-
}
-
if (retryCount.incrementAndGet() > limit) {
-
//重试次数如果大于限制次数,就锁定
-
return true;
-
}
-
//并将其保存到缓存中(有效时长30分)
-
RetryLimitCache.put(username, retryCount, 1800L);
-
return false;
-
}
-
-
/**
-
* 登录成功时,清除
-
*/
-
public static void remove(String userName) {
-
REDIS_UTIL.del(PASSWORD_RETRY_CACHE userName);
-
}
-
-
/**
-
* 密码重置多用户时,清除
-
*/
-
public static void remove(Set<String> userNames) {
-
if(userNames!=null&&userNames.size()>0){
-
Set<String> keys=userNames.stream().map(userName->PASSWORD_RETRY_CACHE userName).collect(Collectors.toSet());
-
REDIS_UTIL.del(keys);
-
}
-
}
-
-
-
private static void put(String userName, AtomicInteger retryNum, Long expire) {
-
REDIS_UTIL.setEx(PASSWORD_RETRY_CACHE userName, retryNum,expire);
-
}
-
-
private static AtomicInteger get(String userName) {
-
return REDIS_UTIL.get(PASSWORD_RETRY_CACHE userName);
-
}
-
-
-
}
2.登录接口处理类
-
-
-
-
-
public Kv token( String username,
-
String password, HttpServletRequest request) {
-
String grantType = WebUtil.getRequest().getParameter("grant_type");
-
return grant(username,password,grantType,request);
-
}
-
-
private Kv grant(String username,String password,String grantType,HttpServletRequest request){
-
//固定租户id
-
String tenantId = "000000";
-
Kv authInfo = Kv.create();
-
//重连次数锁定
-
if (RetryLimitCache.isOverLimit(username, 5)) {
-
return authInfo.set("error_code", HttpServletResponse.SC_BAD_REQUEST).set("error_description", "密码输错次数达到上限,请30分钟后重试");
-
}
-
String refreshToken = WebUtil.getRequest().getParameter("refresh_token");
-
String userType = Func.toStr(WebUtil.getRequest().getHeader(TokenUtil.USER_TYPE_HEADER_KEY), TokenUtil.DEFAULT_USER_TYPE);
-
TokenParameter tokenParameter = new TokenParameter();
-
tokenParameter.getArgs().set("tenantId", tenantId).set("username", username).set("password", password).set("grantType", grantType).set("refreshToken", refreshToken).set("userType", userType);
-
ITokenGranter granter = TokenGranterBuilder.getGranter(grantType);
-
UserInfo userInfo;
-
try {
-
userInfo = granter.grant(tokenParameter);
-
}catch (CaptchaException e){
-
return authInfo.set("error_code", HttpServletResponse.SC_BAD_REQUEST).set("error_description", "验证码不正确");
-
}
-
-
if (userInfo == null || userInfo.getUser() == null) {
-
return authInfo.set("error_code", HttpServletResponse.SC_BAD_REQUEST).set("error_description", "用户名或密码不正确");
-
}
-
if (Func.isEmpty(userInfo.getRoles())) {
-
return authInfo.set("error_code", HttpServletResponse.SC_BAD_REQUEST).set("error_description", "未获得用户的角色信息");
-
}
-
//用户存入session,CAD异常时候,监听删除用户对于实体的锁定
-
Long userId = userInfo.getUser().getId();
-
request.getSession().setAttribute("userId", userId);
-
RetryLimitCache.remove(username);
-
return TokenUtil.createAuthInfo(userInfo);
-
}
达到错误次数后抛出提示,登录成功后清除缓存。
补充说明,如果后端登录接口有验证校验的话,判断程序要写在,登录错误次数校验前面,以免把验证码输入错误的次数也统计上!!!
3.图片示意
感谢各位看官们的支持,你们的点赞,评论、收藏是我创作的动力!!!!
相关文章推荐
这篇好文章是转载于:学新通技术网
- 版权申明: 本站部分内容来自互联网,仅供学习及演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,请提供相关证据及您的身份证明,我们将在收到邮件后48小时内删除。
- 本站站名: 学新通技术网
- 本文地址: /boutique/detail/tanhfhjbbi
系列文章
更多
同类精品
更多
-
photoshop保存的图片太大微信发不了怎么办
PHP中文网 06-15 -
《学习通》视频自动暂停处理方法
HelloWorld317 07-05 -
Android 11 保存文件到外部存储,并分享文件
Luke 10-12 -
word里面弄一个表格后上面的标题会跑到下面怎么办
PHP中文网 06-20 -
photoshop扩展功能面板显示灰色怎么办
PHP中文网 06-14 -
微信公众号没有声音提示怎么办
PHP中文网 03-31 -
excel下划线不显示怎么办
PHP中文网 06-23 -
excel打印预览压线压字怎么办
PHP中文网 06-22 -
TikTok加速器哪个好免费的TK加速器推荐
TK小达人 10-01 -
怎样阻止微信小程序自动打开
PHP中文网 06-13