Commit 12ccae18 authored by 董建华's avatar 董建华

Merge branch 'passwordval' into deviceInterceptor

parents c0be2026 952fc2b2
...@@ -149,7 +149,18 @@ public interface Constants { ...@@ -149,7 +149,18 @@ public interface Constants {
* redis中token的key值前缀 * redis中token的key值前缀
*/ */
String SESSION_PREFIX = "spring:session:sessions:"; String SESSION_PREFIX = "spring:session:sessions:";
/**
* 账号密码锁定阈值
*/
Long PASSWORD_ERROR_LOCK_COUNT = 5L;
/**
* 账号密码错误锁定时间 30分钟
*/
Long PASSWORD_ERROR_LOCK_TIME = 30L;
/**
* 密码错误次数过多锁定key前缀
*/
String PASSWORD_LOCK_PRE = "password_error_lock:";
/** /**
* 默认随机密码长度 * 默认随机密码长度
*/ */
......
...@@ -30,6 +30,7 @@ import java.util.HashMap; ...@@ -30,6 +30,7 @@ import java.util.HashMap;
import java.util.Map; import java.util.Map;
import java.util.Optional; import java.util.Optional;
import java.util.UUID; import java.util.UUID;
import java.util.concurrent.TimeUnit;
/** /**
* 限次图形验证码校验标记 * 限次图形验证码校验标记
...@@ -46,6 +47,7 @@ public class CaptchaFiniteValidateAdvisor { ...@@ -46,6 +47,7 @@ public class CaptchaFiniteValidateAdvisor {
private static final String SUPER_CAPTCHA_ID = UUID.nameUUIDFromBytes("__QG_APPCLIENT_AGENT__".getBytes(Charset.forName("UTF-8"))).toString(); private static final String SUPER_CAPTCHA_ID = UUID.nameUUIDFromBytes("__QG_APPCLIENT_AGENT__".getBytes(Charset.forName("UTF-8"))).toString();
private static final String SUPER_CAPTCHA = "__SUPERQG__"; private static final String SUPER_CAPTCHA = "__SUPERQG__";
private static final String ALERT_TEMP = "密码错误已超过次数,请%s分钟后再试";
@Autowired @Autowired
@Qualifier("stringRedisTemplate") @Qualifier("stringRedisTemplate")
private RedisTemplate<String, String> redisTemplate; private RedisTemplate<String, String> redisTemplate;
...@@ -89,6 +91,26 @@ public class CaptchaFiniteValidateAdvisor { ...@@ -89,6 +91,26 @@ public class CaptchaFiniteValidateAdvisor {
return JsonResult.buildErrorStateResult("用户名或密码不正确", null); return JsonResult.buildErrorStateResult("用户名或密码不正确", null);
} }
if (countErrorByPhone > Constants.Image_Need_Count) { if (countErrorByPhone > Constants.Image_Need_Count) {
/**
* 输入密码错误超过一定次数限制登陆
*/
if (countErrorByPhone > Constants.PASSWORD_ERROR_LOCK_COUNT) {
String lock_key = Constants.PASSWORD_LOCK_PRE.concat(phoneNo);
Long expire = redisTemplate.opsForValue().getOperations().getExpire(lock_key);
/**
* 查看锁的剩余时间不存在说明已经解锁
*/
if (null != expire && expire > 0L) {
/**
* 获取到的时间是秒 转化为分 大概转一下吧不要太精确
*/
expire = expire > 60L ? expire / 60 : 1L;
return JsonResult.buildErrorStateResult(String.format(ALERT_TEMP, expire ), null);
}
}
String registerFrom = Optional.ofNullable(request.getParameter("registerFrom")).orElse(""); String registerFrom = Optional.ofNullable(request.getParameter("registerFrom")).orElse("");
String captchaId = Optional.ofNullable(request.getParameter(Constants.QG_CAPTCHA_ID)).orElse(""); String captchaId = Optional.ofNullable(request.getParameter(Constants.QG_CAPTCHA_ID)).orElse("");
String captchaValue = request.getParameter(Constants.QG_CAPTCHA_VALUE); String captchaValue = request.getParameter(Constants.QG_CAPTCHA_VALUE);
...@@ -180,4 +202,5 @@ public class CaptchaFiniteValidateAdvisor { ...@@ -180,4 +202,5 @@ public class CaptchaFiniteValidateAdvisor {
return phonePasswordMap; return phonePasswordMap;
} }
} }
...@@ -337,6 +337,8 @@ public class UserController implements IBaseController { ...@@ -337,6 +337,8 @@ public class UserController implements IBaseController {
// TODO 加渠道号 // TODO 加渠道号
log.info("修改密码成功, phoneNo:{}, registerFrom:{}", phoneNo, registerFrom); log.info("修改密码成功, phoneNo:{}, registerFrom:{}", phoneNo, registerFrom);
//修改密码成功也要清除一下
lockIpv4Service.unLockPhone(phoneNo);
return JsonResult.buildSuccessResult(null, null); return JsonResult.buildSuccessResult(null, null);
} }
...@@ -509,8 +511,12 @@ public class UserController implements IBaseController { ...@@ -509,8 +511,12 @@ public class UserController implements IBaseController {
lockIpv4Service.countErrorByPhoneNo(phoneNo); lockIpv4Service.countErrorByPhoneNo(phoneNo);
return null; return null;
} }
// 向该ipv4添加成功计数器 // 向该ipv4添加成功计数器
lockIpv4Service.countSuccessByIpv4(clientIp); lockIpv4Service.countSuccessByIpv4(clientIp);
//尝试解锁
lockIpv4Service.unLockPhone(phoneNo);
return user; return user;
} }
...@@ -524,6 +530,8 @@ public class UserController implements IBaseController { ...@@ -524,6 +530,8 @@ public class UserController implements IBaseController {
return JsonResult.buildErrorStateResult("登录时微信关联失败", null); return JsonResult.buildErrorStateResult("登录时微信关联失败", null);
} }
LoginProperties loginProperties = new LoginProperties("", 4, channelId, createdFrom, appChannel, merchant.getId(), merchant.getName()); LoginProperties loginProperties = new LoginProperties("", 4, channelId, createdFrom, appChannel, merchant.getId(), merchant.getName());
//尝试解锁
lockIpv4Service.unLockPhone(user.getPhoneNo());
//更新session //更新session
return new JsonResult(sessionService.createSession(user, loginProperties)); return new JsonResult(sessionService.createSession(user, loginProperties));
} }
......
...@@ -45,4 +45,12 @@ public interface ILockIpv4Service { ...@@ -45,4 +45,12 @@ public interface ILockIpv4Service {
*/ */
void lockSuccessIpv4(String ip, long count); void lockSuccessIpv4(String ip, long count);
/**
* 锁定手机号
*/
void lockPhone(String phone , long count);
/**
* 解锁手机号
*/
void unLockPhone(String phone);
} }
...@@ -42,6 +42,9 @@ public class LockIpv4ServiceImpl implements ILockIpv4Service { ...@@ -42,6 +42,9 @@ public class LockIpv4ServiceImpl implements ILockIpv4Service {
} }
// 密码错误计数 // 密码错误计数
Long errorCount = stringRedisTemplate.opsForValue().increment(key, 1L); Long errorCount = stringRedisTemplate.opsForValue().increment(key, 1L);
//判断上锁
lockPhone(phoneNo, errorCount);
if (errorCount > Constants.Image_Need_Count) { if (errorCount > Constants.Image_Need_Count) {
log.info("用户名或密码不正确,phoneNo={}", phoneNo); log.info("用户名或密码不正确,phoneNo={}", phoneNo);
throw new PasswordErrorLimitException("用户名或密码不正确"); throw new PasswordErrorLimitException("用户名或密码不正确");
...@@ -124,6 +127,45 @@ public class LockIpv4ServiceImpl implements ILockIpv4Service { ...@@ -124,6 +127,45 @@ public class LockIpv4ServiceImpl implements ILockIpv4Service {
log.info("Lock_ipv4: locked success ip access:{}, success overstep {} times in {} minutes, do lock {} minutes", ip, Constants.IPV4_LOCK_ON_SUCCESS_COUNTS, Constants.IPV4_SUCCESS_COUNT_MINUTES, Constants.IPV4_SUCCESS_LOCK_MINUTES); log.info("Lock_ipv4: locked success ip access:{}, success overstep {} times in {} minutes, do lock {} minutes", ip, Constants.IPV4_LOCK_ON_SUCCESS_COUNTS, Constants.IPV4_SUCCESS_COUNT_MINUTES, Constants.IPV4_SUCCESS_LOCK_MINUTES);
} }
/**
* 锁定手机号
*
* @param phone
* @param count
*/
@Override
public void lockPhone(String phone, long count) {
if (count == Constants.PASSWORD_ERROR_LOCK_COUNT) {
String lock_key = Constants.PASSWORD_LOCK_PRE.concat(phone);
//Constants.PASSWORD_LOCK_PRE
boolean isLock = stringRedisTemplate.hasKey(lock_key);
if (!isLock) {
stringRedisTemplate.opsForValue().set(lock_key, "lock", Constants.PASSWORD_ERROR_LOCK_TIME, TimeUnit.MINUTES);
}
}else if(count > Constants.PASSWORD_ERROR_LOCK_COUNT){
/**
* 如果超过阈值再进来则说明过了限制时间,解锁清楚次数
*/
unLockPhone(phone);
}
}
@Override
public void unLockPhone(String phone) {
try {
stringRedisTemplate.delete(Constants.PASSWORD_LOCK_PRE.concat(phone));
String key = Constants.REDIS_PASSWORD_ERROR_COUNT + phone;
stringRedisTemplate.delete(key);
log.info("解锁成功phone:{}", phone);
} catch (Exception e) {
log.error("解锁异常phone:{}", phone);
}
}
private static String getErrorIpKey(String ipv4) { private static String getErrorIpKey(String ipv4) {
return Constants.REDIS_PASSWORD_ERROR_COUNT_FOR_IPV4 + ipv4; return Constants.REDIS_PASSWORD_ERROR_COUNT_FOR_IPV4 + ipv4;
} }
......
...@@ -22,11 +22,7 @@ import cn.quantgroup.xyqb.repository.IUserHashPhoneNoIdNoMappingRepository; ...@@ -22,11 +22,7 @@ import cn.quantgroup.xyqb.repository.IUserHashPhoneNoIdNoMappingRepository;
import cn.quantgroup.xyqb.repository.IUserRepository; import cn.quantgroup.xyqb.repository.IUserRepository;
import cn.quantgroup.xyqb.service.register.IUserRegisterService; import cn.quantgroup.xyqb.service.register.IUserRegisterService;
import cn.quantgroup.xyqb.service.session.ISessionService; import cn.quantgroup.xyqb.service.session.ISessionService;
import cn.quantgroup.xyqb.service.user.IAddressService; import cn.quantgroup.xyqb.service.user.*;
import cn.quantgroup.xyqb.service.user.IContactService;
import cn.quantgroup.xyqb.service.user.IUserDetailService;
import cn.quantgroup.xyqb.service.user.IUserExtInfoService;
import cn.quantgroup.xyqb.service.user.IUserService;
import cn.quantgroup.xyqb.service.wechat.IWechatService; import cn.quantgroup.xyqb.service.wechat.IWechatService;
import cn.quantgroup.xyqb.util.HashUtil; import cn.quantgroup.xyqb.util.HashUtil;
import cn.quantgroup.xyqb.util.IpUtil; import cn.quantgroup.xyqb.util.IpUtil;
...@@ -94,7 +90,8 @@ public class UserServiceImpl implements IUserService, IBaseController { ...@@ -94,7 +90,8 @@ public class UserServiceImpl implements IUserService, IBaseController {
private IAddressService addressService; private IAddressService addressService;
@Resource @Resource
private IContactService contactService; private IContactService contactService;
@Resource
private ILockIpv4Service lockIpv4Service;
@Override @Override
// @Cacheable(value = "usercache", key = "'xyqbuser' + #phone", unless = "#result == null", cacheManager = "cacheManager") // @Cacheable(value = "usercache", key = "'xyqbuser' + #phone", unless = "#result == null", cacheManager = "cacheManager")
public User findByPhoneInDb(String phone) { public User findByPhoneInDb(String phone) {
...@@ -345,6 +342,7 @@ public class UserServiceImpl implements IUserService, IBaseController { ...@@ -345,6 +342,7 @@ public class UserServiceImpl implements IUserService, IBaseController {
LoginProperties loginProperties = new LoginProperties("", 3, channelId, createdFrom, appChannel, merchant.getId(), merchant.getName()); LoginProperties loginProperties = new LoginProperties("", 3, channelId, createdFrom, appChannel, merchant.getId(), merchant.getName());
AuthBean session = sessionService.createSession(user, loginProperties); AuthBean session = sessionService.createSession(user, loginProperties);
session.setRegister(register); session.setRegister(register);
lockIpv4Service.unLockPhone(phoneNo);
return new JsonResult(session); return new JsonResult(session);
} }
......
Markdown is supported
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