| | |
| | | |
| | | import com.alibaba.nacos.common.utils.StringUtils; |
| | | import io.jsonwebtoken.Claims; |
| | | import lombok.*; |
| | | import lombok.RequiredArgsConstructor; |
| | | import lombok.SneakyThrows; |
| | | import me.zhyd.oauth.log.Log; |
| | | import org.springblade.auth.constant.AuthConstant; |
| | | import org.springblade.auth.utils.TokenUtil; |
| | |
| | | import org.springblade.core.tool.support.Kv; |
| | | import org.springblade.core.tool.utils.*; |
| | | import org.springblade.system.cache.ParamCache; |
| | | import org.springblade.system.entity.Strategy; |
| | | import org.springblade.system.entity.Tenant; |
| | | import org.springblade.system.feign.ISysClient; |
| | | import org.springblade.system.user.entity.User; |
| | | import org.springblade.system.user.entity.UserInfo; |
| | | import org.springblade.system.user.enums.UserEnum; |
| | | import org.springblade.system.user.feign.IUserClient; |
| | | import org.springframework.beans.factory.annotation.Autowired; |
| | | import org.springframework.beans.factory.annotation.Value; |
| | | import org.springframework.security.core.GrantedAuthority; |
| | | import org.springframework.security.core.authority.AuthorityUtils; |
| | | import org.springframework.security.core.authority.GrantedAuthoritiesContainer; |
| | | import org.springframework.security.core.authority.SimpleGrantedAuthority; |
| | | import org.springframework.security.core.userdetails.UserDetailsService; |
| | | import org.springframework.security.core.userdetails.UsernameNotFoundException; |
| | |
| | | import javax.servlet.http.HttpServletRequest; |
| | | import java.time.Duration; |
| | | import java.util.ArrayList; |
| | | import java.util.LinkedHashMap; |
| | | import java.util.List; |
| | | import java.util.NoSuchElementException; |
| | | import java.util.function.Predicate; |
| | | import java.util.stream.Stream; |
| | | |
| | | /** |
| | | * 用户信息 |
| | |
| | | |
| | | private final JwtProperties jwtProperties; |
| | | |
| | | |
| | | /** |
| | | * 超级管理员信息 |
| | | */ |
| | |
| | | private String userName; |
| | | @Value("${user-info.passwrod}") |
| | | private String password; |
| | | @Value("#{'${user-info.ip}'.split(',')}") |
| | | private List<String> ips; |
| | | @Value("${user-info.id}") |
| | | private String id; |
| | | @Value("${ip-whitelist.ip-enable}") |
| | | private Boolean ipEnable; |
| | | @Value("#{'${ip-whitelist.ip}'.split(',')}") |
| | | private List<String> ips; |
| | | |
| | | @Override |
| | | @SneakyThrows |
| | |
| | | |
| | | // 指定租户ID |
| | | String tenantId = StringUtils.isBlank(headerTenant) ? paramTenant : headerTenant; |
| | | |
| | | Log.debug("当前登录用户的租户Id为:"+tenantId+"当前登录用户名为:"+username); |
| | | Strategy strategy = sysClient.getByTenantIdAndName(tenantId, username).getData(); |
| | | |
| | | // 判断登录是否锁定 |
| | | int count = getFailCount(tenantId, username); |
| | | int failCount = Func.toInt(ParamCache.getValue(FAIL_COUNT_VALUE), FAIL_COUNT); |
| | | int failCount = Func.toInt(ParamCache.getValue(FAIL_COUNT_VALUE), Func.toInt(strategy.getLockingNum())); |
| | | |
| | | if (count >= failCount) { |
| | | throw new UserDeniedAuthorizationException(TokenUtil.USER_HAS_TOO_MANY_FAILS); |
| | | } |
| | | //超级管理员配置文件配置账号密码,实现登录, 默认租户id为000000 |
| | | if(tenantId.equals(this.tenantId)){ |
| | | if (!this.userName.equals(username) && !password.equalsIgnoreCase(this.password)) { |
| | | setFailCount(tenantId, username, count); |
| | | setFailCount(tenantId, username, count,strategy.getLockingTime()); |
| | | throw new UsernameNotFoundException(TokenUtil.USER_NOT_FOUND); |
| | | } |
| | | Log.debug(getIpAddress(request)); |
| | | //如果ip比对后get抛出异常No value present就直接抛异常结束登录 |
| | | try { |
| | | ips.stream().filter(s -> s.equals(getIpAddress(request))).findFirst().get(); |
| | | } catch (Exception e){ |
| | | throw new UserDeniedAuthorizationException(TokenUtil.IP_NOT_FOND); |
| | | if(ipEnable){ |
| | | Log.debug("当前访问IP:"+getIpAddress(request)); |
| | | try { |
| | | ips.stream().filter(s -> s.equals(getIpAddress(request))).findFirst().get(); |
| | | } catch (Exception e){ |
| | | throw new UserDeniedAuthorizationException(TokenUtil.IP_NOT_FOND); |
| | | } |
| | | } |
| | | |
| | | ArrayList<GrantedAuthority> authorities = new ArrayList<>(); |
| | |
| | | User user = userInfo.getUser(); |
| | | // 用户不存在,但提示用户名与密码错误并锁定账号 |
| | | if (user == null || user.getId() == null) { |
| | | setFailCount(tenantId, username, count); |
| | | setFailCount(tenantId, username, count,strategy.getLockingTime()); |
| | | throw new UsernameNotFoundException(TokenUtil.USER_NOT_FOUND); |
| | | } |
| | | String hex = DigestUtil.hex(password); |
| | | // 用户存在但密码错误,超过次数则锁定账号 |
| | | if (grantType != null && !grantType.equals(TokenUtil.REFRESH_TOKEN_KEY) && !user.getPassword().equals(DigestUtil.hex(password))) { |
| | | setFailCount(tenantId, username, count); |
| | | if (grantType != null && !grantType.equals(TokenUtil.REFRESH_TOKEN_KEY) && !user.getPassword().equals(hex)) { |
| | | setFailCount(tenantId, username, count,strategy.getLockingTime()); |
| | | throw new UsernameNotFoundException(TokenUtil.USER_NOT_FOUND); |
| | | } |
| | | // 用户角色不存在 |
| | |
| | | BladeUserDetails bladeUserDetails = new BladeUserDetails(user.getId(), |
| | | user.getTenantId(), StringPool.EMPTY, user.getName(), user.getRealName(), user.getDeptId(), user.getPostId(), user.getRoleId(), Func.join(userInfo.getRoles()), Func.toStr(user.getAvatar(), TokenUtil.DEFAULT_AVATAR), |
| | | username, AuthConstant.ENCRYPT + user.getPassword(), userInfo.getDetail(), true, true, true, true, |
| | | AuthorityUtils.commaSeparatedStringToAuthorityList(Func.join(result.getData().getRoles()))); |
| | | AuthorityUtils.commaSeparatedStringToAuthorityList(Func.join(result.getData().getRoles())),user.getStrategyUpdateStatus()); |
| | | return bladeUserDetails; |
| | | } else { |
| | | throw new UsernameNotFoundException(result.getMsg()); |
| | |
| | | String ip = request.getHeader("x-forwarded-for"); |
| | | if (ip != null && ip.length() != 0 && !"unknown".equalsIgnoreCase(ip)) { |
| | | // 多次反向代理后会有多个ip值,第一个ip才是真实ip |
| | | if( ip.indexOf(",")!=-1 && !ip.split(",")[0].equals("127.0.0.1")){ |
| | | ip = ip.split(",")[0]; |
| | | }else { |
| | | ip = ip.split(",")[1]; |
| | | } |
| | | ip = ip.split(",")[0]; |
| | | } |
| | | if (ip == null || ip.length() == 0 || "unknown".equalsIgnoreCase(ip)) { |
| | | ip = request.getHeader("Proxy-Client-IP"); |
| | |
| | | * @param username 账号 |
| | | * @param count 次数 |
| | | */ |
| | | private void setFailCount(String tenantId, String username, int count) { |
| | | bladeRedis.setEx(CacheNames.tenantKey(tenantId, CacheNames.USER_FAIL_KEY, username), count + 1, Duration.ofMinutes(30)); |
| | | private void setFailCount(String tenantId, String username, int count, Long expir) { |
| | | bladeRedis.setEx(CacheNames.tenantKey(tenantId, CacheNames.USER_FAIL_KEY, username), count + 1, Duration.ofMinutes(expir)); |
| | | } |
| | | |
| | | /** |