mirror of
https://github.com/chillzhuang/blade-tool
synced 2024-11-13 14:09:29 +08:00
🎉 3.7.0.RELEASE
This commit is contained in:
parent
0885b48ad9
commit
911ebedaa9
@ -5,7 +5,7 @@
|
||||
<parent>
|
||||
<groupId>org.springblade</groupId>
|
||||
<artifactId>blade-tool</artifactId>
|
||||
<version>3.6.0</version>
|
||||
<version>3.7.0</version>
|
||||
</parent>
|
||||
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
@ -88,7 +88,7 @@
|
||||
<dependency>
|
||||
<groupId>com.alibaba</groupId>
|
||||
<artifactId>druid-spring-boot-starter</artifactId>
|
||||
<version>1.2.16</version>
|
||||
<version>1.2.19</version>
|
||||
</dependency>
|
||||
<!-- MySQL -->
|
||||
<dependency>
|
||||
|
@ -101,7 +101,7 @@ mybatis-plus:
|
||||
swagger:
|
||||
title: SpringBlade 接口文档系统
|
||||
description: SpringBlade 接口文档系统
|
||||
version: 3.6.0
|
||||
version: 3.7.0
|
||||
license: Powered By SpringBlade
|
||||
licenseUrl: https://bladex.vip
|
||||
terms-of-service-url: https://bladex.vip
|
||||
|
@ -5,7 +5,7 @@
|
||||
<parent>
|
||||
<artifactId>blade-tool</artifactId>
|
||||
<groupId>org.springblade</groupId>
|
||||
<version>3.6.0</version>
|
||||
<version>3.7.0</version>
|
||||
</parent>
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
|
||||
|
@ -5,7 +5,7 @@
|
||||
<parent>
|
||||
<artifactId>blade-tool</artifactId>
|
||||
<groupId>org.springblade</groupId>
|
||||
<version>3.6.0</version>
|
||||
<version>3.7.0</version>
|
||||
</parent>
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
|
||||
|
@ -5,7 +5,7 @@
|
||||
<parent>
|
||||
<artifactId>blade-tool</artifactId>
|
||||
<groupId>org.springblade</groupId>
|
||||
<version>3.6.0</version>
|
||||
<version>3.7.0</version>
|
||||
</parent>
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
|
||||
|
@ -5,7 +5,7 @@
|
||||
<parent>
|
||||
<artifactId>blade-tool</artifactId>
|
||||
<groupId>org.springblade</groupId>
|
||||
<version>3.6.0</version>
|
||||
<version>3.7.0</version>
|
||||
</parent>
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
|
||||
|
@ -5,7 +5,7 @@
|
||||
<parent>
|
||||
<artifactId>blade-tool</artifactId>
|
||||
<groupId>org.springblade</groupId>
|
||||
<version>3.6.0</version>
|
||||
<version>3.7.0</version>
|
||||
</parent>
|
||||
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
|
@ -25,7 +25,7 @@ public interface AppConstant {
|
||||
/**
|
||||
* 应用版本
|
||||
*/
|
||||
String APPLICATION_VERSION = "3.6.0";
|
||||
String APPLICATION_VERSION = "3.7.0";
|
||||
|
||||
/**
|
||||
* 基础包
|
||||
|
@ -25,6 +25,7 @@ public interface TokenConstant {
|
||||
String AVATAR = "avatar";
|
||||
String HEADER = "blade-auth";
|
||||
String BEARER = "bearer";
|
||||
String CRYPTO = "crypto";
|
||||
String ACCESS_TOKEN = "access_token";
|
||||
String REFRESH_TOKEN = "refresh_token";
|
||||
String TOKEN_TYPE = "token_type";
|
||||
|
@ -18,10 +18,14 @@ package org.springblade.core.launch.props;
|
||||
import lombok.Getter;
|
||||
import lombok.Setter;
|
||||
import org.springframework.boot.context.properties.ConfigurationProperties;
|
||||
import org.springframework.context.EnvironmentAware;
|
||||
import org.springframework.core.env.Environment;
|
||||
import org.springframework.core.env.EnvironmentCapable;
|
||||
import org.springframework.lang.Nullable;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
import java.util.Objects;
|
||||
|
||||
/**
|
||||
* 配置文件
|
||||
@ -29,7 +33,9 @@ import java.util.Map;
|
||||
* @author Chill
|
||||
*/
|
||||
@ConfigurationProperties("blade")
|
||||
public class BladeProperties {
|
||||
public class BladeProperties implements EnvironmentAware, EnvironmentCapable {
|
||||
@Nullable
|
||||
private Environment environment;
|
||||
|
||||
/**
|
||||
* 开发环境
|
||||
@ -204,4 +210,14 @@ public class BladeProperties {
|
||||
return prop.containsKey(key);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setEnvironment(Environment environment) {
|
||||
this.environment = environment;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Environment getEnvironment() {
|
||||
Objects.requireNonNull(environment, "Spring boot 环境下 Environment 不可能为null");
|
||||
return this.environment;
|
||||
}
|
||||
}
|
||||
|
@ -5,7 +5,7 @@
|
||||
<parent>
|
||||
<artifactId>blade-tool</artifactId>
|
||||
<groupId>org.springblade</groupId>
|
||||
<version>3.6.0</version>
|
||||
<version>3.7.0</version>
|
||||
</parent>
|
||||
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
|
@ -5,7 +5,7 @@
|
||||
<parent>
|
||||
<artifactId>blade-tool</artifactId>
|
||||
<groupId>org.springblade</groupId>
|
||||
<version>3.6.0</version>
|
||||
<version>3.7.0</version>
|
||||
</parent>
|
||||
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
|
@ -5,7 +5,7 @@
|
||||
<parent>
|
||||
<artifactId>blade-tool</artifactId>
|
||||
<groupId>org.springblade</groupId>
|
||||
<version>3.6.0</version>
|
||||
<version>3.7.0</version>
|
||||
</parent>
|
||||
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
|
@ -16,6 +16,7 @@
|
||||
package org.springblade.core.mp.support;
|
||||
|
||||
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
|
||||
import org.springblade.core.tool.utils.DateUtil;
|
||||
import org.springblade.core.tool.utils.Func;
|
||||
import org.springblade.core.tool.utils.StringPool;
|
||||
import org.springblade.core.tool.utils.StringUtil;
|
||||
@ -28,17 +29,23 @@ import java.util.Map;
|
||||
* @author Chill
|
||||
*/
|
||||
public class SqlKeyword {
|
||||
private final static String SQL_REGEX = "'|%|--|insert|delete|select|count|group|union|drop|truncate|alter|grant|execute|exec|xp_cmdshell|call|declare|sql";
|
||||
private final static String SQL_REGEX = "'|%|--|insert|delete|select|sleep|count|group|union|drop|truncate|alter|grant|execute|exec|xp_cmdshell|call|declare|sql";
|
||||
|
||||
private static final String EQUAL = "_equal";
|
||||
private static final String NOT_EQUAL = "_notequal";
|
||||
private static final String LIKE = "_like";
|
||||
private static final String LIKE_LEFT = "_likeleft";
|
||||
private static final String LIKE_RIGHT = "_likeright";
|
||||
private static final String NOT_LIKE = "_notlike";
|
||||
private static final String GE = "_ge";
|
||||
private static final String LE = "_le";
|
||||
private static final String GT = "_gt";
|
||||
private static final String LT = "_lt";
|
||||
private static final String DATE_GE = "_datege";
|
||||
private static final String DATE_GT = "_dategt";
|
||||
private static final String DATE_EQUAL = "_dateequal";
|
||||
private static final String DATE_LT = "_datelt";
|
||||
private static final String DATE_LE = "_datele";
|
||||
private static final String IS_NULL = "_null";
|
||||
private static final String NOT_NULL = "_notnull";
|
||||
private static final String IGNORE = "_ignore";
|
||||
@ -57,22 +64,36 @@ public class SqlKeyword {
|
||||
if (Func.hasEmpty(k, v) || k.endsWith(IGNORE)) {
|
||||
return;
|
||||
}
|
||||
// 过滤sql注入关键词
|
||||
k = filter(k);
|
||||
if (k.endsWith(EQUAL)) {
|
||||
qw.eq(getColumn(k, EQUAL), v);
|
||||
} else if (k.endsWith(NOT_EQUAL)) {
|
||||
qw.ne(getColumn(k, NOT_EQUAL), v);
|
||||
} else if (k.endsWith(LIKE_LEFT)) {
|
||||
qw.likeLeft(getColumn(k, LIKE_LEFT), v);
|
||||
} else if (k.endsWith(LIKE_RIGHT)) {
|
||||
qw.likeRight(getColumn(k, LIKE_RIGHT), v);
|
||||
} else if (k.endsWith(NOT_LIKE)) {
|
||||
qw.notLike(getColumn(k, NOT_LIKE), v);
|
||||
} else if (k.endsWith(GE)) {
|
||||
qw.ge(getColumn(k, GE), v);
|
||||
} else if (k.endsWith(LE)) {
|
||||
qw.le(getColumn(k, LE), v);
|
||||
} else if (k.endsWith(GT)) {
|
||||
qw.gt(getColumn(k, GT), v);
|
||||
} else if (k.endsWith(LT)) {
|
||||
qw.lt(getColumn(k, LT), v);
|
||||
} else if (k.endsWith(DATE_GE)) {
|
||||
qw.ge(getColumn(k, DATE_GE), DateUtil.parse(String.valueOf(v), DateUtil.PATTERN_DATETIME));
|
||||
} else if (k.endsWith(DATE_GT)) {
|
||||
qw.gt(getColumn(k, DATE_GT), v);
|
||||
qw.gt(getColumn(k, DATE_GT), DateUtil.parse(String.valueOf(v), DateUtil.PATTERN_DATETIME));
|
||||
} else if (k.endsWith(DATE_EQUAL)) {
|
||||
qw.eq(getColumn(k, DATE_EQUAL), v);
|
||||
qw.eq(getColumn(k, DATE_EQUAL), DateUtil.parse(String.valueOf(v), DateUtil.PATTERN_DATETIME));
|
||||
} else if (k.endsWith(DATE_LE)) {
|
||||
qw.le(getColumn(k, DATE_LE), DateUtil.parse(String.valueOf(v), DateUtil.PATTERN_DATETIME));
|
||||
} else if (k.endsWith(DATE_LT)) {
|
||||
qw.lt(getColumn(k, DATE_LT), v);
|
||||
qw.lt(getColumn(k, DATE_LT), DateUtil.parse(String.valueOf(v), DateUtil.PATTERN_DATETIME));
|
||||
} else if (k.endsWith(IS_NULL)) {
|
||||
qw.isNull(getColumn(k, IS_NULL));
|
||||
} else if (k.endsWith(NOT_NULL)) {
|
||||
@ -106,5 +127,4 @@ public class SqlKeyword {
|
||||
}
|
||||
return param.replaceAll("(?i)" + SQL_REGEX, StringPool.EMPTY);
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -5,7 +5,7 @@
|
||||
<parent>
|
||||
<artifactId>blade-tool</artifactId>
|
||||
<groupId>org.springblade</groupId>
|
||||
<version>3.6.0</version>
|
||||
<version>3.7.0</version>
|
||||
</parent>
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
|
||||
|
@ -5,7 +5,7 @@
|
||||
<parent>
|
||||
<artifactId>blade-tool</artifactId>
|
||||
<groupId>org.springblade</groupId>
|
||||
<version>3.6.0</version>
|
||||
<version>3.7.0</version>
|
||||
</parent>
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
|
||||
|
@ -5,7 +5,7 @@
|
||||
<parent>
|
||||
<artifactId>blade-tool</artifactId>
|
||||
<groupId>org.springblade</groupId>
|
||||
<version>3.6.0</version>
|
||||
<version>3.7.0</version>
|
||||
</parent>
|
||||
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
|
@ -15,11 +15,16 @@
|
||||
*/
|
||||
package org.springblade.core.secure.auth;
|
||||
|
||||
import org.springblade.core.launch.constant.TokenConstant;
|
||||
import org.springblade.core.secure.utils.SecureUtil;
|
||||
import org.springblade.core.tool.constant.RoleConstant;
|
||||
import org.springblade.core.tool.utils.CollectionUtil;
|
||||
import org.springblade.core.tool.utils.Func;
|
||||
import org.springblade.core.tool.utils.StringUtil;
|
||||
import org.springblade.core.tool.utils.WebUtil;
|
||||
|
||||
import javax.servlet.http.HttpServletRequest;
|
||||
import java.util.Objects;
|
||||
|
||||
/**
|
||||
* 权限判断
|
||||
@ -76,4 +81,17 @@ public class AuthFun {
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* 判断请求是否为加密token
|
||||
*
|
||||
* @return {boolean}
|
||||
*/
|
||||
public boolean hasCrypto() {
|
||||
HttpServletRequest request = WebUtil.getRequest();
|
||||
String auth = Objects.requireNonNull(request).getHeader(TokenConstant.HEADER);
|
||||
return SecureUtil.isCrypto(
|
||||
StringUtil.isNotBlank(auth) ? auth : request.getParameter(TokenConstant.HEADER)
|
||||
);
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -37,6 +37,11 @@ public class BladeTokenProperties {
|
||||
*/
|
||||
private String signKey = StringPool.EMPTY;
|
||||
|
||||
/**
|
||||
* token签名
|
||||
*/
|
||||
private String aesKey = StringPool.EMPTY;
|
||||
|
||||
/**
|
||||
* 获取签名规则
|
||||
*/
|
||||
|
@ -46,6 +46,7 @@ public class SecureUtil {
|
||||
|
||||
private final static String HEADER = TokenConstant.HEADER;
|
||||
private final static String BEARER = TokenConstant.BEARER;
|
||||
private final static String CRYPTO = TokenConstant.CRYPTO;
|
||||
private final static String ACCOUNT = TokenConstant.ACCOUNT;
|
||||
private final static String USER_ID = TokenConstant.USER_ID;
|
||||
private final static String ROLE_ID = TokenConstant.ROLE_ID;
|
||||
@ -292,21 +293,56 @@ public class SecureUtil {
|
||||
*/
|
||||
public static Claims getClaims(HttpServletRequest request) {
|
||||
String auth = request.getHeader(SecureUtil.HEADER);
|
||||
if (StringUtil.isNotBlank(auth) && auth.length() > AUTH_LENGTH) {
|
||||
String headStr = auth.substring(0, 6).toLowerCase();
|
||||
if (headStr.compareTo(SecureUtil.BEARER) == 0) {
|
||||
auth = auth.substring(7);
|
||||
return SecureUtil.parseJWT(auth);
|
||||
}
|
||||
} else {
|
||||
String parameter = request.getParameter(SecureUtil.HEADER);
|
||||
if (StringUtil.isNotBlank(parameter)) {
|
||||
return SecureUtil.parseJWT(parameter);
|
||||
}
|
||||
String token = getToken(
|
||||
StringUtil.isNotBlank(auth) ? auth : request.getParameter(SecureUtil.HEADER)
|
||||
);
|
||||
return SecureUtil.parseJWT(token);
|
||||
}
|
||||
|
||||
/**
|
||||
* 获取请求传递的token串
|
||||
*
|
||||
* @param auth token
|
||||
* @return String
|
||||
*/
|
||||
public static String getToken(String auth) {
|
||||
if (isBearer(auth)) {
|
||||
return auth.substring(AUTH_LENGTH);
|
||||
}
|
||||
if (isCrypto(auth)) {
|
||||
return AesUtil.decryptFormBase64ToString(auth.substring(AUTH_LENGTH), getTokenProperties().getAesKey());
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* 判断token类型为bearer
|
||||
*
|
||||
* @param auth token
|
||||
* @return String
|
||||
*/
|
||||
public static Boolean isBearer(String auth) {
|
||||
if ((auth != null) && (auth.length() > AUTH_LENGTH)) {
|
||||
String headStr = auth.substring(0, 6).toLowerCase();
|
||||
return headStr.compareTo(BEARER) == 0;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* 判断token类型为crypto
|
||||
*
|
||||
* @param auth token
|
||||
* @return String
|
||||
*/
|
||||
public static Boolean isCrypto(String auth) {
|
||||
if ((auth != null) && (auth.length() > AUTH_LENGTH)) {
|
||||
String headStr = auth.substring(0, 6).toLowerCase();
|
||||
return headStr.compareTo(CRYPTO) == 0;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* 获取请求头
|
||||
*
|
||||
|
@ -5,7 +5,7 @@
|
||||
<parent>
|
||||
<artifactId>blade-tool</artifactId>
|
||||
<groupId>org.springblade</groupId>
|
||||
<version>3.6.0</version>
|
||||
<version>3.7.0</version>
|
||||
</parent>
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
|
||||
|
@ -5,7 +5,7 @@
|
||||
<parent>
|
||||
<artifactId>blade-tool</artifactId>
|
||||
<groupId>org.springblade</groupId>
|
||||
<version>3.6.0</version>
|
||||
<version>3.7.0</version>
|
||||
</parent>
|
||||
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
|
@ -55,7 +55,7 @@ public class SwaggerProperties {
|
||||
/**
|
||||
* 版本
|
||||
**/
|
||||
private String version = "3.6.0";
|
||||
private String version = "3.7.0";
|
||||
/**
|
||||
* 许可证
|
||||
**/
|
||||
|
@ -5,7 +5,7 @@
|
||||
<parent>
|
||||
<groupId>org.springblade</groupId>
|
||||
<artifactId>blade-tool</artifactId>
|
||||
<version>3.6.0</version>
|
||||
<version>3.7.0</version>
|
||||
</parent>
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
|
||||
|
@ -6,7 +6,7 @@
|
||||
<parent>
|
||||
<groupId>org.springblade</groupId>
|
||||
<artifactId>blade-tool</artifactId>
|
||||
<version>3.6.0</version>
|
||||
<version>3.7.0</version>
|
||||
</parent>
|
||||
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
|
@ -215,6 +215,7 @@ public class R<T> implements Serializable {
|
||||
* 返回R
|
||||
*
|
||||
* @param flag 成功状态
|
||||
* @param <T> 泛型
|
||||
* @return R
|
||||
*/
|
||||
public static <T> R<T> status(boolean flag) {
|
||||
|
@ -42,6 +42,8 @@ public class RequestConfiguration {
|
||||
|
||||
/**
|
||||
* 全局过滤器
|
||||
*
|
||||
* @return 自定义过滤器
|
||||
*/
|
||||
@Bean
|
||||
public FilterRegistrationBean<BladeRequestFilter> bladeFilterRegistration() {
|
||||
|
@ -69,6 +69,10 @@ public interface BladeConstant {
|
||||
* 顶级父节点id
|
||||
*/
|
||||
Long TOP_PARENT_ID = 0L;
|
||||
/**
|
||||
* 顶级父节点名称
|
||||
*/
|
||||
String TOP_PARENT_NAME = "顶级";
|
||||
|
||||
/**
|
||||
* 管理员对应的租户ID
|
||||
|
@ -34,4 +34,6 @@ public class RoleConstant {
|
||||
|
||||
public static final String HAS_ROLE_TEST = "hasRole('" + TEST + "')";
|
||||
|
||||
public static final String HAS_CRYPTO = "hasCrypto()";
|
||||
|
||||
}
|
||||
|
@ -45,6 +45,7 @@ public class MappingApiJackson2HttpMessageConverter extends AbstractReadWriteJac
|
||||
* You can use {@link Jackson2ObjectMapperBuilder} to build it easily.
|
||||
*
|
||||
* @param objectMapper ObjectMapper
|
||||
* @param properties properties
|
||||
* @see Jackson2ObjectMapperBuilder#json()
|
||||
*/
|
||||
public MappingApiJackson2HttpMessageConverter(ObjectMapper objectMapper, BladeJacksonProperties properties) {
|
||||
|
@ -26,10 +26,10 @@ import java.util.List;
|
||||
/**
|
||||
* 节点基类
|
||||
*
|
||||
* @author Chill
|
||||
* @author smallchill
|
||||
*/
|
||||
@Data
|
||||
public class BaseNode implements INode {
|
||||
public class BaseNode<T> implements INode<T> {
|
||||
|
||||
private static final long serialVersionUID = 1L;
|
||||
|
||||
@ -49,7 +49,7 @@ public class BaseNode implements INode {
|
||||
* 子孙节点
|
||||
*/
|
||||
@JsonInclude(JsonInclude.Include.NON_EMPTY)
|
||||
protected List<INode> children = new ArrayList<>();
|
||||
protected List<T> children = new ArrayList<T>();
|
||||
|
||||
/**
|
||||
* 是否有子孙节点
|
||||
@ -59,6 +59,8 @@ public class BaseNode implements INode {
|
||||
|
||||
/**
|
||||
* 是否有子孙节点
|
||||
*
|
||||
* @return Boolean
|
||||
*/
|
||||
@Override
|
||||
public Boolean getHasChildren() {
|
||||
|
@ -22,11 +22,11 @@ import lombok.EqualsAndHashCode;
|
||||
/**
|
||||
* 森林节点类
|
||||
*
|
||||
* @author Chill
|
||||
* @author smallchill
|
||||
*/
|
||||
@Data
|
||||
@EqualsAndHashCode(callSuper = false)
|
||||
public class ForestNode extends BaseNode {
|
||||
public class ForestNode extends BaseNode<ForestNode> {
|
||||
|
||||
private static final long serialVersionUID = 1L;
|
||||
|
||||
|
@ -15,28 +15,33 @@
|
||||
*/
|
||||
package org.springblade.core.tool.node;
|
||||
|
||||
import com.google.common.collect.ImmutableMap;
|
||||
import com.google.common.collect.Maps;
|
||||
import org.springblade.core.tool.utils.StringPool;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
/**
|
||||
* 森林管理类
|
||||
*
|
||||
* @author Chill
|
||||
* @author smallchill
|
||||
*/
|
||||
public class ForestNodeManager<T extends INode> {
|
||||
public class ForestNodeManager<T extends INode<T>> {
|
||||
|
||||
/**
|
||||
* 森林的所有节点
|
||||
*/
|
||||
private List<T> list;
|
||||
private final ImmutableMap<Long, T> nodeMap;
|
||||
|
||||
/**
|
||||
* 森林的父节点ID
|
||||
*/
|
||||
private List<Long> parentIds = new ArrayList<>();
|
||||
private final Map<Long, Object> parentIdMap = Maps.newHashMap();
|
||||
|
||||
public ForestNodeManager(List<T> items) {
|
||||
list = items;
|
||||
public ForestNodeManager(List<T> nodes) {
|
||||
nodeMap = Maps.uniqueIndex(nodes, INode::getId);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -45,11 +50,9 @@ public class ForestNodeManager<T extends INode> {
|
||||
* @param id 节点ID
|
||||
* @return 对应的节点对象
|
||||
*/
|
||||
public INode getTreeNodeAT(Long id) {
|
||||
for (INode forestNode : list) {
|
||||
if (forestNode.getId().longValue() == id) {
|
||||
return forestNode;
|
||||
}
|
||||
public INode<T> getTreeNodeAt(Long id) {
|
||||
if (nodeMap.containsKey(id)) {
|
||||
return nodeMap.get(id);
|
||||
}
|
||||
return null;
|
||||
}
|
||||
@ -60,7 +63,7 @@ public class ForestNodeManager<T extends INode> {
|
||||
* @param parentId 父节点ID
|
||||
*/
|
||||
public void addParentId(Long parentId) {
|
||||
parentIds.add(parentId);
|
||||
parentIdMap.put(parentId, StringPool.EMPTY);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -70,11 +73,11 @@ public class ForestNodeManager<T extends INode> {
|
||||
*/
|
||||
public List<T> getRoot() {
|
||||
List<T> roots = new ArrayList<>();
|
||||
for (T forestNode : list) {
|
||||
if (forestNode.getParentId() == 0 || parentIds.contains(forestNode.getId())) {
|
||||
roots.add(forestNode);
|
||||
nodeMap.forEach((key, node) -> {
|
||||
if (node.getParentId() == 0 || parentIdMap.containsKey(node.getId())) {
|
||||
roots.add(node);
|
||||
}
|
||||
}
|
||||
});
|
||||
return roots;
|
||||
}
|
||||
|
||||
|
@ -20,7 +20,7 @@ import java.util.List;
|
||||
/**
|
||||
* 森林节点归并类
|
||||
*
|
||||
* @author Chill
|
||||
* @author smallchill
|
||||
*/
|
||||
public class ForestNodeMerger {
|
||||
|
||||
@ -29,14 +29,14 @@ public class ForestNodeMerger {
|
||||
* 时间复杂度为O(n^2)
|
||||
*
|
||||
* @param items 节点域
|
||||
* @param <T> T 泛型标记
|
||||
* @param <T> 泛型
|
||||
* @return 多棵树的根节点集合
|
||||
*/
|
||||
public static <T extends INode> List<T> merge(List<T> items) {
|
||||
public static <T extends INode<T>> List<T> merge(List<T> items) {
|
||||
ForestNodeManager<T> forestNodeManager = new ForestNodeManager<>(items);
|
||||
items.forEach(forestNode -> {
|
||||
if (forestNode.getParentId() != 0) {
|
||||
INode node = forestNodeManager.getTreeNodeAT(forestNode.getParentId());
|
||||
INode<T> node = forestNodeManager.getTreeNodeAt(forestNode.getParentId());
|
||||
if (node != null) {
|
||||
node.getChildren().add(forestNode);
|
||||
} else {
|
||||
|
@ -21,21 +21,21 @@ import java.util.List;
|
||||
/**
|
||||
* Created by Blade.
|
||||
*
|
||||
* @author Chill
|
||||
* @author smallchill
|
||||
*/
|
||||
public interface INode extends Serializable {
|
||||
public interface INode<T> extends Serializable {
|
||||
|
||||
/**
|
||||
* 主键
|
||||
*
|
||||
* @return Integer
|
||||
* @return Long
|
||||
*/
|
||||
Long getId();
|
||||
|
||||
/**
|
||||
* 父主键
|
||||
*
|
||||
* @return Integer
|
||||
* @return Long
|
||||
*/
|
||||
Long getParentId();
|
||||
|
||||
@ -44,7 +44,7 @@ public interface INode extends Serializable {
|
||||
*
|
||||
* @return List
|
||||
*/
|
||||
List<INode> getChildren();
|
||||
List<T> getChildren();
|
||||
|
||||
/**
|
||||
* 是否有子孙节点
|
||||
|
@ -8,7 +8,7 @@ import java.util.List;
|
||||
/**
|
||||
* Created by Blade.
|
||||
*
|
||||
* @author Chill
|
||||
* @author smallchill
|
||||
*/
|
||||
public class NodeTest {
|
||||
|
||||
|
@ -18,16 +18,17 @@ package org.springblade.core.tool.node;
|
||||
import com.fasterxml.jackson.databind.annotation.JsonSerialize;
|
||||
import com.fasterxml.jackson.databind.ser.std.ToStringSerializer;
|
||||
import lombok.Data;
|
||||
import lombok.EqualsAndHashCode;
|
||||
import org.springblade.core.tool.utils.Func;
|
||||
|
||||
import java.util.Objects;
|
||||
|
||||
/**
|
||||
* 树型节点类
|
||||
*
|
||||
* @author Chill
|
||||
* @author smallchill
|
||||
*/
|
||||
@Data
|
||||
@EqualsAndHashCode(callSuper = false)
|
||||
public class TreeNode extends BaseNode {
|
||||
public class TreeNode extends BaseNode<TreeNode> {
|
||||
|
||||
private static final long serialVersionUID = 1L;
|
||||
|
||||
@ -39,4 +40,21 @@ public class TreeNode extends BaseNode {
|
||||
@JsonSerialize(using = ToStringSerializer.class)
|
||||
private Long value;
|
||||
|
||||
@Override
|
||||
public boolean equals(Object obj) {
|
||||
if (this == obj) {
|
||||
return true;
|
||||
}
|
||||
if (obj == null) {
|
||||
return false;
|
||||
}
|
||||
TreeNode other = (TreeNode) obj;
|
||||
return Func.equals(this.getId(), other.getId());
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
return Objects.hash(id, parentId);
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -406,6 +406,7 @@ public class DateUtil {
|
||||
* @param dateStr 时间字符串
|
||||
* @param pattern 表达式
|
||||
* @param query 移动查询
|
||||
* @param <T> 泛型
|
||||
* @return 时间
|
||||
*/
|
||||
public static <T> T parse(String dateStr, String pattern, TemporalQuery<T> query) {
|
||||
|
@ -398,6 +398,20 @@ public class Func {
|
||||
return String.valueOf(str);
|
||||
}
|
||||
|
||||
/**
|
||||
* 强转string(包含空字符串),并去掉多余空格
|
||||
*
|
||||
* @param str 字符串
|
||||
* @param defaultValue 默认值
|
||||
* @return {String}
|
||||
*/
|
||||
public static String toStrWithEmpty(Object str, String defaultValue) {
|
||||
if (null == str || str.equals(StringPool.NULL) || str.equals(StringPool.EMPTY)) {
|
||||
return defaultValue;
|
||||
}
|
||||
return String.valueOf(str);
|
||||
}
|
||||
|
||||
/**
|
||||
* 判断一个字符串是否是数字
|
||||
*
|
||||
|
@ -364,7 +364,7 @@ public final class ImageUtil {
|
||||
*
|
||||
* @param src 源图像地址
|
||||
* @param output 目标图像地址
|
||||
* @param type 类型
|
||||
* @param type 类型
|
||||
*/
|
||||
public final static void gray(BufferedImage src, OutputStream output, String type) {
|
||||
try {
|
||||
@ -385,7 +385,7 @@ public final class ImageUtil {
|
||||
*
|
||||
* @param src 源图像
|
||||
* @param output 输出流
|
||||
* @param type 类型
|
||||
* @param type 类型
|
||||
* @param text 水印文字
|
||||
* @param font 水印的字体
|
||||
* @param color 水印的字体颜色
|
||||
@ -424,7 +424,7 @@ public final class ImageUtil {
|
||||
*
|
||||
* @param src 源图像
|
||||
* @param output 输出流
|
||||
* @param type 类型
|
||||
* @param type 类型
|
||||
* @param stamp 水印图片
|
||||
* @param position 水印位置 {@link ImagePosition}
|
||||
* @param x 修正值
|
||||
@ -477,9 +477,10 @@ public final class ImageUtil {
|
||||
|
||||
/**
|
||||
* 默认字符串
|
||||
* @param str 字符串
|
||||
*
|
||||
* @param str 字符串
|
||||
* @param defaultStr 默认值
|
||||
* @return
|
||||
* @return 字符串
|
||||
*/
|
||||
public static String defaultString(String str, String defaultStr) {
|
||||
return ((str == null) ? defaultStr : str);
|
||||
|
@ -5,7 +5,7 @@
|
||||
<parent>
|
||||
<artifactId>blade-tool</artifactId>
|
||||
<groupId>org.springblade</groupId>
|
||||
<version>3.6.0</version>
|
||||
<version>3.7.0</version>
|
||||
</parent>
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
|
||||
|
14
pom.xml
14
pom.xml
@ -5,7 +5,7 @@
|
||||
|
||||
<groupId>org.springblade</groupId>
|
||||
<artifactId>blade-tool</artifactId>
|
||||
<version>3.6.0</version>
|
||||
<version>3.7.0</version>
|
||||
<packaging>pom</packaging>
|
||||
<name>blade-tool</name>
|
||||
<description>
|
||||
@ -36,14 +36,14 @@
|
||||
</scm>
|
||||
|
||||
<properties>
|
||||
<blade.tool.version>3.6.0</blade.tool.version>
|
||||
<blade.tool.version>3.7.0</blade.tool.version>
|
||||
|
||||
<java.version>1.8</java.version>
|
||||
<maven.plugin.version>3.8.1</maven.plugin.version>
|
||||
|
||||
<knife4j.version>4.1.0</knife4j.version>
|
||||
<mybatis.plus.version>3.5.3.1</mybatis.plus.version>
|
||||
<mybatis.plus.generator.version>3.5.3.1</mybatis.plus.generator.version>
|
||||
<mybatis.plus.version>3.5.3.2</mybatis.plus.version>
|
||||
<mybatis.plus.generator.version>3.5.3.2</mybatis.plus.generator.version>
|
||||
<protostuff.version>1.6.0</protostuff.version>
|
||||
<disruptor.version>3.4.2</disruptor.version>
|
||||
<guava.version>31.1-jre</guava.version>
|
||||
@ -52,10 +52,10 @@
|
||||
<alibaba.cloud.version>2021.0.5.0</alibaba.cloud.version>
|
||||
<alibaba.nacos.version>2.1.2</alibaba.nacos.version>
|
||||
|
||||
<spring.version>5.3.27</spring.version>
|
||||
<spring.boot.version>2.7.10</spring.boot.version>
|
||||
<spring.version>5.3.29</spring.version>
|
||||
<spring.boot.version>2.7.15</spring.boot.version>
|
||||
<spring.boot.admin.version>2.7.10</spring.boot.admin.version>
|
||||
<spring.cloud.version>2021.0.6</spring.cloud.version>
|
||||
<spring.cloud.version>2021.0.8</spring.cloud.version>
|
||||
|
||||
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
|
||||
<maven.compiler.encoding>UTF-8</maven.compiler.encoding>
|
||||
|
Loading…
Reference in New Issue
Block a user