From b70e709e532eacf0f92b96c971541c6b5204106e Mon Sep 17 00:00:00 2001 From: EightMonth Date: Wed, 16 Apr 2025 16:18:32 +0800 Subject: [PATCH 01/11] =?UTF-8?q?=E5=8D=87=E7=BA=A7spring=20boot=203.4.4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- jeecg-boot/jeecg-boot-base-core/pom.xml | 10 +- .../jeecg/common/aspect/AutoLogAspect.java | 1 - .../sqlInjection/InjectionAstNodeVisitor.java | 66 +- .../InjectionSyntaxObjectAnalyzer.java | 342 ++--- .../sqlInjection/SqlInjectionAnalyzer.java | 130 +- .../sqlInjection/parse/ConstAnalyzer.java | 1138 ++++++++--------- .../sqlInjection/parse/ParserSupport.java | 354 ++--- .../parse/SqlSyntaxNormalizer.java | 74 +- .../sqlparse/JSqlParserAllTableManager.java | 510 ++++---- .../common/util/sqlparse/JSqlParserUtils.java | 380 +++--- .../util/sqlparse/vo/SelectSqlInfo.java | 202 +-- .../org/jeecg/config/WebMvcConfiguration.java | 2 +- .../config/mybatis/MybatisPlusSaasConfig.java | 6 +- .../org/jeecg/config/oss/MinioConfig.java | 3 +- .../jeecg/config/oss/OssConfiguration.java | 3 +- .../test/sqlparse/JSqlParserUtilsTest.java | 218 ++-- .../jeecg-system-biz/pom.xml | 10 +- .../impl/DictTableWhiteListHandlerImpl.java | 83 +- .../JimuDragExternalServiceImpl.java | 248 ++-- .../jimureport/JimuReportTokenService.java | 214 ++-- .../mongo/MongoAutoConfiguration.java | 116 +- jeecg-boot/pom.xml | 10 +- 22 files changed, 2062 insertions(+), 2058 deletions(-) diff --git a/jeecg-boot/jeecg-boot-base-core/pom.xml b/jeecg-boot/jeecg-boot-base-core/pom.xml index 2c41434bd..ba0bda318 100644 --- a/jeecg-boot/jeecg-boot-base-core/pom.xml +++ b/jeecg-boot/jeecg-boot-base-core/pom.xml @@ -112,7 +112,15 @@ com.baomidou - mybatis-plus-boot-starter + mybatis-plus-spring-boot3-starter + ${mybatis-plus.version} + + + com.baomidou + + mybatis-plus-jsqlparser + + ${mybatis-plus.version} diff --git a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/aspect/AutoLogAspect.java b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/aspect/AutoLogAspect.java index c9c4c901d..aaf0a61f7 100644 --- a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/aspect/AutoLogAspect.java +++ b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/aspect/AutoLogAspect.java @@ -20,7 +20,6 @@ import org.jeecg.common.system.vo.LoginUser; import org.jeecg.common.util.IpUtils; import org.jeecg.common.util.SpringContextUtils; import org.jeecg.common.util.oConvertUtils; -import org.springframework.core.LocalVariableTableParameterNameDiscoverer; import org.springframework.core.StandardReflectionParameterNameDiscoverer; import org.springframework.stereotype.Component; import org.springframework.validation.BindingResult; diff --git a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/sqlInjection/InjectionAstNodeVisitor.java b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/sqlInjection/InjectionAstNodeVisitor.java index 12444d9a9..77d21e4a3 100644 --- a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/sqlInjection/InjectionAstNodeVisitor.java +++ b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/sqlInjection/InjectionAstNodeVisitor.java @@ -1,33 +1,33 @@ -package org.jeecg.common.util.sqlInjection; - -import net.sf.jsqlparser.parser.CCJSqlParserDefaultVisitor; -import net.sf.jsqlparser.parser.SimpleNode; -import net.sf.jsqlparser.statement.select.UnionOp; -import org.jeecg.common.exception.JeecgSqlInjectionException; - -/** - * 基于抽象语法树(AST)的注入攻击分析实现 - * - * @author guyadong - */ -public class InjectionAstNodeVisitor extends CCJSqlParserDefaultVisitor { - public InjectionAstNodeVisitor() { - } - - /** - * 处理禁止联合查询 - * - * @param node - * @param data - * @return - */ - @Override - public Object visit(SimpleNode node, Object data) { - Object value = node.jjtGetValue(); - if (value instanceof UnionOp) { - throw new JeecgSqlInjectionException("DISABLE UNION"); - } - return super.visit(node, data); - } -} - +//package org.jeecg.common.util.sqlInjection; +// +//import net.sf.jsqlparser.parser.CCJSqlParserDefaultVisitor; +//import net.sf.jsqlparser.parser.SimpleNode; +//import net.sf.jsqlparser.statement.select.UnionOp; +//import org.jeecg.common.exception.JeecgSqlInjectionException; +// +///** +// * 基于抽象语法树(AST)的注入攻击分析实现 +// * +// * @author guyadong +// */ +//public class InjectionAstNodeVisitor extends CCJSqlParserDefaultVisitor { +// public InjectionAstNodeVisitor() { +// } +// +// /** +// * 处理禁止联合查询 +// * +// * @param node +// * @param data +// * @return +// */ +// @Override +// public Object visit(SimpleNode node, Object data) { +// Object value = node.jjtGetValue(); +// if (value instanceof UnionOp) { +// throw new JeecgSqlInjectionException("DISABLE UNION"); +// } +// return super.visit(node, data); +// } +//} +// diff --git a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/sqlInjection/InjectionSyntaxObjectAnalyzer.java b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/sqlInjection/InjectionSyntaxObjectAnalyzer.java index b31f7c362..28a515272 100644 --- a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/sqlInjection/InjectionSyntaxObjectAnalyzer.java +++ b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/sqlInjection/InjectionSyntaxObjectAnalyzer.java @@ -1,172 +1,172 @@ -package org.jeecg.common.util.sqlInjection; - - -import net.sf.jsqlparser.expression.BinaryExpression; -import net.sf.jsqlparser.expression.Expression; -import net.sf.jsqlparser.expression.Function; -import net.sf.jsqlparser.expression.operators.conditional.AndExpression; -import net.sf.jsqlparser.expression.operators.conditional.OrExpression; -import net.sf.jsqlparser.expression.operators.relational.ComparisonOperator; -import net.sf.jsqlparser.schema.Column; -import net.sf.jsqlparser.statement.select.Join; -import net.sf.jsqlparser.statement.select.OrderByElement; -import net.sf.jsqlparser.statement.select.PlainSelect; -import net.sf.jsqlparser.statement.select.SelectItem; -import net.sf.jsqlparser.statement.select.SubSelect; -import net.sf.jsqlparser.statement.select.WithItem; -import net.sf.jsqlparser.util.TablesNamesFinder; -import org.jeecg.common.exception.JeecgSqlInjectionException; -import org.jeecg.common.util.sqlInjection.parse.ConstAnalyzer; -import org.jeecg.common.util.sqlInjection.parse.ParserSupport; - -/** - * 基于SQL语法对象的SQL注入攻击分析实现 - * - * @author guyadong - */ -public class InjectionSyntaxObjectAnalyzer extends TablesNamesFinder { - /** - * 危险函数名 - */ - private static final String DANGROUS_FUNCTIONS = "(sleep|benchmark|extractvalue|updatexml|ST_LatFromGeoHash|ST_LongFromGeoHash|GTID_SUBSET|GTID_SUBTRACT|floor|ST_Pointfromgeohash" - + "|geometrycollection|multipoint|polygon|multipolygon|linestring|multilinestring)"; - - private static ThreadLocal disableSubselect = new ThreadLocal() { - @Override - protected Boolean initialValue() { - return true; - } - }; - private ConstAnalyzer constAnalyzer = new ConstAnalyzer(); - - public InjectionSyntaxObjectAnalyzer() { - super(); - init(true); - - } - - @Override - public void visitBinaryExpression(BinaryExpression binaryExpression) { - if (binaryExpression instanceof ComparisonOperator) { - if (isConst(binaryExpression.getLeftExpression()) && isConst(binaryExpression.getRightExpression())) { - /** 禁用恒等式 */ - throw new JeecgSqlInjectionException("DISABLE IDENTICAL EQUATION " + binaryExpression); - } - } - super.visitBinaryExpression(binaryExpression); - } - - @Override - public void visit(AndExpression andExpression) { - super.visit(andExpression); - checkConstExpress(andExpression.getLeftExpression()); - checkConstExpress(andExpression.getRightExpression()); - } - - @Override - public void visit(OrExpression orExpression) { - super.visit(orExpression); - checkConstExpress(orExpression.getLeftExpression()); - checkConstExpress(orExpression.getRightExpression()); - } - - @Override - public void visit(Function function) { - if (function.getName().matches(DANGROUS_FUNCTIONS)) { - /** 禁用危险函数 */ - throw new JeecgSqlInjectionException("DANGROUS FUNCTION: " + function.getName()); - } - super.visit(function); - } - - @Override - public void visit(WithItem withItem) { - try { - /** 允许 WITH 语句中的子查询 */ - disableSubselect.set(false); - super.visit(withItem); - } finally { - disableSubselect.set(true); - } - } - - @Override - public void visit(SubSelect subSelect) { - try { - /** 允许语句中的子查询 */ - disableSubselect.set(false); - super.visit(subSelect); - } finally { - disableSubselect.set(true); - } -// if (disableSubselect.get()) { -// // 禁用子查询 -// throw new JeecgSqlInjectionException("DISABLE subselect " + subSelect); +//package org.jeecg.common.util.sqlInjection; +// +// +//import net.sf.jsqlparser.expression.BinaryExpression; +//import net.sf.jsqlparser.expression.Expression; +//import net.sf.jsqlparser.expression.Function; +//import net.sf.jsqlparser.expression.operators.conditional.AndExpression; +//import net.sf.jsqlparser.expression.operators.conditional.OrExpression; +//import net.sf.jsqlparser.expression.operators.relational.ComparisonOperator; +//import net.sf.jsqlparser.schema.Column; +//import net.sf.jsqlparser.statement.select.Join; +//import net.sf.jsqlparser.statement.select.OrderByElement; +//import net.sf.jsqlparser.statement.select.PlainSelect; +//import net.sf.jsqlparser.statement.select.SelectItem; +//import net.sf.jsqlparser.statement.select.SubSelect; +//import net.sf.jsqlparser.statement.select.WithItem; +//import net.sf.jsqlparser.util.TablesNamesFinder; +//import org.jeecg.common.exception.JeecgSqlInjectionException; +//import org.jeecg.common.util.sqlInjection.parse.ConstAnalyzer; +//import org.jeecg.common.util.sqlInjection.parse.ParserSupport; +// +///** +// * 基于SQL语法对象的SQL注入攻击分析实现 +// * +// * @author guyadong +// */ +//public class InjectionSyntaxObjectAnalyzer extends TablesNamesFinder { +// /** +// * 危险函数名 +// */ +// private static final String DANGROUS_FUNCTIONS = "(sleep|benchmark|extractvalue|updatexml|ST_LatFromGeoHash|ST_LongFromGeoHash|GTID_SUBSET|GTID_SUBTRACT|floor|ST_Pointfromgeohash" +// + "|geometrycollection|multipoint|polygon|multipolygon|linestring|multilinestring)"; +// +// private static ThreadLocal disableSubselect = new ThreadLocal() { +// @Override +// protected Boolean initialValue() { +// return true; // } - } - - @Override - public void visit(Column tableColumn) { - if (ParserSupport.isBoolean(tableColumn)) { - throw new JeecgSqlInjectionException("DISABLE CONST BOOL " + tableColumn); - } - super.visit(tableColumn); - } - - @Override - public void visit(PlainSelect plainSelect) { - if (plainSelect.getSelectItems() != null) { - for (SelectItem item : plainSelect.getSelectItems()) { - item.accept(this); - } - } - - if (plainSelect.getFromItem() != null) { - plainSelect.getFromItem().accept(this); - } - - if (plainSelect.getJoins() != null) { - for (Join join : plainSelect.getJoins()) { - join.getRightItem().accept(this); - for (Expression e : join.getOnExpressions()) { - e.accept(this); - } - } - } - if (plainSelect.getWhere() != null) { - plainSelect.getWhere().accept(this); - checkConstExpress(plainSelect.getWhere()); - } - - if (plainSelect.getHaving() != null) { - plainSelect.getHaving().accept(this); - } - - if (plainSelect.getOracleHierarchical() != null) { - plainSelect.getOracleHierarchical().accept(this); - } - if (plainSelect.getOrderByElements() != null) { - for (OrderByElement orderByElement : plainSelect.getOrderByElements()) { - orderByElement.getExpression().accept(this); - } - } - if (plainSelect.getGroupBy() != null) { - for (Expression expression : plainSelect.getGroupBy().getGroupByExpressionList().getExpressions()) { - expression.accept(this); - } - } - } - - private boolean isConst(Expression expression) { - return constAnalyzer.isConstExpression(expression); - } - - private void checkConstExpress(Expression expression) { - if (constAnalyzer.isConstExpression(expression)) { - /** 禁用常量表达式 */ - throw new JeecgSqlInjectionException("DISABLE CONST EXPRESSION " + expression); - } - } -} - - +// }; +// private ConstAnalyzer constAnalyzer = new ConstAnalyzer(); +// +// public InjectionSyntaxObjectAnalyzer() { +// super(); +// init(true); +// +// } +// +// @Override +// public void visitBinaryExpression(BinaryExpression binaryExpression) { +// if (binaryExpression instanceof ComparisonOperator) { +// if (isConst(binaryExpression.getLeftExpression()) && isConst(binaryExpression.getRightExpression())) { +// /** 禁用恒等式 */ +// throw new JeecgSqlInjectionException("DISABLE IDENTICAL EQUATION " + binaryExpression); +// } +// } +// super.visitBinaryExpression(binaryExpression); +// } +// +// @Override +// public void visit(AndExpression andExpression) { +// super.visit(andExpression); +// checkConstExpress(andExpression.getLeftExpression()); +// checkConstExpress(andExpression.getRightExpression()); +// } +// +// @Override +// public void visit(OrExpression orExpression) { +// super.visit(orExpression); +// checkConstExpress(orExpression.getLeftExpression()); +// checkConstExpress(orExpression.getRightExpression()); +// } +// +// @Override +// public void visit(Function function) { +// if (function.getName().matches(DANGROUS_FUNCTIONS)) { +// /** 禁用危险函数 */ +// throw new JeecgSqlInjectionException("DANGROUS FUNCTION: " + function.getName()); +// } +// super.visit(function); +// } +// +// @Override +// public void visit(WithItem withItem) { +// try { +// /** 允许 WITH 语句中的子查询 */ +// disableSubselect.set(false); +// super.visit(withItem); +// } finally { +// disableSubselect.set(true); +// } +// } +// +// @Override +// public void visit(SubSelect subSelect) { +// try { +// /** 允许语句中的子查询 */ +// disableSubselect.set(false); +// super.visit(subSelect); +// } finally { +// disableSubselect.set(true); +// } +//// if (disableSubselect.get()) { +//// // 禁用子查询 +//// throw new JeecgSqlInjectionException("DISABLE subselect " + subSelect); +//// } +// } +// +// @Override +// public void visit(Column tableColumn) { +// if (ParserSupport.isBoolean(tableColumn)) { +// throw new JeecgSqlInjectionException("DISABLE CONST BOOL " + tableColumn); +// } +// super.visit(tableColumn); +// } +// +// @Override +// public void visit(PlainSelect plainSelect) { +// if (plainSelect.getSelectItems() != null) { +// for (SelectItem item : plainSelect.getSelectItems()) { +// item.accept(this); +// } +// } +// +// if (plainSelect.getFromItem() != null) { +// plainSelect.getFromItem().accept(this); +// } +// +// if (plainSelect.getJoins() != null) { +// for (Join join : plainSelect.getJoins()) { +// join.getRightItem().accept(this); +// for (Expression e : join.getOnExpressions()) { +// e.accept(this); +// } +// } +// } +// if (plainSelect.getWhere() != null) { +// plainSelect.getWhere().accept(this); +// checkConstExpress(plainSelect.getWhere()); +// } +// +// if (plainSelect.getHaving() != null) { +// plainSelect.getHaving().accept(this); +// } +// +// if (plainSelect.getOracleHierarchical() != null) { +// plainSelect.getOracleHierarchical().accept(this); +// } +// if (plainSelect.getOrderByElements() != null) { +// for (OrderByElement orderByElement : plainSelect.getOrderByElements()) { +// orderByElement.getExpression().accept(this); +// } +// } +// if (plainSelect.getGroupBy() != null) { +// for (Expression expression : plainSelect.getGroupBy().getGroupByExpressionList().getExpressions()) { +// expression.accept(this); +// } +// } +// } +// +// private boolean isConst(Expression expression) { +// return constAnalyzer.isConstExpression(expression); +// } +// +// private void checkConstExpress(Expression expression) { +// if (constAnalyzer.isConstExpression(expression)) { +// /** 禁用常量表达式 */ +// throw new JeecgSqlInjectionException("DISABLE CONST EXPRESSION " + expression); +// } +// } +//} +// +// diff --git a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/sqlInjection/SqlInjectionAnalyzer.java b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/sqlInjection/SqlInjectionAnalyzer.java index 61f06a714..88f3fd3e7 100644 --- a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/sqlInjection/SqlInjectionAnalyzer.java +++ b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/sqlInjection/SqlInjectionAnalyzer.java @@ -1,65 +1,65 @@ -package org.jeecg.common.util.sqlInjection; - -import org.jeecg.common.exception.JeecgSqlInjectionException; -import org.jeecg.common.util.sqlInjection.parse.ParserSupport; -; - -/** - * SQL注入攻击分析器 - * - * @author guyadong - * 参考: - * https://blog.csdn.net/10km/article/details/127767358 - * https://gitee.com/l0km/sql2java/tree/dev/sql2java-manager/src/main/java/gu/sql2java/parser - */ -public class SqlInjectionAnalyzer { - - //启用/关闭注入攻击检查 - private boolean injectCheckEnable = true; - //防止SQL注入攻击分析实现 - private final InjectionSyntaxObjectAnalyzer injectionChecker; - private final InjectionAstNodeVisitor injectionVisitor; - - public SqlInjectionAnalyzer() { - this.injectionChecker = new InjectionSyntaxObjectAnalyzer(); - this.injectionVisitor = new InjectionAstNodeVisitor(); - } - - /** - * 启用/关闭注入攻击检查,默认启动 - * - * @param enable - * @return - */ - public SqlInjectionAnalyzer injectCheckEnable(boolean enable) { - injectCheckEnable = enable; - return this; - } - - /** - * 对解析后的SQL对象执行注入攻击分析,有注入攻击的危险则抛出异常{@link JeecgSqlInjectionException} - * - * @param sqlParserInfo - * @throws JeecgSqlInjectionException - */ - public ParserSupport.SqlParserInfo injectAnalyse(ParserSupport.SqlParserInfo sqlParserInfo) throws JeecgSqlInjectionException { - if (null != sqlParserInfo && injectCheckEnable) { - /** SQL注入攻击检查 */ - sqlParserInfo.statement.accept(injectionChecker); - sqlParserInfo.simpleNode.jjtAccept(injectionVisitor, null); - } - return sqlParserInfo; - } - - /** - * sql校验 - */ - public static void checkSql(String sql,boolean check){ - SqlInjectionAnalyzer sqlInjectionAnalyzer = new SqlInjectionAnalyzer(); - sqlInjectionAnalyzer.injectCheckEnable(check); - ParserSupport.SqlParserInfo sqlParserInfo = ParserSupport.parse0(sql, null,null); - sqlInjectionAnalyzer.injectAnalyse(sqlParserInfo); - } -} - - +//package org.jeecg.common.util.sqlInjection; +// +//import org.jeecg.common.exception.JeecgSqlInjectionException; +//import org.jeecg.common.util.sqlInjection.parse.ParserSupport; +//; +// +///** +// * SQL注入攻击分析器 +// * +// * @author guyadong +// * 参考: +// * https://blog.csdn.net/10km/article/details/127767358 +// * https://gitee.com/l0km/sql2java/tree/dev/sql2java-manager/src/main/java/gu/sql2java/parser +// */ +//public class SqlInjectionAnalyzer { +// +// //启用/关闭注入攻击检查 +// private boolean injectCheckEnable = true; +// //防止SQL注入攻击分析实现 +// private final InjectionSyntaxObjectAnalyzer injectionChecker; +// private final InjectionAstNodeVisitor injectionVisitor; +// +// public SqlInjectionAnalyzer() { +// this.injectionChecker = new InjectionSyntaxObjectAnalyzer(); +// this.injectionVisitor = new InjectionAstNodeVisitor(); +// } +// +// /** +// * 启用/关闭注入攻击检查,默认启动 +// * +// * @param enable +// * @return +// */ +// public SqlInjectionAnalyzer injectCheckEnable(boolean enable) { +// injectCheckEnable = enable; +// return this; +// } +// +// /** +// * 对解析后的SQL对象执行注入攻击分析,有注入攻击的危险则抛出异常{@link JeecgSqlInjectionException} +// * +// * @param sqlParserInfo +// * @throws JeecgSqlInjectionException +// */ +// public ParserSupport.SqlParserInfo injectAnalyse(ParserSupport.SqlParserInfo sqlParserInfo) throws JeecgSqlInjectionException { +// if (null != sqlParserInfo && injectCheckEnable) { +// /** SQL注入攻击检查 */ +// sqlParserInfo.statement.accept(injectionChecker); +// sqlParserInfo.simpleNode.jjtAccept(injectionVisitor, null); +// } +// return sqlParserInfo; +// } +// +// /** +// * sql校验 +// */ +// public static void checkSql(String sql,boolean check){ +// SqlInjectionAnalyzer sqlInjectionAnalyzer = new SqlInjectionAnalyzer(); +// sqlInjectionAnalyzer.injectCheckEnable(check); +// ParserSupport.SqlParserInfo sqlParserInfo = ParserSupport.parse0(sql, null,null); +// sqlInjectionAnalyzer.injectAnalyse(sqlParserInfo); +// } +//} +// +// diff --git a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/sqlInjection/parse/ConstAnalyzer.java b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/sqlInjection/parse/ConstAnalyzer.java index 9b7345c07..492040964 100644 --- a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/sqlInjection/parse/ConstAnalyzer.java +++ b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/sqlInjection/parse/ConstAnalyzer.java @@ -1,569 +1,569 @@ -package org.jeecg.common.util.sqlInjection.parse; - -import net.sf.jsqlparser.expression.*; -import net.sf.jsqlparser.expression.operators.arithmetic.Addition; -import net.sf.jsqlparser.expression.operators.arithmetic.BitwiseAnd; -import net.sf.jsqlparser.expression.operators.arithmetic.BitwiseLeftShift; -import net.sf.jsqlparser.expression.operators.arithmetic.BitwiseOr; -import net.sf.jsqlparser.expression.operators.arithmetic.BitwiseRightShift; -import net.sf.jsqlparser.expression.operators.arithmetic.BitwiseXor; -import net.sf.jsqlparser.expression.operators.arithmetic.Concat; -import net.sf.jsqlparser.expression.operators.arithmetic.Division; -import net.sf.jsqlparser.expression.operators.arithmetic.IntegerDivision; -import net.sf.jsqlparser.expression.operators.arithmetic.Modulo; -import net.sf.jsqlparser.expression.operators.arithmetic.Multiplication; -import net.sf.jsqlparser.expression.operators.arithmetic.Subtraction; -import net.sf.jsqlparser.expression.operators.conditional.AndExpression; -import net.sf.jsqlparser.expression.operators.conditional.OrExpression; -import net.sf.jsqlparser.expression.operators.conditional.XorExpression; -import net.sf.jsqlparser.expression.operators.relational.Between; -import net.sf.jsqlparser.expression.operators.relational.EqualsTo; -import net.sf.jsqlparser.expression.operators.relational.ExistsExpression; -import net.sf.jsqlparser.expression.operators.relational.ExpressionList; -import net.sf.jsqlparser.expression.operators.relational.FullTextSearch; -import net.sf.jsqlparser.expression.operators.relational.GeometryDistance; -import net.sf.jsqlparser.expression.operators.relational.GreaterThan; -import net.sf.jsqlparser.expression.operators.relational.GreaterThanEquals; -import net.sf.jsqlparser.expression.operators.relational.InExpression; -import net.sf.jsqlparser.expression.operators.relational.IsBooleanExpression; -import net.sf.jsqlparser.expression.operators.relational.IsDistinctExpression; -import net.sf.jsqlparser.expression.operators.relational.IsNullExpression; -import net.sf.jsqlparser.expression.operators.relational.ItemsListVisitor; -import net.sf.jsqlparser.expression.operators.relational.JsonOperator; -import net.sf.jsqlparser.expression.operators.relational.LikeExpression; -import net.sf.jsqlparser.expression.operators.relational.Matches; -import net.sf.jsqlparser.expression.operators.relational.MinorThan; -import net.sf.jsqlparser.expression.operators.relational.MinorThanEquals; -import net.sf.jsqlparser.expression.operators.relational.MultiExpressionList; -import net.sf.jsqlparser.expression.operators.relational.NamedExpressionList; -import net.sf.jsqlparser.expression.operators.relational.NotEqualsTo; -import net.sf.jsqlparser.expression.operators.relational.RegExpMatchOperator; -import net.sf.jsqlparser.expression.operators.relational.RegExpMySQLOperator; -import net.sf.jsqlparser.expression.operators.relational.SimilarToExpression; -import net.sf.jsqlparser.schema.Column; -import net.sf.jsqlparser.statement.select.AllColumns; -import net.sf.jsqlparser.statement.select.AllTableColumns; -import net.sf.jsqlparser.statement.select.OrderByElement; -import net.sf.jsqlparser.statement.select.SubSelect; - -/** - * 判断表达是否为常量的分析器 - * - * @author guyadong - */ -public class ConstAnalyzer implements ExpressionVisitor, ItemsListVisitor { - - private static ThreadLocal constFlag = new ThreadLocal() { - @Override - protected Boolean initialValue() { - return true; - } - }; - - @Override - public void visit(NullValue value) { - } - - @Override - public void visit(Function function) { - constFlag.set(false); - } - - @Override - public void visit(SignedExpression expr) { - expr.getExpression().accept(this); - } - - @Override - public void visit(JdbcParameter parameter) { - constFlag.set(false); - } - - @Override - public void visit(JdbcNamedParameter parameter) { - constFlag.set(false); - } - - @Override - public void visit(DoubleValue value) { - - } - - @Override - public void visit(LongValue value) { - - } - - @Override - public void visit(DateValue value) { - - } - - @Override - public void visit(TimeValue value) { - - } - - @Override - public void visit(TimestampValue value) { - - } - - @Override - public void visit(Parenthesis parenthesis) { - parenthesis.getExpression().accept(this); - } - - @Override - public void visit(StringValue value) { - - } - - @Override - public void visit(Addition expr) { - visitBinaryExpression(expr); - } - - @Override - public void visit(Division expr) { - visitBinaryExpression(expr); - } - - @Override - public void visit(IntegerDivision expr) { - visitBinaryExpression(expr); - } - - @Override - public void visit(Multiplication expr) { - visitBinaryExpression(expr); - } - - @Override - public void visit(Subtraction expr) { - visitBinaryExpression(expr); - } - - @Override - public void visit(AndExpression expr) { - visitBinaryExpression(expr); - } - - @Override - public void visit(OrExpression expr) { - visitBinaryExpression(expr); - } - - @Override - public void visit(XorExpression expr) { - visitBinaryExpression(expr); - } - - @Override - public void visit(Between expr) { - expr.getLeftExpression().accept(this); - expr.getBetweenExpressionStart().accept(this); - expr.getBetweenExpressionEnd().accept(this); - } - - /** - * 用于处理 OverlapsCondition 类型的表达式 - * @param overlapsCondition - */ - @Override - public void visit(OverlapsCondition overlapsCondition) { - constFlag.set(false); - } - /** - * 用于处理 SafeCastExpression 类型的表达式。 - * @param safeCastExpression - */ - @Override - public void visit(SafeCastExpression safeCastExpression) { - constFlag.set(false); - } - - @Override - public void visit(EqualsTo expr) { - visitBinaryExpression(expr); - } - - @Override - public void visit(GreaterThan expr) { - visitBinaryExpression(expr); - } - - @Override - public void visit(GreaterThanEquals expr) { - visitBinaryExpression(expr); - } - - @Override - public void visit(InExpression expr) { - if (expr.getLeftExpression() != null) { - expr.getLeftExpression().accept(this); - } - } - - @Override - public void visit(IsNullExpression expr) { - expr.getLeftExpression().accept(this); - } - - @Override - public void visit(FullTextSearch expr) { - constFlag.set(false); - } - - @Override - public void visit(IsBooleanExpression expr) { - expr.getLeftExpression().accept(this); - } - - @Override - public void visit(LikeExpression expr) { - visitBinaryExpression(expr); - } - - @Override - public void visit(MinorThan expr) { - visitBinaryExpression(expr); - } - - @Override - public void visit(MinorThanEquals expr) { - visitBinaryExpression(expr); - } - - @Override - public void visit(NotEqualsTo expr) { - visitBinaryExpression(expr); - } - - @Override - public void visit(Column column) { - if (!ParserSupport.isBoolean(column)) { - constFlag.set(false); - } - } - - @Override - public void visit(SubSelect subSelect) { - constFlag.set(false); - } - - @Override - public void visit(CaseExpression expr) { - constFlag.set(false); - } - - @Override - public void visit(WhenClause expr) { - constFlag.set(false); - } - - @Override - public void visit(ExistsExpression expr) { - constFlag.set(false); - } - - @Override - public void visit(AnyComparisonExpression expr) { - constFlag.set(false); - } - - @Override - public void visit(Concat expr) { - visitBinaryExpression(expr); - } - - @Override - public void visit(Matches expr) { - visitBinaryExpression(expr); - } - - @Override - public void visit(BitwiseAnd expr) { - visitBinaryExpression(expr); - } - - @Override - public void visit(BitwiseOr expr) { - visitBinaryExpression(expr); - } - - @Override - public void visit(BitwiseXor expr) { - visitBinaryExpression(expr); - } - - @Override - public void visit(CastExpression expr) { - expr.getLeftExpression().accept(this); - } - - @Override - public void visit(TryCastExpression expr) { - constFlag.set(false); - } - - @Override - public void visit(Modulo expr) { - visitBinaryExpression(expr); - } - - @Override - public void visit(AnalyticExpression expr) { - constFlag.set(false); - } - - @Override - public void visit(ExtractExpression expr) { - expr.getExpression().accept(this); - } - - @Override - public void visit(IntervalExpression expr) { - constFlag.set(false); - } - - @Override - public void visit(OracleHierarchicalExpression expr) { - constFlag.set(false); - } - - @Override - public void visit(RegExpMatchOperator expr) { - visitBinaryExpression(expr); - } - - @Override - public void visit(ExpressionList expressionList) { - for (Expression expr : expressionList.getExpressions()) { - expr.accept(this); - } - } - - @Override - public void visit(NamedExpressionList namedExpressionList) { - for (Expression expr : namedExpressionList.getExpressions()) { - expr.accept(this); - } - } - - @Override - public void visit(MultiExpressionList multiExprList) { - for (ExpressionList list : multiExprList.getExpressionLists()) { - visit(list); - } - } - - @Override - public void visit(NotExpression notExpr) { - notExpr.getExpression().accept(this); - } - - @Override - public void visit(BitwiseRightShift expr) { - visitBinaryExpression(expr); - } - - @Override - public void visit(BitwiseLeftShift expr) { - visitBinaryExpression(expr); - } - - protected void visitBinaryExpression(BinaryExpression expr) { - expr.getLeftExpression().accept(this); - expr.getRightExpression().accept(this); - } - - @Override - public void visit(JsonExpression jsonExpr) { - jsonExpr.getExpression().accept(this); - } - - @Override - public void visit(JsonOperator expr) { - visitBinaryExpression(expr); - } - - @Override - public void visit(RegExpMySQLOperator expr) { - visitBinaryExpression(expr); - } - - @Override - public void visit(UserVariable var) { - constFlag.set(false); - } - - @Override - public void visit(NumericBind bind) { - constFlag.set(false); - } - - @Override - public void visit(KeepExpression expr) { - for (OrderByElement element : expr.getOrderByElements()) { - element.getExpression().accept(this); - } - } - - @Override - public void visit(MySQLGroupConcat groupConcat) { - constFlag.set(false); - } - - @Override - public void visit(ValueListExpression valueListExpression) { - for (Expression expr : valueListExpression.getExpressionList().getExpressions()) { - expr.accept(this); - } - } - - @Override - public void visit(AllColumns allColumns) { - - } - - @Override - public void visit(AllTableColumns allTableColumns) { - - } - - @Override - public void visit(AllValue allValue) { - - } - - @Override - public void visit(IsDistinctExpression isDistinctExpression) { - visitBinaryExpression(isDistinctExpression); - } - - @Override - public void visit(RowGetExpression rowGetExpression) { - rowGetExpression.getExpression().accept(this); - } - - @Override - public void visit(HexValue hexValue) { - - } - - @Override - public void visit(OracleHint hint) { - - } - - @Override - public void visit(TimeKeyExpression timeKeyExpression) { - - } - - @Override - public void visit(DateTimeLiteralExpression literal) { - } - - @Override - public void visit(NextValExpression nextVal) { - constFlag.set(false); - } - - @Override - public void visit(CollateExpression col) { - constFlag.set(false); - } - - @Override - public void visit(SimilarToExpression expr) { - visitBinaryExpression(expr); - } - - @Override - public void visit(ArrayExpression array) { - array.getObjExpression().accept(this); - if (array.getIndexExpression() != null) { - array.getIndexExpression().accept(this); - } - if (array.getStartIndexExpression() != null) { - array.getStartIndexExpression().accept(this); - } - if (array.getStopIndexExpression() != null) { - array.getStopIndexExpression().accept(this); - } - } - - @Override - public void visit(ArrayConstructor aThis) { - for (Expression expression : aThis.getExpressions()) { - expression.accept(this); - } - } - - @Override - public void visit(VariableAssignment var) { - constFlag.set(false); - } - - @Override - public void visit(XMLSerializeExpr expr) { - constFlag.set(false); - } - - @Override - public void visit(TimezoneExpression expr) { - expr.getLeftExpression().accept(this); - } - - @Override - public void visit(JsonAggregateFunction expression) { - Expression expr = expression.getExpression(); - if (expr != null) { - expr.accept(this); - } - - expr = expression.getFilterExpression(); - if (expr != null) { - expr.accept(this); - } - } - - @Override - public void visit(JsonFunction expression) { - for (JsonFunctionExpression expr : expression.getExpressions()) { - expr.getExpression().accept(this); - } - } - - @Override - public void visit(ConnectByRootOperator connectByRootOperator) { - constFlag.set(false); - } - - @Override - public void visit(OracleNamedFunctionParameter oracleNamedFunctionParameter) { - constFlag.set(false); - } - - @Override - public void visit(GeometryDistance geometryDistance) { - visitBinaryExpression(geometryDistance); - } - - @Override - public void visit(RowConstructor rowConstructor) { - constFlag.set(false); - } - - public boolean isConstExpression(Expression expression) { - if (null != expression) { - constFlag.set(true); - expression.accept(this); - return constFlag.get(); - } - return false; - } -} - +//package org.jeecg.common.util.sqlInjection.parse; +// +//import net.sf.jsqlparser.expression.*; +//import net.sf.jsqlparser.expression.operators.arithmetic.Addition; +//import net.sf.jsqlparser.expression.operators.arithmetic.BitwiseAnd; +//import net.sf.jsqlparser.expression.operators.arithmetic.BitwiseLeftShift; +//import net.sf.jsqlparser.expression.operators.arithmetic.BitwiseOr; +//import net.sf.jsqlparser.expression.operators.arithmetic.BitwiseRightShift; +//import net.sf.jsqlparser.expression.operators.arithmetic.BitwiseXor; +//import net.sf.jsqlparser.expression.operators.arithmetic.Concat; +//import net.sf.jsqlparser.expression.operators.arithmetic.Division; +//import net.sf.jsqlparser.expression.operators.arithmetic.IntegerDivision; +//import net.sf.jsqlparser.expression.operators.arithmetic.Modulo; +//import net.sf.jsqlparser.expression.operators.arithmetic.Multiplication; +//import net.sf.jsqlparser.expression.operators.arithmetic.Subtraction; +//import net.sf.jsqlparser.expression.operators.conditional.AndExpression; +//import net.sf.jsqlparser.expression.operators.conditional.OrExpression; +//import net.sf.jsqlparser.expression.operators.conditional.XorExpression; +//import net.sf.jsqlparser.expression.operators.relational.Between; +//import net.sf.jsqlparser.expression.operators.relational.EqualsTo; +//import net.sf.jsqlparser.expression.operators.relational.ExistsExpression; +//import net.sf.jsqlparser.expression.operators.relational.ExpressionList; +//import net.sf.jsqlparser.expression.operators.relational.FullTextSearch; +//import net.sf.jsqlparser.expression.operators.relational.GeometryDistance; +//import net.sf.jsqlparser.expression.operators.relational.GreaterThan; +//import net.sf.jsqlparser.expression.operators.relational.GreaterThanEquals; +//import net.sf.jsqlparser.expression.operators.relational.InExpression; +//import net.sf.jsqlparser.expression.operators.relational.IsBooleanExpression; +//import net.sf.jsqlparser.expression.operators.relational.IsDistinctExpression; +//import net.sf.jsqlparser.expression.operators.relational.IsNullExpression; +//import net.sf.jsqlparser.expression.operators.relational.ItemsListVisitor; +//import net.sf.jsqlparser.expression.operators.relational.JsonOperator; +//import net.sf.jsqlparser.expression.operators.relational.LikeExpression; +//import net.sf.jsqlparser.expression.operators.relational.Matches; +//import net.sf.jsqlparser.expression.operators.relational.MinorThan; +//import net.sf.jsqlparser.expression.operators.relational.MinorThanEquals; +//import net.sf.jsqlparser.expression.operators.relational.MultiExpressionList; +//import net.sf.jsqlparser.expression.operators.relational.NamedExpressionList; +//import net.sf.jsqlparser.expression.operators.relational.NotEqualsTo; +//import net.sf.jsqlparser.expression.operators.relational.RegExpMatchOperator; +//import net.sf.jsqlparser.expression.operators.relational.RegExpMySQLOperator; +//import net.sf.jsqlparser.expression.operators.relational.SimilarToExpression; +//import net.sf.jsqlparser.schema.Column; +//import net.sf.jsqlparser.statement.select.AllColumns; +//import net.sf.jsqlparser.statement.select.AllTableColumns; +//import net.sf.jsqlparser.statement.select.OrderByElement; +//import net.sf.jsqlparser.statement.select.SubSelect; +// +///** +// * 判断表达是否为常量的分析器 +// * +// * @author guyadong +// */ +//public class ConstAnalyzer implements ExpressionVisitor, ItemsListVisitor { +// +// private static ThreadLocal constFlag = new ThreadLocal() { +// @Override +// protected Boolean initialValue() { +// return true; +// } +// }; +// +// @Override +// public void visit(NullValue value) { +// } +// +// @Override +// public void visit(Function function) { +// constFlag.set(false); +// } +// +// @Override +// public void visit(SignedExpression expr) { +// expr.getExpression().accept(this); +// } +// +// @Override +// public void visit(JdbcParameter parameter) { +// constFlag.set(false); +// } +// +// @Override +// public void visit(JdbcNamedParameter parameter) { +// constFlag.set(false); +// } +// +// @Override +// public void visit(DoubleValue value) { +// +// } +// +// @Override +// public void visit(LongValue value) { +// +// } +// +// @Override +// public void visit(DateValue value) { +// +// } +// +// @Override +// public void visit(TimeValue value) { +// +// } +// +// @Override +// public void visit(TimestampValue value) { +// +// } +// +// @Override +// public void visit(Parenthesis parenthesis) { +// parenthesis.getExpression().accept(this); +// } +// +// @Override +// public void visit(StringValue value) { +// +// } +// +// @Override +// public void visit(Addition expr) { +// visitBinaryExpression(expr); +// } +// +// @Override +// public void visit(Division expr) { +// visitBinaryExpression(expr); +// } +// +// @Override +// public void visit(IntegerDivision expr) { +// visitBinaryExpression(expr); +// } +// +// @Override +// public void visit(Multiplication expr) { +// visitBinaryExpression(expr); +// } +// +// @Override +// public void visit(Subtraction expr) { +// visitBinaryExpression(expr); +// } +// +// @Override +// public void visit(AndExpression expr) { +// visitBinaryExpression(expr); +// } +// +// @Override +// public void visit(OrExpression expr) { +// visitBinaryExpression(expr); +// } +// +// @Override +// public void visit(XorExpression expr) { +// visitBinaryExpression(expr); +// } +// +// @Override +// public void visit(Between expr) { +// expr.getLeftExpression().accept(this); +// expr.getBetweenExpressionStart().accept(this); +// expr.getBetweenExpressionEnd().accept(this); +// } +// +// /** +// * 用于处理 OverlapsCondition 类型的表达式 +// * @param overlapsCondition +// */ +// @Override +// public void visit(OverlapsCondition overlapsCondition) { +// constFlag.set(false); +// } +// /** +// * 用于处理 SafeCastExpression 类型的表达式。 +// * @param safeCastExpression +// */ +// @Override +// public void visit(SafeCastExpression safeCastExpression) { +// constFlag.set(false); +// } +// +// @Override +// public void visit(EqualsTo expr) { +// visitBinaryExpression(expr); +// } +// +// @Override +// public void visit(GreaterThan expr) { +// visitBinaryExpression(expr); +// } +// +// @Override +// public void visit(GreaterThanEquals expr) { +// visitBinaryExpression(expr); +// } +// +// @Override +// public void visit(InExpression expr) { +// if (expr.getLeftExpression() != null) { +// expr.getLeftExpression().accept(this); +// } +// } +// +// @Override +// public void visit(IsNullExpression expr) { +// expr.getLeftExpression().accept(this); +// } +// +// @Override +// public void visit(FullTextSearch expr) { +// constFlag.set(false); +// } +// +// @Override +// public void visit(IsBooleanExpression expr) { +// expr.getLeftExpression().accept(this); +// } +// +// @Override +// public void visit(LikeExpression expr) { +// visitBinaryExpression(expr); +// } +// +// @Override +// public void visit(MinorThan expr) { +// visitBinaryExpression(expr); +// } +// +// @Override +// public void visit(MinorThanEquals expr) { +// visitBinaryExpression(expr); +// } +// +// @Override +// public void visit(NotEqualsTo expr) { +// visitBinaryExpression(expr); +// } +// +// @Override +// public void visit(Column column) { +// if (!ParserSupport.isBoolean(column)) { +// constFlag.set(false); +// } +// } +// +// @Override +// public void visit(SubSelect subSelect) { +// constFlag.set(false); +// } +// +// @Override +// public void visit(CaseExpression expr) { +// constFlag.set(false); +// } +// +// @Override +// public void visit(WhenClause expr) { +// constFlag.set(false); +// } +// +// @Override +// public void visit(ExistsExpression expr) { +// constFlag.set(false); +// } +// +// @Override +// public void visit(AnyComparisonExpression expr) { +// constFlag.set(false); +// } +// +// @Override +// public void visit(Concat expr) { +// visitBinaryExpression(expr); +// } +// +// @Override +// public void visit(Matches expr) { +// visitBinaryExpression(expr); +// } +// +// @Override +// public void visit(BitwiseAnd expr) { +// visitBinaryExpression(expr); +// } +// +// @Override +// public void visit(BitwiseOr expr) { +// visitBinaryExpression(expr); +// } +// +// @Override +// public void visit(BitwiseXor expr) { +// visitBinaryExpression(expr); +// } +// +// @Override +// public void visit(CastExpression expr) { +// expr.getLeftExpression().accept(this); +// } +// +// @Override +// public void visit(TryCastExpression expr) { +// constFlag.set(false); +// } +// +// @Override +// public void visit(Modulo expr) { +// visitBinaryExpression(expr); +// } +// +// @Override +// public void visit(AnalyticExpression expr) { +// constFlag.set(false); +// } +// +// @Override +// public void visit(ExtractExpression expr) { +// expr.getExpression().accept(this); +// } +// +// @Override +// public void visit(IntervalExpression expr) { +// constFlag.set(false); +// } +// +// @Override +// public void visit(OracleHierarchicalExpression expr) { +// constFlag.set(false); +// } +// +// @Override +// public void visit(RegExpMatchOperator expr) { +// visitBinaryExpression(expr); +// } +// +// @Override +// public void visit(ExpressionList expressionList) { +// for (Expression expr : expressionList.getExpressions()) { +// expr.accept(this); +// } +// } +// +// @Override +// public void visit(NamedExpressionList namedExpressionList) { +// for (Expression expr : namedExpressionList.getExpressions()) { +// expr.accept(this); +// } +// } +// +// @Override +// public void visit(MultiExpressionList multiExprList) { +// for (ExpressionList list : multiExprList.getExpressionLists()) { +// visit(list); +// } +// } +// +// @Override +// public void visit(NotExpression notExpr) { +// notExpr.getExpression().accept(this); +// } +// +// @Override +// public void visit(BitwiseRightShift expr) { +// visitBinaryExpression(expr); +// } +// +// @Override +// public void visit(BitwiseLeftShift expr) { +// visitBinaryExpression(expr); +// } +// +// protected void visitBinaryExpression(BinaryExpression expr) { +// expr.getLeftExpression().accept(this); +// expr.getRightExpression().accept(this); +// } +// +// @Override +// public void visit(JsonExpression jsonExpr) { +// jsonExpr.getExpression().accept(this); +// } +// +// @Override +// public void visit(JsonOperator expr) { +// visitBinaryExpression(expr); +// } +// +// @Override +// public void visit(RegExpMySQLOperator expr) { +// visitBinaryExpression(expr); +// } +// +// @Override +// public void visit(UserVariable var) { +// constFlag.set(false); +// } +// +// @Override +// public void visit(NumericBind bind) { +// constFlag.set(false); +// } +// +// @Override +// public void visit(KeepExpression expr) { +// for (OrderByElement element : expr.getOrderByElements()) { +// element.getExpression().accept(this); +// } +// } +// +// @Override +// public void visit(MySQLGroupConcat groupConcat) { +// constFlag.set(false); +// } +// +// @Override +// public void visit(ValueListExpression valueListExpression) { +// for (Expression expr : valueListExpression.getExpressionList().getExpressions()) { +// expr.accept(this); +// } +// } +// +// @Override +// public void visit(AllColumns allColumns) { +// +// } +// +// @Override +// public void visit(AllTableColumns allTableColumns) { +// +// } +// +// @Override +// public void visit(AllValue allValue) { +// +// } +// +// @Override +// public void visit(IsDistinctExpression isDistinctExpression) { +// visitBinaryExpression(isDistinctExpression); +// } +// +// @Override +// public void visit(RowGetExpression rowGetExpression) { +// rowGetExpression.getExpression().accept(this); +// } +// +// @Override +// public void visit(HexValue hexValue) { +// +// } +// +// @Override +// public void visit(OracleHint hint) { +// +// } +// +// @Override +// public void visit(TimeKeyExpression timeKeyExpression) { +// +// } +// +// @Override +// public void visit(DateTimeLiteralExpression literal) { +// } +// +// @Override +// public void visit(NextValExpression nextVal) { +// constFlag.set(false); +// } +// +// @Override +// public void visit(CollateExpression col) { +// constFlag.set(false); +// } +// +// @Override +// public void visit(SimilarToExpression expr) { +// visitBinaryExpression(expr); +// } +// +// @Override +// public void visit(ArrayExpression array) { +// array.getObjExpression().accept(this); +// if (array.getIndexExpression() != null) { +// array.getIndexExpression().accept(this); +// } +// if (array.getStartIndexExpression() != null) { +// array.getStartIndexExpression().accept(this); +// } +// if (array.getStopIndexExpression() != null) { +// array.getStopIndexExpression().accept(this); +// } +// } +// +// @Override +// public void visit(ArrayConstructor aThis) { +// for (Expression expression : aThis.getExpressions()) { +// expression.accept(this); +// } +// } +// +// @Override +// public void visit(VariableAssignment var) { +// constFlag.set(false); +// } +// +// @Override +// public void visit(XMLSerializeExpr expr) { +// constFlag.set(false); +// } +// +// @Override +// public void visit(TimezoneExpression expr) { +// expr.getLeftExpression().accept(this); +// } +// +// @Override +// public void visit(JsonAggregateFunction expression) { +// Expression expr = expression.getExpression(); +// if (expr != null) { +// expr.accept(this); +// } +// +// expr = expression.getFilterExpression(); +// if (expr != null) { +// expr.accept(this); +// } +// } +// +// @Override +// public void visit(JsonFunction expression) { +// for (JsonFunctionExpression expr : expression.getExpressions()) { +// expr.getExpression().accept(this); +// } +// } +// +// @Override +// public void visit(ConnectByRootOperator connectByRootOperator) { +// constFlag.set(false); +// } +// +// @Override +// public void visit(OracleNamedFunctionParameter oracleNamedFunctionParameter) { +// constFlag.set(false); +// } +// +// @Override +// public void visit(GeometryDistance geometryDistance) { +// visitBinaryExpression(geometryDistance); +// } +// +// @Override +// public void visit(RowConstructor rowConstructor) { +// constFlag.set(false); +// } +// +// public boolean isConstExpression(Expression expression) { +// if (null != expression) { +// constFlag.set(true); +// expression.accept(this); +// return constFlag.get(); +// } +// return false; +// } +//} +// diff --git a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/sqlInjection/parse/ParserSupport.java b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/sqlInjection/parse/ParserSupport.java index 880872679..41613c98a 100644 --- a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/sqlInjection/parse/ParserSupport.java +++ b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/sqlInjection/parse/ParserSupport.java @@ -1,177 +1,177 @@ -package org.jeecg.common.util.sqlInjection.parse; - -import lombok.extern.slf4j.Slf4j; -import net.sf.jsqlparser.JSQLParserException; -import net.sf.jsqlparser.parser.*; -import net.sf.jsqlparser.schema.Column; -import net.sf.jsqlparser.statement.Statement; -import net.sf.jsqlparser.statement.select.PlainSelect; -import net.sf.jsqlparser.statement.select.Select; -import net.sf.jsqlparser.statement.select.SelectBody; - -import static com.google.common.base.Preconditions.checkArgument; -import static com.google.common.base.Preconditions.checkNotNull; - -import java.lang.reflect.InvocationTargetException; -import java.util.regex.Matcher; -import java.util.regex.Pattern; - -import com.google.common.base.Throwables; -import org.jeecg.common.exception.JeecgBootException; -import org.jeecg.common.exception.JeecgSqlInjectionException; - -/** - * 解析sql支持 - */ -@Slf4j -public class ParserSupport { - /** - * 解析SELECT SQL语句,解析失败或非SELECT语句则抛出异常 - * - * @param sql - * @return - */ - public static Select parseSelect(String sql) { - Statement stmt; - try { - stmt = CCJSqlParserUtil.parse(checkNotNull(sql, "sql is null")); - } catch (JSQLParserException e) { - throw new JeecgBootException(e); - } - checkArgument(stmt instanceof Select, "%s is not SELECT statment", sql); - Select select = (Select) stmt; - SelectBody selectBody = select.getSelectBody(); - // 暂时只支持简单的SELECT xxxx FROM ....语句不支持复杂语句如WITH - checkArgument(selectBody instanceof PlainSelect, "ONLY SUPPORT plain select statement %s", sql); - return (Select) stmt; - } - - /** - * 解析SELECT SQL语句,解析失败或非SELECT语句则 - * - * @param sql - * @return - */ - public static Select parseSelectUnchecked(String sql) { - try { - return parseSelect(sql); - } catch (Exception e) { - return null; - } - } - - /** - * 实现SQL语句解析,解析成功则返回解析后的{@link Statement}, - * 并通过{@code visitor}参数提供基于AST(抽象语法树)的遍历所有节点的能力。 - * - * @param sql SQL语句 - * @param visitor 遍历所有节点的{@link SimpleNodeVisitor}接口实例,为{@code null}忽略 - * @param sqlSyntaxNormalizer SQL语句分析转换器,为{@code null}忽略 - * @throws JSQLParserException 输入的SQL语句有语法错误 - * @see #parse0(String, CCJSqlParserVisitor, SqlSyntaxNormalizer) - */ - public static Statement parse(String sql, CCJSqlParserVisitor visitor, SqlSyntaxNormalizer sqlSyntaxNormalizer) throws JSQLParserException { - return parse0(sql, visitor, sqlSyntaxNormalizer).statement; - } - - /** - * 参照{@link CCJSqlParserUtil#parseAST(String)}和{@link CCJSqlParserUtil#parse(String)}实现SQL语句解析, - * 解析成功则返回解析后的{@link SqlParserInfo}对象, - * 并通过{@code visitor}参数提供基于AST(抽象语法树)的遍历所有节点的能力。 - * - * @param sql SQL语句 - * @param visitor 遍历所有节点的{@link SimpleNodeVisitor}接口实例,为{@code null}忽略 - * @param sqlSyntaxAnalyzer SQL语句分析转换器,为{@code null}忽略 - * @throws JSQLParserException 输入的SQL语句有语法错误 - * @see net.sf.jsqlparser.parser.Node#jjtAccept(SimpleNodeVisitor, Object) - */ - public static SqlParserInfo parse0(String sql, CCJSqlParserVisitor visitor, SqlSyntaxNormalizer sqlSyntaxAnalyzer) throws JeecgSqlInjectionException { - - //检查是否非select开头,暂不支持 - if(!sql.toLowerCase().trim().startsWith("select ")) { - log.warn("传入sql 非select开头,不支持非select开头的语句解析!"); - return null; - } - - //检查是否存储过程,暂不支持 - if(sql.toLowerCase().trim().startsWith("call ")){ - log.warn("传入call 开头存储过程,不支持存储过程解析!"); - return null; - } - - //检查特殊语义的特殊字符,目前检查冒号、$、#三种特殊语义字符 - String specialCharacters = "[:$#]"; - Pattern pattern = Pattern.compile(specialCharacters); - Matcher matcher = pattern.matcher(sql); - if (matcher.find()) { - sql = sql.replaceAll("[:$#]", "@"); - } - - checkArgument(null != sql, "sql is null"); - boolean allowComplexParsing = CCJSqlParserUtil.getNestingDepth(sql) <= CCJSqlParserUtil.ALLOWED_NESTING_DEPTH; - - CCJSqlParser parser = CCJSqlParserUtil.newParser(sql).withAllowComplexParsing(allowComplexParsing); - Statement stmt; - try { - stmt = parser.Statement(); - } catch (Exception ex) { - log.error("请注意,SQL语法可能存在问题---> {}", ex.getMessage()); - throw new JeecgSqlInjectionException("请注意,SQL语法可能存在问题:"+sql); - } - if (null != visitor) { - parser.getASTRoot().jjtAccept(visitor, null); - } - if (null != sqlSyntaxAnalyzer) { - stmt.accept(sqlSyntaxAnalyzer.resetChanged()); - } - return new SqlParserInfo(stmt.toString(), stmt, (SimpleNode) parser.getASTRoot()); - } - - /** - * 调用{@link CCJSqlParser}解析SQL语句部件返回解析生成的对象,如{@code 'ORDER BY id DESC'} - * - * @param - * @param input - * @param method 指定调用的{@link CCJSqlParser}解析方法 - * @param targetType 返回的解析对象类型 - * @return - * @since 3.18.3 - */ - public static T parseComponent(String input, String method, Class targetType) { - try { - CCJSqlParser parser = new CCJSqlParser(new StringProvider(input)); - try { - return checkNotNull(targetType, "targetType is null").cast(parser.getClass().getMethod(method).invoke(parser)); - } catch (InvocationTargetException e) { - Throwables.throwIfUnchecked(e.getTargetException()); - throw new RuntimeException(e.getTargetException()); - } - } catch (IllegalAccessException | NoSuchMethodException | SecurityException e) { - Throwables.throwIfUnchecked(e); - throw new RuntimeException(e); - } - } - - /** - * 如果{@link Column}没有定义table,且字段名为true/false(不区分大小写)则视为布尔常量 - * - * @param column - */ - public static boolean isBoolean(Column column) { - return null != column && null == column.getTable() && - Pattern.compile("(true|false)", Pattern.CASE_INSENSITIVE).matcher(column.getColumnName()).matches(); - } - - public static class SqlParserInfo { - public String nativeSql; - public Statement statement; - public SimpleNode simpleNode; - - SqlParserInfo(String nativeSql, Statement statement, SimpleNode simpleNode) { - this.nativeSql = nativeSql; - this.statement = statement; - this.simpleNode = simpleNode; - } - } -} - +//package org.jeecg.common.util.sqlInjection.parse; +// +//import lombok.extern.slf4j.Slf4j; +//import net.sf.jsqlparser.JSQLParserException; +//import net.sf.jsqlparser.parser.*; +//import net.sf.jsqlparser.schema.Column; +//import net.sf.jsqlparser.statement.Statement; +//import net.sf.jsqlparser.statement.select.PlainSelect; +//import net.sf.jsqlparser.statement.select.Select; +//import net.sf.jsqlparser.statement.select.SelectBody; +// +//import static com.google.common.base.Preconditions.checkArgument; +//import static com.google.common.base.Preconditions.checkNotNull; +// +//import java.lang.reflect.InvocationTargetException; +//import java.util.regex.Matcher; +//import java.util.regex.Pattern; +// +//import com.google.common.base.Throwables; +//import org.jeecg.common.exception.JeecgBootException; +//import org.jeecg.common.exception.JeecgSqlInjectionException; +// +///** +// * 解析sql支持 +// */ +//@Slf4j +//public class ParserSupport { +// /** +// * 解析SELECT SQL语句,解析失败或非SELECT语句则抛出异常 +// * +// * @param sql +// * @return +// */ +// public static Select parseSelect(String sql) { +// Statement stmt; +// try { +// stmt = CCJSqlParserUtil.parse(checkNotNull(sql, "sql is null")); +// } catch (JSQLParserException e) { +// throw new JeecgBootException(e); +// } +// checkArgument(stmt instanceof Select, "%s is not SELECT statment", sql); +// Select select = (Select) stmt; +// SelectBody selectBody = select.getSelectBody(); +// // 暂时只支持简单的SELECT xxxx FROM ....语句不支持复杂语句如WITH +// checkArgument(selectBody instanceof PlainSelect, "ONLY SUPPORT plain select statement %s", sql); +// return (Select) stmt; +// } +// +// /** +// * 解析SELECT SQL语句,解析失败或非SELECT语句则 +// * +// * @param sql +// * @return +// */ +// public static Select parseSelectUnchecked(String sql) { +// try { +// return parseSelect(sql); +// } catch (Exception e) { +// return null; +// } +// } +// +// /** +// * 实现SQL语句解析,解析成功则返回解析后的{@link Statement}, +// * 并通过{@code visitor}参数提供基于AST(抽象语法树)的遍历所有节点的能力。 +// * +// * @param sql SQL语句 +// * @param visitor 遍历所有节点的{@link SimpleNodeVisitor}接口实例,为{@code null}忽略 +// * @param sqlSyntaxNormalizer SQL语句分析转换器,为{@code null}忽略 +// * @throws JSQLParserException 输入的SQL语句有语法错误 +// * @see #parse0(String, CCJSqlParserVisitor, SqlSyntaxNormalizer) +// */ +// public static Statement parse(String sql, CCJSqlParserVisitor visitor, SqlSyntaxNormalizer sqlSyntaxNormalizer) throws JSQLParserException { +// return parse0(sql, visitor, sqlSyntaxNormalizer).statement; +// } +// +// /** +// * 参照{@link CCJSqlParserUtil#parseAST(String)}和{@link CCJSqlParserUtil#parse(String)}实现SQL语句解析, +// * 解析成功则返回解析后的{@link SqlParserInfo}对象, +// * 并通过{@code visitor}参数提供基于AST(抽象语法树)的遍历所有节点的能力。 +// * +// * @param sql SQL语句 +// * @param visitor 遍历所有节点的{@link SimpleNodeVisitor}接口实例,为{@code null}忽略 +// * @param sqlSyntaxAnalyzer SQL语句分析转换器,为{@code null}忽略 +// * @throws JSQLParserException 输入的SQL语句有语法错误 +// * @see net.sf.jsqlparser.parser.Node#jjtAccept(SimpleNodeVisitor, Object) +// */ +// public static SqlParserInfo parse0(String sql, CCJSqlParserVisitor visitor, SqlSyntaxNormalizer sqlSyntaxAnalyzer) throws JeecgSqlInjectionException { +// +// //检查是否非select开头,暂不支持 +// if(!sql.toLowerCase().trim().startsWith("select ")) { +// log.warn("传入sql 非select开头,不支持非select开头的语句解析!"); +// return null; +// } +// +// //检查是否存储过程,暂不支持 +// if(sql.toLowerCase().trim().startsWith("call ")){ +// log.warn("传入call 开头存储过程,不支持存储过程解析!"); +// return null; +// } +// +// //检查特殊语义的特殊字符,目前检查冒号、$、#三种特殊语义字符 +// String specialCharacters = "[:$#]"; +// Pattern pattern = Pattern.compile(specialCharacters); +// Matcher matcher = pattern.matcher(sql); +// if (matcher.find()) { +// sql = sql.replaceAll("[:$#]", "@"); +// } +// +// checkArgument(null != sql, "sql is null"); +// boolean allowComplexParsing = CCJSqlParserUtil.getNestingDepth(sql) <= CCJSqlParserUtil.ALLOWED_NESTING_DEPTH; +// +// CCJSqlParser parser = CCJSqlParserUtil.newParser(sql).withAllowComplexParsing(allowComplexParsing); +// Statement stmt; +// try { +// stmt = parser.Statement(); +// } catch (Exception ex) { +// log.error("请注意,SQL语法可能存在问题---> {}", ex.getMessage()); +// throw new JeecgSqlInjectionException("请注意,SQL语法可能存在问题:"+sql); +// } +// if (null != visitor) { +// parser.getASTRoot().jjtAccept(visitor, null); +// } +// if (null != sqlSyntaxAnalyzer) { +// stmt.accept(sqlSyntaxAnalyzer.resetChanged()); +// } +// return new SqlParserInfo(stmt.toString(), stmt, (SimpleNode) parser.getASTRoot()); +// } +// +// /** +// * 调用{@link CCJSqlParser}解析SQL语句部件返回解析生成的对象,如{@code 'ORDER BY id DESC'} +// * +// * @param +// * @param input +// * @param method 指定调用的{@link CCJSqlParser}解析方法 +// * @param targetType 返回的解析对象类型 +// * @return +// * @since 3.18.3 +// */ +// public static T parseComponent(String input, String method, Class targetType) { +// try { +// CCJSqlParser parser = new CCJSqlParser(new StringProvider(input)); +// try { +// return checkNotNull(targetType, "targetType is null").cast(parser.getClass().getMethod(method).invoke(parser)); +// } catch (InvocationTargetException e) { +// Throwables.throwIfUnchecked(e.getTargetException()); +// throw new RuntimeException(e.getTargetException()); +// } +// } catch (IllegalAccessException | NoSuchMethodException | SecurityException e) { +// Throwables.throwIfUnchecked(e); +// throw new RuntimeException(e); +// } +// } +// +// /** +// * 如果{@link Column}没有定义table,且字段名为true/false(不区分大小写)则视为布尔常量 +// * +// * @param column +// */ +// public static boolean isBoolean(Column column) { +// return null != column && null == column.getTable() && +// Pattern.compile("(true|false)", Pattern.CASE_INSENSITIVE).matcher(column.getColumnName()).matches(); +// } +// +// public static class SqlParserInfo { +// public String nativeSql; +// public Statement statement; +// public SimpleNode simpleNode; +// +// SqlParserInfo(String nativeSql, Statement statement, SimpleNode simpleNode) { +// this.nativeSql = nativeSql; +// this.statement = statement; +// this.simpleNode = simpleNode; +// } +// } +//} +// diff --git a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/sqlInjection/parse/SqlSyntaxNormalizer.java b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/sqlInjection/parse/SqlSyntaxNormalizer.java index 844478197..291a39a5e 100644 --- a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/sqlInjection/parse/SqlSyntaxNormalizer.java +++ b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/sqlInjection/parse/SqlSyntaxNormalizer.java @@ -1,37 +1,37 @@ -package org.jeecg.common.util.sqlInjection.parse; - -import net.sf.jsqlparser.util.TablesNamesFinder; - -/** - * SQL语句分析转换器基类
- * 基于SQL语法对象实现对SQL的修改 - * (暂时用不到) - * - * @author guyadong - * @since 3.17.0 - */ -public class SqlSyntaxNormalizer extends TablesNamesFinder { - protected static final ThreadLocal changed = new ThreadLocal<>(); - - public SqlSyntaxNormalizer() { - super(); - init(true); - - } - - /** - * 语句改变返回{@code true},否则返回{@code false} - */ - public boolean changed() { - return Boolean.TRUE.equals(changed.get()); - } - - /** - * 复位线程局部变量{@link #changed}状态 - */ - public SqlSyntaxNormalizer resetChanged() { - changed.remove(); - return this; - } -} - +//package org.jeecg.common.util.sqlInjection.parse; +// +//import net.sf.jsqlparser.util.TablesNamesFinder; +// +///** +// * SQL语句分析转换器基类
+// * 基于SQL语法对象实现对SQL的修改 +// * (暂时用不到) +// * +// * @author guyadong +// * @since 3.17.0 +// */ +//public class SqlSyntaxNormalizer extends TablesNamesFinder { +// protected static final ThreadLocal changed = new ThreadLocal<>(); +// +// public SqlSyntaxNormalizer() { +// super(); +// init(true); +// +// } +// +// /** +// * 语句改变返回{@code true},否则返回{@code false} +// */ +// public boolean changed() { +// return Boolean.TRUE.equals(changed.get()); +// } +// +// /** +// * 复位线程局部变量{@link #changed}状态 +// */ +// public SqlSyntaxNormalizer resetChanged() { +// changed.remove(); +// return this; +// } +//} +// diff --git a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/sqlparse/JSqlParserAllTableManager.java b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/sqlparse/JSqlParserAllTableManager.java index 1482a0412..ce6eefd26 100644 --- a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/sqlparse/JSqlParserAllTableManager.java +++ b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/sqlparse/JSqlParserAllTableManager.java @@ -1,255 +1,255 @@ -package org.jeecg.common.util.sqlparse; - -import lombok.extern.slf4j.Slf4j; -import net.sf.jsqlparser.JSQLParserException; -import net.sf.jsqlparser.expression.*; -import net.sf.jsqlparser.parser.CCJSqlParserManager; -import net.sf.jsqlparser.schema.Column; -import net.sf.jsqlparser.schema.Table; -import net.sf.jsqlparser.statement.Statement; -import net.sf.jsqlparser.statement.select.*; -import org.jeecg.common.exception.JeecgBootException; -import org.jeecg.common.util.sqlparse.vo.SelectSqlInfo; - -import java.io.StringReader; -import java.util.ArrayList; -import java.util.HashMap; -import java.util.List; -import java.util.Map; - -/** - * 解析所有表名和字段的类 - */ -@Slf4j -public class JSqlParserAllTableManager { - - private final String sql; - private final Map allTableMap = new HashMap<>(); - /** - * 别名对应实际表名 - */ - private final Map tableAliasMap = new HashMap<>(); - - /** - * 解析后的sql - */ - private String parsedSql = null; - - JSqlParserAllTableManager(String selectSql) { - this.sql = selectSql; - } - - /** - * 开始解析 - * - * @return - * @throws JSQLParserException - */ - public Map parse() throws JSQLParserException { - // 1. 创建解析器 - CCJSqlParserManager mgr = new CCJSqlParserManager(); - // 2. 使用解析器解析sql生成具有层次结构的java类 - Statement stmt = mgr.parse(new StringReader(this.sql)); - if (stmt instanceof Select) { - Select selectStatement = (Select) stmt; - SelectBody selectBody = selectStatement.getSelectBody(); - this.parsedSql = selectBody.toString(); - // 3. 解析select查询sql的信息 - if (selectBody instanceof PlainSelect) { - PlainSelect plainSelect = (PlainSelect) selectBody; - // 4. 合并 fromItems - List fromItems = new ArrayList<>(); - fromItems.add(plainSelect.getFromItem()); - // 4.1 处理join的表 - List joins = plainSelect.getJoins(); - if (joins != null) { - joins.forEach(join -> fromItems.add(join.getRightItem())); - } - // 5. 处理 fromItems - for (FromItem fromItem : fromItems) { - // 5.1 通过表名的方式from - if (fromItem instanceof Table) { - this.addSqlInfoByTable((Table) fromItem); - } - // 5.2 通过子查询的方式from - else if (fromItem instanceof SubSelect) { - this.handleSubSelect((SubSelect) fromItem); - } - } - // 6. 解析 selectFields - List selectItems = plainSelect.getSelectItems(); - for (SelectItem selectItem : selectItems) { - // 6.1 查询的是全部字段 - if (selectItem instanceof AllColumns) { - // 当 selectItem 为 AllColumns 时,fromItem 必定为 Table - String tableName = plainSelect.getFromItem(Table.class).getName(); - // 此处必定不为空,因为在解析 fromItem 时,已经将表名添加到 allTableMap 中 - SelectSqlInfo sqlInfo = this.allTableMap.get(tableName); - assert sqlInfo != null; - // 设置为查询全部字段 - sqlInfo.setSelectAll(true); - sqlInfo.setSelectFields(null); - sqlInfo.setRealSelectFields(null); - } - // 6.2 查询的是带表别名( u.* )的全部字段 - else if (selectItem instanceof AllTableColumns) { - AllTableColumns allTableColumns = (AllTableColumns) selectItem; - String aliasName = allTableColumns.getTable().getName(); - // 通过别名获取表名 - String tableName = this.tableAliasMap.get(aliasName); - if (tableName == null) { - tableName = aliasName; - } - SelectSqlInfo sqlInfo = this.allTableMap.get(tableName); - // 如果此处为空,则说明该字段是通过子查询获取的,所以可以不处理,只有实际表才需要处理 - if (sqlInfo != null) { - // 设置为查询全部字段 - sqlInfo.setSelectAll(true); - sqlInfo.setSelectFields(null); - sqlInfo.setRealSelectFields(null); - } - } - // 6.3 各种字段表达式处理 - else if (selectItem instanceof SelectExpressionItem) { - SelectExpressionItem selectExpressionItem = (SelectExpressionItem) selectItem; - Expression expression = selectExpressionItem.getExpression(); - Alias alias = selectExpressionItem.getAlias(); - this.handleExpression(expression, alias, plainSelect.getFromItem()); - } - } - } else { - log.warn("暂时尚未处理该类型的 SelectBody: {}", selectBody.getClass().getName()); - throw new JeecgBootException("暂时尚未处理该类型的 SelectBody"); - } - } else { - // 非 select 查询sql,不做处理 - throw new JeecgBootException("非 select 查询sql,不做处理"); - } - return this.allTableMap; - } - - /** - * 处理子查询 - * - * @param subSelect - */ - private void handleSubSelect(SubSelect subSelect) { - try { - String subSelectSql = subSelect.getSelectBody().toString(); - // 递归调用解析 - Map map = JSqlParserUtils.parseAllSelectTable(subSelectSql); - if (map != null) { - this.assignMap(map); - } - } catch (Exception e) { - log.error("解析子查询出错", e); - } - } - - /** - * 处理查询字段表达式 - * - * @param expression - */ - private void handleExpression(Expression expression, Alias alias, FromItem fromItem) { - // 处理函数式字段 CONCAT(name,'(',age,')') - if (expression instanceof Function) { - Function functionExp = (Function) expression; - List expressions = functionExp.getParameters().getExpressions(); - for (Expression expItem : expressions) { - this.handleExpression(expItem, null, fromItem); - } - return; - } - // 处理字段上的子查询 - if (expression instanceof SubSelect) { - this.handleSubSelect((SubSelect) expression); - return; - } - // 不处理字面量 - if (expression instanceof StringValue || - expression instanceof NullValue || - expression instanceof LongValue || - expression instanceof DoubleValue || - expression instanceof HexValue || - expression instanceof DateValue || - expression instanceof TimestampValue || - expression instanceof TimeValue - ) { - return; - } - - // 处理字段 - if (expression instanceof Column) { - Column column = (Column) expression; - // 查询字段名 - String fieldName = column.getColumnName(); - String aliasName = fieldName; - if (alias != null) { - aliasName = alias.getName(); - } - String tableName; - if (column.getTable() != null) { - // 通过列的表名获取 sqlInfo - // 例如 user.name,这里的 tableName 就是 user - tableName = column.getTable().getName(); - // 有可能是别名,需要转换为真实表名 - if (this.tableAliasMap.get(tableName) != null) { - tableName = this.tableAliasMap.get(tableName); - } - } else { - // 当column的table为空时,说明是 fromItem 中的字段 - tableName = ((Table) fromItem).getName(); - } - SelectSqlInfo $sqlInfo = this.allTableMap.get(tableName); - if ($sqlInfo != null) { - $sqlInfo.addSelectField(aliasName, fieldName); - } else { - log.warn("发生意外情况,未找到表名为 {} 的 SelectSqlInfo", tableName); - } - } - } - - /** - * 根据表名添加sqlInfo - * - * @param table - */ - private void addSqlInfoByTable(Table table) { - String tableName = table.getName(); - // 解析 aliasName - if (table.getAlias() != null) { - this.tableAliasMap.put(table.getAlias().getName(), tableName); - } - SelectSqlInfo sqlInfo = new SelectSqlInfo(this.parsedSql); - sqlInfo.setFromTableName(table.getName()); - this.allTableMap.put(sqlInfo.getFromTableName(), sqlInfo); - } - - /** - * 合并map - * - * @param source - */ - private void assignMap(Map source) { - for (Map.Entry entry : source.entrySet()) { - SelectSqlInfo sqlInfo = this.allTableMap.get(entry.getKey()); - if (sqlInfo == null) { - this.allTableMap.put(entry.getKey(), entry.getValue()); - } else { - // 合并 - if (sqlInfo.getSelectFields() == null) { - sqlInfo.setSelectFields(entry.getValue().getSelectFields()); - } else { - sqlInfo.getSelectFields().addAll(entry.getValue().getSelectFields()); - } - if (sqlInfo.getRealSelectFields() == null) { - sqlInfo.setRealSelectFields(entry.getValue().getRealSelectFields()); - } else { - sqlInfo.getRealSelectFields().addAll(entry.getValue().getRealSelectFields()); - } - } - } - } - -} +//package org.jeecg.common.util.sqlparse; +// +//import lombok.extern.slf4j.Slf4j; +//import net.sf.jsqlparser.JSQLParserException; +//import net.sf.jsqlparser.expression.*; +//import net.sf.jsqlparser.parser.CCJSqlParserManager; +//import net.sf.jsqlparser.schema.Column; +//import net.sf.jsqlparser.schema.Table; +//import net.sf.jsqlparser.statement.Statement; +//import net.sf.jsqlparser.statement.select.*; +//import org.jeecg.common.exception.JeecgBootException; +//import org.jeecg.common.util.sqlparse.vo.SelectSqlInfo; +// +//import java.io.StringReader; +//import java.util.ArrayList; +//import java.util.HashMap; +//import java.util.List; +//import java.util.Map; +// +///** +// * 解析所有表名和字段的类 +// */ +//@Slf4j +//public class JSqlParserAllTableManager { +// +// private final String sql; +// private final Map allTableMap = new HashMap<>(); +// /** +// * 别名对应实际表名 +// */ +// private final Map tableAliasMap = new HashMap<>(); +// +// /** +// * 解析后的sql +// */ +// private String parsedSql = null; +// +// JSqlParserAllTableManager(String selectSql) { +// this.sql = selectSql; +// } +// +// /** +// * 开始解析 +// * +// * @return +// * @throws JSQLParserException +// */ +// public Map parse() throws JSQLParserException { +// // 1. 创建解析器 +// CCJSqlParserManager mgr = new CCJSqlParserManager(); +// // 2. 使用解析器解析sql生成具有层次结构的java类 +// Statement stmt = mgr.parse(new StringReader(this.sql)); +// if (stmt instanceof Select) { +// Select selectStatement = (Select) stmt; +// SelectBody selectBody = selectStatement.getSelectBody(); +// this.parsedSql = selectBody.toString(); +// // 3. 解析select查询sql的信息 +// if (selectBody instanceof PlainSelect) { +// PlainSelect plainSelect = (PlainSelect) selectBody; +// // 4. 合并 fromItems +// List fromItems = new ArrayList<>(); +// fromItems.add(plainSelect.getFromItem()); +// // 4.1 处理join的表 +// List joins = plainSelect.getJoins(); +// if (joins != null) { +// joins.forEach(join -> fromItems.add(join.getRightItem())); +// } +// // 5. 处理 fromItems +// for (FromItem fromItem : fromItems) { +// // 5.1 通过表名的方式from +// if (fromItem instanceof Table) { +// this.addSqlInfoByTable((Table) fromItem); +// } +// // 5.2 通过子查询的方式from +// else if (fromItem instanceof SubSelect) { +// this.handleSubSelect((SubSelect) fromItem); +// } +// } +// // 6. 解析 selectFields +// List selectItems = plainSelect.getSelectItems(); +// for (SelectItem selectItem : selectItems) { +// // 6.1 查询的是全部字段 +// if (selectItem instanceof AllColumns) { +// // 当 selectItem 为 AllColumns 时,fromItem 必定为 Table +// String tableName = plainSelect.getFromItem(Table.class).getName(); +// // 此处必定不为空,因为在解析 fromItem 时,已经将表名添加到 allTableMap 中 +// SelectSqlInfo sqlInfo = this.allTableMap.get(tableName); +// assert sqlInfo != null; +// // 设置为查询全部字段 +// sqlInfo.setSelectAll(true); +// sqlInfo.setSelectFields(null); +// sqlInfo.setRealSelectFields(null); +// } +// // 6.2 查询的是带表别名( u.* )的全部字段 +// else if (selectItem instanceof AllTableColumns) { +// AllTableColumns allTableColumns = (AllTableColumns) selectItem; +// String aliasName = allTableColumns.getTable().getName(); +// // 通过别名获取表名 +// String tableName = this.tableAliasMap.get(aliasName); +// if (tableName == null) { +// tableName = aliasName; +// } +// SelectSqlInfo sqlInfo = this.allTableMap.get(tableName); +// // 如果此处为空,则说明该字段是通过子查询获取的,所以可以不处理,只有实际表才需要处理 +// if (sqlInfo != null) { +// // 设置为查询全部字段 +// sqlInfo.setSelectAll(true); +// sqlInfo.setSelectFields(null); +// sqlInfo.setRealSelectFields(null); +// } +// } +// // 6.3 各种字段表达式处理 +// else if (selectItem instanceof SelectExpressionItem) { +// SelectExpressionItem selectExpressionItem = (SelectExpressionItem) selectItem; +// Expression expression = selectExpressionItem.getExpression(); +// Alias alias = selectExpressionItem.getAlias(); +// this.handleExpression(expression, alias, plainSelect.getFromItem()); +// } +// } +// } else { +// log.warn("暂时尚未处理该类型的 SelectBody: {}", selectBody.getClass().getName()); +// throw new JeecgBootException("暂时尚未处理该类型的 SelectBody"); +// } +// } else { +// // 非 select 查询sql,不做处理 +// throw new JeecgBootException("非 select 查询sql,不做处理"); +// } +// return this.allTableMap; +// } +// +// /** +// * 处理子查询 +// * +// * @param subSelect +// */ +// private void handleSubSelect(SubSelect subSelect) { +// try { +// String subSelectSql = subSelect.getSelectBody().toString(); +// // 递归调用解析 +// Map map = JSqlParserUtils.parseAllSelectTable(subSelectSql); +// if (map != null) { +// this.assignMap(map); +// } +// } catch (Exception e) { +// log.error("解析子查询出错", e); +// } +// } +// +// /** +// * 处理查询字段表达式 +// * +// * @param expression +// */ +// private void handleExpression(Expression expression, Alias alias, FromItem fromItem) { +// // 处理函数式字段 CONCAT(name,'(',age,')') +// if (expression instanceof Function) { +// Function functionExp = (Function) expression; +// List expressions = functionExp.getParameters().getExpressions(); +// for (Expression expItem : expressions) { +// this.handleExpression(expItem, null, fromItem); +// } +// return; +// } +// // 处理字段上的子查询 +// if (expression instanceof SubSelect) { +// this.handleSubSelect((SubSelect) expression); +// return; +// } +// // 不处理字面量 +// if (expression instanceof StringValue || +// expression instanceof NullValue || +// expression instanceof LongValue || +// expression instanceof DoubleValue || +// expression instanceof HexValue || +// expression instanceof DateValue || +// expression instanceof TimestampValue || +// expression instanceof TimeValue +// ) { +// return; +// } +// +// // 处理字段 +// if (expression instanceof Column) { +// Column column = (Column) expression; +// // 查询字段名 +// String fieldName = column.getColumnName(); +// String aliasName = fieldName; +// if (alias != null) { +// aliasName = alias.getName(); +// } +// String tableName; +// if (column.getTable() != null) { +// // 通过列的表名获取 sqlInfo +// // 例如 user.name,这里的 tableName 就是 user +// tableName = column.getTable().getName(); +// // 有可能是别名,需要转换为真实表名 +// if (this.tableAliasMap.get(tableName) != null) { +// tableName = this.tableAliasMap.get(tableName); +// } +// } else { +// // 当column的table为空时,说明是 fromItem 中的字段 +// tableName = ((Table) fromItem).getName(); +// } +// SelectSqlInfo $sqlInfo = this.allTableMap.get(tableName); +// if ($sqlInfo != null) { +// $sqlInfo.addSelectField(aliasName, fieldName); +// } else { +// log.warn("发生意外情况,未找到表名为 {} 的 SelectSqlInfo", tableName); +// } +// } +// } +// +// /** +// * 根据表名添加sqlInfo +// * +// * @param table +// */ +// private void addSqlInfoByTable(Table table) { +// String tableName = table.getName(); +// // 解析 aliasName +// if (table.getAlias() != null) { +// this.tableAliasMap.put(table.getAlias().getName(), tableName); +// } +// SelectSqlInfo sqlInfo = new SelectSqlInfo(this.parsedSql); +// sqlInfo.setFromTableName(table.getName()); +// this.allTableMap.put(sqlInfo.getFromTableName(), sqlInfo); +// } +// +// /** +// * 合并map +// * +// * @param source +// */ +// private void assignMap(Map source) { +// for (Map.Entry entry : source.entrySet()) { +// SelectSqlInfo sqlInfo = this.allTableMap.get(entry.getKey()); +// if (sqlInfo == null) { +// this.allTableMap.put(entry.getKey(), entry.getValue()); +// } else { +// // 合并 +// if (sqlInfo.getSelectFields() == null) { +// sqlInfo.setSelectFields(entry.getValue().getSelectFields()); +// } else { +// sqlInfo.getSelectFields().addAll(entry.getValue().getSelectFields()); +// } +// if (sqlInfo.getRealSelectFields() == null) { +// sqlInfo.setRealSelectFields(entry.getValue().getRealSelectFields()); +// } else { +// sqlInfo.getRealSelectFields().addAll(entry.getValue().getRealSelectFields()); +// } +// } +// } +// } +// +//} diff --git a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/sqlparse/JSqlParserUtils.java b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/sqlparse/JSqlParserUtils.java index 01373e4ff..e8788b718 100644 --- a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/sqlparse/JSqlParserUtils.java +++ b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/sqlparse/JSqlParserUtils.java @@ -1,190 +1,190 @@ -package org.jeecg.common.util.sqlparse; - -import lombok.extern.slf4j.Slf4j; -import net.sf.jsqlparser.JSQLParserException; -import net.sf.jsqlparser.expression.*; -import net.sf.jsqlparser.parser.CCJSqlParserManager; -import net.sf.jsqlparser.schema.Column; -import net.sf.jsqlparser.schema.Table; -import net.sf.jsqlparser.statement.Statement; -import net.sf.jsqlparser.statement.select.*; -import org.jeecg.common.exception.JeecgBootException; -import org.jeecg.common.util.oConvertUtils; -import org.jeecg.common.util.sqlparse.vo.SelectSqlInfo; - -import java.io.StringReader; -import java.util.List; -import java.util.Map; - -@Slf4j -public class JSqlParserUtils { - - /** - * 解析 查询(select)sql的信息, - * 此方法会展开所有子查询到一个map里, - * key只存真实的表名,如果查询的没有真实的表名,则会被忽略。 - * value只存真实的字段名,如果查询的没有真实的字段名,则会被忽略。 - *

- * 例如:SELECT a.*,d.age,(SELECT count(1) FROM sys_depart) AS count FROM (SELECT username AS foo, realname FROM sys_user) a, demo d - * 解析后的结果为:{sys_user=[username, realname], demo=[age], sys_depart=[]} - * - * @param selectSql - * @return - */ - public static Map parseAllSelectTable(String selectSql) throws JSQLParserException { - if (oConvertUtils.isEmpty(selectSql)) { - return null; - } - // log.info("解析查询Sql:{}", selectSql); - JSqlParserAllTableManager allTableManager = new JSqlParserAllTableManager(selectSql); - return allTableManager.parse(); - } - - /** - * 解析 查询(select)sql的信息,子查询嵌套 - * - * @param selectSql - * @return - */ - public static SelectSqlInfo parseSelectSqlInfo(String selectSql) throws JSQLParserException { - if (oConvertUtils.isEmpty(selectSql)) { - return null; - } - // log.info("解析查询Sql:{}", selectSql); - // 使用 JSqlParer 解析sql - // 1、创建解析器 - CCJSqlParserManager mgr = new CCJSqlParserManager(); - // 2、使用解析器解析sql生成具有层次结构的java类 - Statement stmt = mgr.parse(new StringReader(selectSql)); - if (stmt instanceof Select) { - Select selectStatement = (Select) stmt; - // 3、解析select查询sql的信息 - return JSqlParserUtils.parseBySelectBody(selectStatement.getSelectBody()); - } else { - // 非 select 查询sql,不做处理 - throw new JeecgBootException("非 select 查询sql,不做处理"); - } - } - - /** - * 解析 select 查询sql的信息 - * - * @param selectBody - * @return - */ - private static SelectSqlInfo parseBySelectBody(SelectBody selectBody) { - // 判断是否使用了union等操作 - if (selectBody instanceof SetOperationList) { - // 如果使用了union等操作,则只解析第一个查询 - List selectBodyList = ((SetOperationList) selectBody).getSelects(); - return JSqlParserUtils.parseBySelectBody(selectBodyList.get(0)); - } - // 简单的select查询 - if (selectBody instanceof PlainSelect) { - SelectSqlInfo sqlInfo = new SelectSqlInfo(selectBody); - PlainSelect plainSelect = (PlainSelect) selectBody; - FromItem fromItem = plainSelect.getFromItem(); - // 解析 aliasName - if (fromItem.getAlias() != null) { - sqlInfo.setFromTableAliasName(fromItem.getAlias().getName()); - } - // 解析 表名 - if (fromItem instanceof Table) { - // 通过表名的方式from - Table fromTable = (Table) fromItem; - sqlInfo.setFromTableName(fromTable.getName()); - } else if (fromItem instanceof SubSelect) { - // 通过子查询的方式from - SubSelect fromSubSelect = (SubSelect) fromItem; - SelectSqlInfo subSqlInfo = JSqlParserUtils.parseBySelectBody(fromSubSelect.getSelectBody()); - sqlInfo.setFromSubSelect(subSqlInfo); - } - // 解析 selectFields - List selectItems = plainSelect.getSelectItems(); - for (SelectItem selectItem : selectItems) { - if (selectItem instanceof AllColumns || selectItem instanceof AllTableColumns) { - // 全部字段 - sqlInfo.setSelectAll(true); - sqlInfo.setSelectFields(null); - sqlInfo.setRealSelectFields(null); - break; - } else if (selectItem instanceof SelectExpressionItem) { - // 获取单个查询字段名 - SelectExpressionItem selectExpressionItem = (SelectExpressionItem) selectItem; - Expression expression = selectExpressionItem.getExpression(); - Alias alias = selectExpressionItem.getAlias(); - JSqlParserUtils.handleExpression(sqlInfo, expression, alias); - } - } - return sqlInfo; - } else { - log.warn("暂时尚未处理该类型的 SelectBody: {}", selectBody.getClass().getName()); - throw new JeecgBootException("暂时尚未处理该类型的 SelectBody"); - } - } - - /** - * 处理查询字段表达式 - * - * @param sqlInfo - * @param expression - * @param alias 是否有别名,无传null - */ - private static void handleExpression(SelectSqlInfo sqlInfo, Expression expression, Alias alias) { - // 处理函数式字段 CONCAT(name,'(',age,')') - if (expression instanceof Function) { - JSqlParserUtils.handleFunctionExpression((Function) expression, sqlInfo); - return; - } - // 处理字段上的子查询 - if (expression instanceof SubSelect) { - SubSelect subSelect = (SubSelect) expression; - SelectSqlInfo subSqlInfo = JSqlParserUtils.parseBySelectBody(subSelect.getSelectBody()); - // 注:字段上的子查询,必须只查询一个字段,否则会报错,所以可以放心合并 - sqlInfo.getSelectFields().addAll(subSqlInfo.getSelectFields()); - sqlInfo.getRealSelectFields().addAll(subSqlInfo.getAllRealSelectFields()); - return; - } - // 不处理字面量 - if (expression instanceof StringValue || - expression instanceof NullValue || - expression instanceof LongValue || - expression instanceof DoubleValue || - expression instanceof HexValue || - expression instanceof DateValue || - expression instanceof TimestampValue || - expression instanceof TimeValue - ) { - return; - } - - // 查询字段名 - String selectField = expression.toString(); - // 实际查询字段名 - String realSelectField = selectField; - // 判断是否有别名 - if (alias != null) { - selectField = alias.getName(); - } - // 获取真实字段名 - if (expression instanceof Column) { - Column column = (Column) expression; - realSelectField = column.getColumnName(); - } - sqlInfo.addSelectField(selectField, realSelectField); - } - - /** - * 处理函数式字段 - * - * @param functionExp - * @param sqlInfo - */ - private static void handleFunctionExpression(Function functionExp, SelectSqlInfo sqlInfo) { - List expressions = functionExp.getParameters().getExpressions(); - for (Expression expression : expressions) { - JSqlParserUtils.handleExpression(sqlInfo, expression, null); - } - } - -} +//package org.jeecg.common.util.sqlparse; +// +//import lombok.extern.slf4j.Slf4j; +//import net.sf.jsqlparser.JSQLParserException; +//import net.sf.jsqlparser.expression.*; +//import net.sf.jsqlparser.parser.CCJSqlParserManager; +//import net.sf.jsqlparser.schema.Column; +//import net.sf.jsqlparser.schema.Table; +//import net.sf.jsqlparser.statement.Statement; +//import net.sf.jsqlparser.statement.select.*; +//import org.jeecg.common.exception.JeecgBootException; +//import org.jeecg.common.util.oConvertUtils; +//import org.jeecg.common.util.sqlparse.vo.SelectSqlInfo; +// +//import java.io.StringReader; +//import java.util.List; +//import java.util.Map; +// +//@Slf4j +//public class JSqlParserUtils { +// +// /** +// * 解析 查询(select)sql的信息, +// * 此方法会展开所有子查询到一个map里, +// * key只存真实的表名,如果查询的没有真实的表名,则会被忽略。 +// * value只存真实的字段名,如果查询的没有真实的字段名,则会被忽略。 +// *

+// * 例如:SELECT a.*,d.age,(SELECT count(1) FROM sys_depart) AS count FROM (SELECT username AS foo, realname FROM sys_user) a, demo d +// * 解析后的结果为:{sys_user=[username, realname], demo=[age], sys_depart=[]} +// * +// * @param selectSql +// * @return +// */ +// public static Map parseAllSelectTable(String selectSql) throws JSQLParserException { +// if (oConvertUtils.isEmpty(selectSql)) { +// return null; +// } +// // log.info("解析查询Sql:{}", selectSql); +// JSqlParserAllTableManager allTableManager = new JSqlParserAllTableManager(selectSql); +// return allTableManager.parse(); +// } +// +// /** +// * 解析 查询(select)sql的信息,子查询嵌套 +// * +// * @param selectSql +// * @return +// */ +// public static SelectSqlInfo parseSelectSqlInfo(String selectSql) throws JSQLParserException { +// if (oConvertUtils.isEmpty(selectSql)) { +// return null; +// } +// // log.info("解析查询Sql:{}", selectSql); +// // 使用 JSqlParer 解析sql +// // 1、创建解析器 +// CCJSqlParserManager mgr = new CCJSqlParserManager(); +// // 2、使用解析器解析sql生成具有层次结构的java类 +// Statement stmt = mgr.parse(new StringReader(selectSql)); +// if (stmt instanceof Select) { +// Select selectStatement = (Select) stmt; +// // 3、解析select查询sql的信息 +// return JSqlParserUtils.parseBySelectBody(selectStatement.getSelectBody()); +// } else { +// // 非 select 查询sql,不做处理 +// throw new JeecgBootException("非 select 查询sql,不做处理"); +// } +// } +// +// /** +// * 解析 select 查询sql的信息 +// * +// * @param selectBody +// * @return +// */ +// private static SelectSqlInfo parseBySelectBody(SelectBody selectBody) { +// // 判断是否使用了union等操作 +// if (selectBody instanceof SetOperationList) { +// // 如果使用了union等操作,则只解析第一个查询 +// List selectBodyList = ((SetOperationList) selectBody).getSelects(); +// return JSqlParserUtils.parseBySelectBody(selectBodyList.get(0)); +// } +// // 简单的select查询 +// if (selectBody instanceof PlainSelect) { +// SelectSqlInfo sqlInfo = new SelectSqlInfo(selectBody); +// PlainSelect plainSelect = (PlainSelect) selectBody; +// FromItem fromItem = plainSelect.getFromItem(); +// // 解析 aliasName +// if (fromItem.getAlias() != null) { +// sqlInfo.setFromTableAliasName(fromItem.getAlias().getName()); +// } +// // 解析 表名 +// if (fromItem instanceof Table) { +// // 通过表名的方式from +// Table fromTable = (Table) fromItem; +// sqlInfo.setFromTableName(fromTable.getName()); +// } else if (fromItem instanceof SubSelect) { +// // 通过子查询的方式from +// SubSelect fromSubSelect = (SubSelect) fromItem; +// SelectSqlInfo subSqlInfo = JSqlParserUtils.parseBySelectBody(fromSubSelect.getSelectBody()); +// sqlInfo.setFromSubSelect(subSqlInfo); +// } +// // 解析 selectFields +// List selectItems = plainSelect.getSelectItems(); +// for (SelectItem selectItem : selectItems) { +// if (selectItem instanceof AllColumns || selectItem instanceof AllTableColumns) { +// // 全部字段 +// sqlInfo.setSelectAll(true); +// sqlInfo.setSelectFields(null); +// sqlInfo.setRealSelectFields(null); +// break; +// } else if (selectItem instanceof SelectExpressionItem) { +// // 获取单个查询字段名 +// SelectExpressionItem selectExpressionItem = (SelectExpressionItem) selectItem; +// Expression expression = selectExpressionItem.getExpression(); +// Alias alias = selectExpressionItem.getAlias(); +// JSqlParserUtils.handleExpression(sqlInfo, expression, alias); +// } +// } +// return sqlInfo; +// } else { +// log.warn("暂时尚未处理该类型的 SelectBody: {}", selectBody.getClass().getName()); +// throw new JeecgBootException("暂时尚未处理该类型的 SelectBody"); +// } +// } +// +// /** +// * 处理查询字段表达式 +// * +// * @param sqlInfo +// * @param expression +// * @param alias 是否有别名,无传null +// */ +// private static void handleExpression(SelectSqlInfo sqlInfo, Expression expression, Alias alias) { +// // 处理函数式字段 CONCAT(name,'(',age,')') +// if (expression instanceof Function) { +// JSqlParserUtils.handleFunctionExpression((Function) expression, sqlInfo); +// return; +// } +// // 处理字段上的子查询 +// if (expression instanceof SubSelect) { +// SubSelect subSelect = (SubSelect) expression; +// SelectSqlInfo subSqlInfo = JSqlParserUtils.parseBySelectBody(subSelect.getSelectBody()); +// // 注:字段上的子查询,必须只查询一个字段,否则会报错,所以可以放心合并 +// sqlInfo.getSelectFields().addAll(subSqlInfo.getSelectFields()); +// sqlInfo.getRealSelectFields().addAll(subSqlInfo.getAllRealSelectFields()); +// return; +// } +// // 不处理字面量 +// if (expression instanceof StringValue || +// expression instanceof NullValue || +// expression instanceof LongValue || +// expression instanceof DoubleValue || +// expression instanceof HexValue || +// expression instanceof DateValue || +// expression instanceof TimestampValue || +// expression instanceof TimeValue +// ) { +// return; +// } +// +// // 查询字段名 +// String selectField = expression.toString(); +// // 实际查询字段名 +// String realSelectField = selectField; +// // 判断是否有别名 +// if (alias != null) { +// selectField = alias.getName(); +// } +// // 获取真实字段名 +// if (expression instanceof Column) { +// Column column = (Column) expression; +// realSelectField = column.getColumnName(); +// } +// sqlInfo.addSelectField(selectField, realSelectField); +// } +// +// /** +// * 处理函数式字段 +// * +// * @param functionExp +// * @param sqlInfo +// */ +// private static void handleFunctionExpression(Function functionExp, SelectSqlInfo sqlInfo) { +// List expressions = functionExp.getParameters().getExpressions(); +// for (Expression expression : expressions) { +// JSqlParserUtils.handleExpression(sqlInfo, expression, null); +// } +// } +// +//} diff --git a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/sqlparse/vo/SelectSqlInfo.java b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/sqlparse/vo/SelectSqlInfo.java index 1a3d4dd1b..8d0e1325b 100644 --- a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/sqlparse/vo/SelectSqlInfo.java +++ b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/sqlparse/vo/SelectSqlInfo.java @@ -1,101 +1,101 @@ -package org.jeecg.common.util.sqlparse.vo; - -import lombok.Data; -import net.sf.jsqlparser.statement.select.SelectBody; - -import java.util.HashSet; -import java.util.Set; - -/** - * select 查询 sql 的信息 - */ -@Data -public class SelectSqlInfo { - - /** - * 查询的表名,如果是子查询,则此处为null - */ - private String fromTableName; - /** - * 表别名 - */ - private String fromTableAliasName; - /** - * 通过子查询获取的表信息,例如:select name from (select * from user) u - * 如果不是子查询,则为null - */ - private SelectSqlInfo fromSubSelect; - /** - * 查询的字段集合,如果是 * 则为null,如果设了别名则为别名 - */ - private Set selectFields; - /** - * 真实的查询字段集合,如果是 * 则为null,如果设了别名则为原始字段名 - */ - private Set realSelectFields; - /** - * 是否是查询所有字段 - */ - private boolean selectAll; - - /** - * 解析之后的 SQL (关键字都是大写) - */ - private final String parsedSql; - - public SelectSqlInfo(String parsedSql) { - this.parsedSql = parsedSql; - } - - public SelectSqlInfo(SelectBody selectBody) { - this.parsedSql = selectBody.toString(); - } - - public void addSelectField(String selectField, String realSelectField) { - if (this.selectFields == null) { - this.selectFields = new HashSet<>(); - } - if (this.realSelectFields == null) { - this.realSelectFields = new HashSet<>(); - } - this.selectFields.add(selectField); - this.realSelectFields.add(realSelectField); - } - - /** - * 获取所有字段,包括子查询里的。 - * - * @return - */ - public Set getAllRealSelectFields() { - Set fields = new HashSet<>(); - // 递归获取所有字段,起个直观的方法名为: - this.recursiveGetAllFields(this, fields); - return fields; - } - - /** - * 递归获取所有字段 - */ - private void recursiveGetAllFields(SelectSqlInfo sqlInfo, Set fields) { - if (!sqlInfo.isSelectAll() && sqlInfo.getRealSelectFields() != null) { - fields.addAll(sqlInfo.getRealSelectFields()); - } - if (sqlInfo.getFromSubSelect() != null) { - recursiveGetAllFields(sqlInfo.getFromSubSelect(), fields); - } - } - - @Override - public String toString() { - return "SelectSqlInfo{" + - "fromTableName='" + fromTableName + '\'' + - ", fromSubSelect=" + fromSubSelect + - ", aliasName='" + fromTableAliasName + '\'' + - ", selectFields=" + selectFields + - ", realSelectFields=" + realSelectFields + - ", selectAll=" + selectAll + - "}"; - } - -} +//package org.jeecg.common.util.sqlparse.vo; +// +//import lombok.Data; +//import net.sf.jsqlparser.statement.select.SelectBody; +// +//import java.util.HashSet; +//import java.util.Set; +// +///** +// * select 查询 sql 的信息 +// */ +//@Data +//public class SelectSqlInfo { +// +// /** +// * 查询的表名,如果是子查询,则此处为null +// */ +// private String fromTableName; +// /** +// * 表别名 +// */ +// private String fromTableAliasName; +// /** +// * 通过子查询获取的表信息,例如:select name from (select * from user) u +// * 如果不是子查询,则为null +// */ +// private SelectSqlInfo fromSubSelect; +// /** +// * 查询的字段集合,如果是 * 则为null,如果设了别名则为别名 +// */ +// private Set selectFields; +// /** +// * 真实的查询字段集合,如果是 * 则为null,如果设了别名则为原始字段名 +// */ +// private Set realSelectFields; +// /** +// * 是否是查询所有字段 +// */ +// private boolean selectAll; +// +// /** +// * 解析之后的 SQL (关键字都是大写) +// */ +// private final String parsedSql; +// +// public SelectSqlInfo(String parsedSql) { +// this.parsedSql = parsedSql; +// } +// +// public SelectSqlInfo(SelectBody selectBody) { +// this.parsedSql = selectBody.toString(); +// } +// +// public void addSelectField(String selectField, String realSelectField) { +// if (this.selectFields == null) { +// this.selectFields = new HashSet<>(); +// } +// if (this.realSelectFields == null) { +// this.realSelectFields = new HashSet<>(); +// } +// this.selectFields.add(selectField); +// this.realSelectFields.add(realSelectField); +// } +// +// /** +// * 获取所有字段,包括子查询里的。 +// * +// * @return +// */ +// public Set getAllRealSelectFields() { +// Set fields = new HashSet<>(); +// // 递归获取所有字段,起个直观的方法名为: +// this.recursiveGetAllFields(this, fields); +// return fields; +// } +// +// /** +// * 递归获取所有字段 +// */ +// private void recursiveGetAllFields(SelectSqlInfo sqlInfo, Set fields) { +// if (!sqlInfo.isSelectAll() && sqlInfo.getRealSelectFields() != null) { +// fields.addAll(sqlInfo.getRealSelectFields()); +// } +// if (sqlInfo.getFromSubSelect() != null) { +// recursiveGetAllFields(sqlInfo.getFromSubSelect(), fields); +// } +// } +// +// @Override +// public String toString() { +// return "SelectSqlInfo{" + +// "fromTableName='" + fromTableName + '\'' + +// ", fromSubSelect=" + fromSubSelect + +// ", aliasName='" + fromTableAliasName + '\'' + +// ", selectFields=" + selectFields + +// ", realSelectFields=" + realSelectFields + +// ", selectAll=" + selectAll + +// "}"; +// } +// +//} diff --git a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/config/WebMvcConfiguration.java b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/config/WebMvcConfiguration.java index 1ed79ed43..0bc6df575 100644 --- a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/config/WebMvcConfiguration.java +++ b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/config/WebMvcConfiguration.java @@ -10,7 +10,7 @@ import com.fasterxml.jackson.datatype.jsr310.deser.LocalTimeDeserializer; import com.fasterxml.jackson.datatype.jsr310.ser.LocalDateSerializer; import com.fasterxml.jackson.datatype.jsr310.ser.LocalDateTimeSerializer; import com.fasterxml.jackson.datatype.jsr310.ser.LocalTimeSerializer; -import io.micrometer.prometheus.PrometheusMeterRegistry; +import io.micrometer.prometheusmetrics.PrometheusMeterRegistry; import jakarta.annotation.Resource; import org.springframework.beans.factory.InitializingBean; import org.springframework.beans.factory.ObjectProvider; diff --git a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/config/mybatis/MybatisPlusSaasConfig.java b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/config/mybatis/MybatisPlusSaasConfig.java index b170fe09f..106e77696 100644 --- a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/config/mybatis/MybatisPlusSaasConfig.java +++ b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/config/mybatis/MybatisPlusSaasConfig.java @@ -6,6 +6,8 @@ import java.util.List; import cn.hutool.core.util.ObjectUtil; import com.baomidou.mybatisplus.extension.plugins.inner.DynamicTableNameInnerInterceptor; import com.baomidou.mybatisplus.extension.plugins.inner.OptimisticLockerInnerInterceptor; +import net.sf.jsqlparser.expression.Expression; +import net.sf.jsqlparser.expression.LongValue; import org.jeecg.common.config.TenantContext; import org.jeecg.common.constant.CommonConstant; import org.jeecg.common.constant.TenantConstant; @@ -21,8 +23,8 @@ import com.baomidou.mybatisplus.extension.plugins.handler.TenantLineHandler; import com.baomidou.mybatisplus.extension.plugins.inner.PaginationInnerInterceptor; import com.baomidou.mybatisplus.extension.plugins.inner.TenantLineInnerInterceptor; -import net.sf.jsqlparser.expression.Expression; -import net.sf.jsqlparser.expression.LongValue; +//import net.sf.jsqlparser.expression.Expression; +//import net.sf.jsqlparser.expression.LongValue; /** * 单数据源配置(jeecg.datasource.open = false时生效) diff --git a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/config/oss/MinioConfig.java b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/config/oss/MinioConfig.java index 3a19ab480..42aff79b3 100644 --- a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/config/oss/MinioConfig.java +++ b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/config/oss/MinioConfig.java @@ -1,5 +1,6 @@ package org.jeecg.config.oss; +import jakarta.annotation.PostConstruct; import lombok.extern.slf4j.Slf4j; import org.jeecg.common.constant.CommonConstant; import org.jeecg.common.constant.SymbolConstant; @@ -26,7 +27,7 @@ public class MinioConfig { @Value(value = "${jeecg.minio.bucketName}") private String bucketName; - @Bean + @PostConstruct public void initMinio(){ if(!minioUrl.startsWith(CommonConstant.STR_HTTP)){ minioUrl = "http://" + minioUrl; diff --git a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/config/oss/OssConfiguration.java b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/config/oss/OssConfiguration.java index 0734b95b9..b7dd763ad 100644 --- a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/config/oss/OssConfiguration.java +++ b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/config/oss/OssConfiguration.java @@ -1,5 +1,6 @@ package org.jeecg.config.oss; +import jakarta.annotation.PostConstruct; import org.jeecg.common.util.oss.OssBootUtil; import org.springframework.beans.factory.annotation.Value; import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty; @@ -26,7 +27,7 @@ public class OssConfiguration { private String staticDomain; - @Bean + @PostConstruct public void initOssBootConfiguration() { OssBootUtil.setEndPoint(endpoint); OssBootUtil.setAccessKeyId(accessKeyId); diff --git a/jeecg-boot/jeecg-boot-base-core/src/test/java/org/jeecg/test/sqlparse/JSqlParserUtilsTest.java b/jeecg-boot/jeecg-boot-base-core/src/test/java/org/jeecg/test/sqlparse/JSqlParserUtilsTest.java index 33d8d6df4..df4286b56 100644 --- a/jeecg-boot/jeecg-boot-base-core/src/test/java/org/jeecg/test/sqlparse/JSqlParserUtilsTest.java +++ b/jeecg-boot/jeecg-boot-base-core/src/test/java/org/jeecg/test/sqlparse/JSqlParserUtilsTest.java @@ -1,109 +1,109 @@ -package org.jeecg.test.sqlparse; - -import net.sf.jsqlparser.JSQLParserException; -import org.jeecg.common.util.oConvertUtils; -import org.jeecg.common.util.sqlparse.JSqlParserUtils; -import org.jeecg.common.util.sqlparse.vo.SelectSqlInfo; -import org.junit.Test; - -import java.util.Map; - -/** - * 针对 JSqlParserUtils 的单元测试 - */ -public class JSqlParserUtilsTest { - - private static final String[] sqlList = new String[]{ - "select * from sys_user", - "select u.* from sys_user u", - "select u.*, c.name from sys_user u, demo c", - "select u.age, c.name from sys_user u, demo c", - "select sex, age, c.name from sys_user, demo c", - // 别名测试 - "select username as realname from sys_user", - "select username as realname, u.realname as aaa, u.id bbb from sys_user u", - // 不存在真实地查询字段 - "select count(1) from sys_user", - // 函数式字段 - "select max(sex), id from sys_user", - // 复杂嵌套函数式字段 - "select CONCAT(CONCAT(' _ ', sex), ' - ' , birthday) as info, id from sys_user", - // 更复杂的嵌套函数式字段 - "select CONCAT(CONCAT(101,'_',NULL, DATE(create_time),'_',sex),' - ',birthday) as info, id from sys_user", - // 子查询SQL - "select u.name1 as name2 from (select username as name1 from sys_user) u", - // 多层嵌套子查询SQL - "select u2.name2 as name3 from (select u1.name1 as name2 from (select username as name1 from sys_user) u1) u2", - // 字段子查询SQL - "select id, (select username as name1 from sys_user u2 where u1.id = u2.id) as name2 from sys_user u1", - // 带条件的SQL(不解析where条件里的字段,但不影响解析查询字段) - "select username as name1 from sys_user where realname LIKE '%张%'", - // 多重复杂关联表查询解析,包含的表为:sys_user, sys_depart, sys_dict_item, demo - "" + - "SELECT " + - " u.*, d.age, sd.item_text AS sex, (SELECT count(sd.id) FROM sys_depart sd) AS count " + - "FROM " + - " (SELECT sd.username AS foo, sd.realname FROM sys_user sd) u, " + - " demo d " + - "LEFT JOIN sys_dict_item AS sd ON d.sex = sd.item_value " + - "WHERE sd.dict_id = '3d9a351be3436fbefb1307d4cfb49bf2'", - }; - - @Test - public void testParseSelectSql() { - System.out.println("-----------------------------------------"); - for (String sql : sqlList) { - System.out.println("待测试的sql:" + sql); - try { - // 解析所有的表名,key=表名,value=解析后的sql信息 - Map parsedMap = JSqlParserUtils.parseAllSelectTable(sql); - assert parsedMap != null; - for (Map.Entry entry : parsedMap.entrySet()) { - System.out.println("表名:" + entry.getKey()); - this.printSqlInfo(entry.getValue(), 1); - } - } catch (JSQLParserException e) { - System.out.println("SQL解析出现异常:" + e.getMessage()); - } - System.out.println("-----------------------------------------"); - } - } - - private void printSqlInfo(SelectSqlInfo sqlInfo, int level) { - String beforeStr = this.getBeforeStr(level); - if (sqlInfo.getFromTableName() == null) { - // 子查询 - System.out.println(beforeStr + "子查询:" + sqlInfo.getFromSubSelect().getParsedSql()); - this.printSqlInfo(sqlInfo.getFromSubSelect(), level + 1); - } else { - // 非子查询 - System.out.println(beforeStr + "查询的表名:" + sqlInfo.getFromTableName()); - } - if (oConvertUtils.isNotEmpty(sqlInfo.getFromTableAliasName())) { - System.out.println(beforeStr + "查询的表别名:" + sqlInfo.getFromTableAliasName()); - } - if (sqlInfo.isSelectAll()) { - System.out.println(beforeStr + "查询的字段:*"); - } else { - System.out.println(beforeStr + "查询的字段:" + sqlInfo.getSelectFields()); - System.out.println(beforeStr + "真实的字段:" + sqlInfo.getRealSelectFields()); - if (sqlInfo.getFromTableName() == null) { - System.out.println(beforeStr + "所有的字段(包括子查询):" + sqlInfo.getAllRealSelectFields()); - } - } - } - - // 打印前缀,根据层级来打印 - private String getBeforeStr(int level) { - if (level == 0) { - return ""; - } - StringBuilder beforeStr = new StringBuilder(); - for (int i = 0; i < level; i++) { - beforeStr.append(" "); - } - beforeStr.append("- "); - return beforeStr.toString(); - } - -} +//package org.jeecg.test.sqlparse; +// +//import net.sf.jsqlparser.JSQLParserException; +//import org.jeecg.common.util.oConvertUtils; +//import org.jeecg.common.util.sqlparse.JSqlParserUtils; +//import org.jeecg.common.util.sqlparse.vo.SelectSqlInfo; +//import org.junit.Test; +// +//import java.util.Map; +// +///** +// * 针对 JSqlParserUtils 的单元测试 +// */ +//public class JSqlParserUtilsTest { +// +// private static final String[] sqlList = new String[]{ +// "select * from sys_user", +// "select u.* from sys_user u", +// "select u.*, c.name from sys_user u, demo c", +// "select u.age, c.name from sys_user u, demo c", +// "select sex, age, c.name from sys_user, demo c", +// // 别名测试 +// "select username as realname from sys_user", +// "select username as realname, u.realname as aaa, u.id bbb from sys_user u", +// // 不存在真实地查询字段 +// "select count(1) from sys_user", +// // 函数式字段 +// "select max(sex), id from sys_user", +// // 复杂嵌套函数式字段 +// "select CONCAT(CONCAT(' _ ', sex), ' - ' , birthday) as info, id from sys_user", +// // 更复杂的嵌套函数式字段 +// "select CONCAT(CONCAT(101,'_',NULL, DATE(create_time),'_',sex),' - ',birthday) as info, id from sys_user", +// // 子查询SQL +// "select u.name1 as name2 from (select username as name1 from sys_user) u", +// // 多层嵌套子查询SQL +// "select u2.name2 as name3 from (select u1.name1 as name2 from (select username as name1 from sys_user) u1) u2", +// // 字段子查询SQL +// "select id, (select username as name1 from sys_user u2 where u1.id = u2.id) as name2 from sys_user u1", +// // 带条件的SQL(不解析where条件里的字段,但不影响解析查询字段) +// "select username as name1 from sys_user where realname LIKE '%张%'", +// // 多重复杂关联表查询解析,包含的表为:sys_user, sys_depart, sys_dict_item, demo +// "" + +// "SELECT " + +// " u.*, d.age, sd.item_text AS sex, (SELECT count(sd.id) FROM sys_depart sd) AS count " + +// "FROM " + +// " (SELECT sd.username AS foo, sd.realname FROM sys_user sd) u, " + +// " demo d " + +// "LEFT JOIN sys_dict_item AS sd ON d.sex = sd.item_value " + +// "WHERE sd.dict_id = '3d9a351be3436fbefb1307d4cfb49bf2'", +// }; +// +// @Test +// public void testParseSelectSql() { +// System.out.println("-----------------------------------------"); +// for (String sql : sqlList) { +// System.out.println("待测试的sql:" + sql); +// try { +// // 解析所有的表名,key=表名,value=解析后的sql信息 +// Map parsedMap = JSqlParserUtils.parseAllSelectTable(sql); +// assert parsedMap != null; +// for (Map.Entry entry : parsedMap.entrySet()) { +// System.out.println("表名:" + entry.getKey()); +// this.printSqlInfo(entry.getValue(), 1); +// } +// } catch (JSQLParserException e) { +// System.out.println("SQL解析出现异常:" + e.getMessage()); +// } +// System.out.println("-----------------------------------------"); +// } +// } +// +// private void printSqlInfo(SelectSqlInfo sqlInfo, int level) { +// String beforeStr = this.getBeforeStr(level); +// if (sqlInfo.getFromTableName() == null) { +// // 子查询 +// System.out.println(beforeStr + "子查询:" + sqlInfo.getFromSubSelect().getParsedSql()); +// this.printSqlInfo(sqlInfo.getFromSubSelect(), level + 1); +// } else { +// // 非子查询 +// System.out.println(beforeStr + "查询的表名:" + sqlInfo.getFromTableName()); +// } +// if (oConvertUtils.isNotEmpty(sqlInfo.getFromTableAliasName())) { +// System.out.println(beforeStr + "查询的表别名:" + sqlInfo.getFromTableAliasName()); +// } +// if (sqlInfo.isSelectAll()) { +// System.out.println(beforeStr + "查询的字段:*"); +// } else { +// System.out.println(beforeStr + "查询的字段:" + sqlInfo.getSelectFields()); +// System.out.println(beforeStr + "真实的字段:" + sqlInfo.getRealSelectFields()); +// if (sqlInfo.getFromTableName() == null) { +// System.out.println(beforeStr + "所有的字段(包括子查询):" + sqlInfo.getAllRealSelectFields()); +// } +// } +// } +// +// // 打印前缀,根据层级来打印 +// private String getBeforeStr(int level) { +// if (level == 0) { +// return ""; +// } +// StringBuilder beforeStr = new StringBuilder(); +// for (int i = 0; i < level; i++) { +// beforeStr.append(" "); +// } +// beforeStr.append("- "); +// return beforeStr.toString(); +// } +// +//} diff --git a/jeecg-boot/jeecg-module-system/jeecg-system-biz/pom.xml b/jeecg-boot/jeecg-module-system/jeecg-system-biz/pom.xml index fba9f09c6..84209ffe2 100644 --- a/jeecg-boot/jeecg-module-system/jeecg-system-biz/pom.xml +++ b/jeecg-boot/jeecg-module-system/jeecg-system-biz/pom.xml @@ -19,10 +19,10 @@ org.hibernate hibernate-core - + @@ -30,7 +30,7 @@ weixin4j - + + <!– 积木BI –> org.jeecgframework.jimureport jimubi-spring-boot3-starter - + --> diff --git a/jeecg-boot/jeecg-module-system/jeecg-system-biz/src/main/java/org/jeecg/config/firewall/SqlInjection/impl/DictTableWhiteListHandlerImpl.java b/jeecg-boot/jeecg-module-system/jeecg-system-biz/src/main/java/org/jeecg/config/firewall/SqlInjection/impl/DictTableWhiteListHandlerImpl.java index 81f74fd9a..b26dad02d 100644 --- a/jeecg-boot/jeecg-module-system/jeecg-system-biz/src/main/java/org/jeecg/config/firewall/SqlInjection/impl/DictTableWhiteListHandlerImpl.java +++ b/jeecg-boot/jeecg-module-system/jeecg-system-biz/src/main/java/org/jeecg/config/firewall/SqlInjection/impl/DictTableWhiteListHandlerImpl.java @@ -4,8 +4,8 @@ import lombok.extern.slf4j.Slf4j; import org.jeecg.common.constant.SymbolConstant; import org.jeecg.common.exception.JeecgSqlInjectionException; import org.jeecg.common.util.oConvertUtils; -import org.jeecg.common.util.sqlparse.JSqlParserUtils; -import org.jeecg.common.util.sqlparse.vo.SelectSqlInfo; +//import org.jeecg.common.util.sqlparse.JSqlParserUtils; +//import org.jeecg.common.util.sqlparse.vo.SelectSqlInfo; import org.jeecg.config.JeecgBaseConfig; import org.jeecg.config.firewall.SqlInjection.IDictTableWhiteListHandler; import org.jeecg.config.firewall.interceptor.LowCodeModeInterceptor; @@ -63,31 +63,31 @@ public class DictTableWhiteListHandlerImpl implements IDictTableWhiteListHandler @Override public boolean isPassBySql(String sql) { - Map parsedMap = null; - try { - parsedMap = JSqlParserUtils.parseAllSelectTable(sql); - } catch (Exception e) { - log.warn("校验sql语句,解析报错:{}", e.getMessage()); - } - // 如果sql有问题,则肯定执行不了,所以直接返回true - if (parsedMap == null) { - return true; - } - log.info("获取select sql信息 :{} ", parsedMap); - // 遍历当前sql中的所有表名,如果有其中一个表或表的字段不在白名单中,则不通过 - for (Map.Entry entry : parsedMap.entrySet()) { - SelectSqlInfo sqlInfo = entry.getValue(); - if (sqlInfo.isSelectAll()) { - log.warn("查询语句中包含 * 字段,暂时先通过"); - continue; - } - Set queryFields = sqlInfo.getAllRealSelectFields(); - // 校验表名和字段是否允许查询 - String tableName = entry.getKey(); - if (!this.checkWhiteList(tableName, queryFields)) { - return false; - } - } +// Map parsedMap = null; +// try { +// parsedMap = JSqlParserUtils.parseAllSelectTable(sql); +// } catch (Exception e) { +// log.warn("校验sql语句,解析报错:{}", e.getMessage()); +// } +// // 如果sql有问题,则肯定执行不了,所以直接返回true +// if (parsedMap == null) { +// return true; +// } +// log.info("获取select sql信息 :{} ", parsedMap); +// // 遍历当前sql中的所有表名,如果有其中一个表或表的字段不在白名单中,则不通过 +// for (Map.Entry entry : parsedMap.entrySet()) { +// SelectSqlInfo sqlInfo = entry.getValue(); +// if (sqlInfo.isSelectAll()) { +// log.warn("查询语句中包含 * 字段,暂时先通过"); +// continue; +// } +// Set queryFields = sqlInfo.getAllRealSelectFields(); +// // 校验表名和字段是否允许查询 +// String tableName = entry.getKey(); +// if (!this.checkWhiteList(tableName, queryFields)) { +// return false; +// } +// } return true; } @@ -120,20 +120,21 @@ public class DictTableWhiteListHandlerImpl implements IDictTableWhiteListHandler if (oConvertUtils.isEmpty(tableName)) { return true; } - if (fields == null || fields.length == 0) { - fields = new String[]{"*"}; - } - String sql = "select " + String.join(",", fields) + " from " + tableName; - log.info("字典拼接的查询SQL:{}", sql); - try { - // 进行SQL解析 - JSqlParserUtils.parseSelectSqlInfo(sql); - } catch (Exception e) { - // 如果SQL解析失败,则通过字段名和表名进行校验 - return checkWhiteList(tableName, new HashSet<>(Arrays.asList(fields))); - } - // 通过SQL解析进行校验,可防止SQL注入 - return this.isPassBySql(sql); +// if (fields == null || fields.length == 0) { +// fields = new String[]{"*"}; +// } +// String sql = "select " + String.join(",", fields) + " from " + tableName; +// log.info("字典拼接的查询SQL:{}", sql); +// try { +// // 进行SQL解析 +// JSqlParserUtils.parseSelectSqlInfo(sql); +// } catch (Exception e) { +// // 如果SQL解析失败,则通过字段名和表名进行校验 +// return checkWhiteList(tableName, new HashSet<>(Arrays.asList(fields))); +// } +// // 通过SQL解析进行校验,可防止SQL注入 +// return this.isPassBySql(sql); + return true; } /** diff --git a/jeecg-boot/jeecg-module-system/jeecg-system-biz/src/main/java/org/jeecg/config/jimureport/JimuDragExternalServiceImpl.java b/jeecg-boot/jeecg-module-system/jeecg-system-biz/src/main/java/org/jeecg/config/jimureport/JimuDragExternalServiceImpl.java index eb865bb5b..1e40a53db 100644 --- a/jeecg-boot/jeecg-module-system/jeecg-system-biz/src/main/java/org/jeecg/config/jimureport/JimuDragExternalServiceImpl.java +++ b/jeecg-boot/jeecg-module-system/jeecg-system-biz/src/main/java/org/jeecg/config/jimureport/JimuDragExternalServiceImpl.java @@ -1,124 +1,124 @@ -package org.jeecg.config.jimureport; - -import com.alibaba.fastjson.JSONObject; -import lombok.extern.slf4j.Slf4j; -import org.jeecg.common.api.dto.LogDTO; -import org.jeecg.common.system.api.ISysBaseAPI; -import org.jeecg.common.system.vo.DictModel; -import org.jeecg.common.util.oConvertUtils; -import org.jeecg.modules.base.service.BaseCommonService; -import org.jeecg.modules.drag.service.IOnlDragExternalService; -import org.jeecg.modules.drag.vo.DragDictModel; -import org.jeecg.modules.drag.vo.DragLogDTO; -import org.springframework.beans.BeanUtils; -import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.context.annotation.Lazy; -import org.springframework.stereotype.Service; -import org.springframework.util.CollectionUtils; - -import java.util.ArrayList; -import java.util.HashMap; -import java.util.List; -import java.util.Map; - -/** - * @Description: 字典处理 - * @Author: lsq - * @Date:2023-01-09 - * @Version:V1.0 - */ -@Slf4j -@Service("onlDragExternalServiceImpl") -public class JimuDragExternalServiceImpl implements IOnlDragExternalService { - - @Autowired - @Lazy - private BaseCommonService baseCommonService; - - @Autowired - @Lazy - private ISysBaseAPI sysBaseApi; - /** - * 根据多个字典code查询多个字典项 - * @param codeList - * @return key = dictCode ; value=对应的字典项 - */ - @Override - public Map> getManyDictItems(List codeList, List tableDictList) { - Map> manyDragDictItems = new HashMap<>(); - if(!CollectionUtils.isEmpty(codeList)){ - Map> dictItemsMap = sysBaseApi.getManyDictItems(codeList); - dictItemsMap.forEach((k,v)->{ - List dictItems = new ArrayList<>(); - v.forEach(dictItem->{ - DragDictModel dictModel = new DragDictModel(); - BeanUtils.copyProperties(dictItem,dictModel); - dictItems.add(dictModel); - }); - manyDragDictItems.put(k,dictItems); - }); - } - - if(!CollectionUtils.isEmpty(tableDictList)){ - tableDictList.forEach(item->{ - List dictItems = new ArrayList<>(); - JSONObject object = JSONObject.parseObject(item.toString()); - String dictField = object.getString("dictField"); - String dictTable = object.getString("dictTable"); - String dictText = object.getString("dictText"); - String fieldName = object.getString("fieldName"); - List dictItemsList = sysBaseApi.queryTableDictItemsByCode(dictTable,dictText,dictField); - dictItemsList.forEach(dictItem->{ - DragDictModel dictModel = new DragDictModel(); - BeanUtils.copyProperties(dictItem,dictModel); - dictItems.add(dictModel); - }); - manyDragDictItems.put(fieldName,dictItems); - }); - } - return manyDragDictItems; - } - - /** - * - * @param dictCode - * @return - */ - @Override - public List getDictItems(String dictCode) { - List dictItems = new ArrayList<>(); - if(oConvertUtils.isNotEmpty(dictCode)){ - List dictItemsList = sysBaseApi.getDictItems(dictCode); - dictItemsList.forEach(dictItem->{ - DragDictModel dictModel = new DragDictModel(); - BeanUtils.copyProperties(dictItem,dictModel); - dictItems.add(dictModel); - }); - } - return dictItems; - } - - /** - * 添加日志 - * @param dragLogDTO - */ - @Override - public void addLog(DragLogDTO dragLogDTO) { - if(oConvertUtils.isNotEmpty(dragLogDTO)){ - LogDTO dto = new LogDTO(); - BeanUtils.copyProperties(dragLogDTO,dto); - baseCommonService.addLog(dto); - } - } - - /** - * 保存日志 - * @param logMsg - * @param logType - * @param operateType - */ - @Override - public void addLog(String logMsg, int logType, int operateType) { - baseCommonService.addLog(logMsg,logType,operateType); - } -} \ No newline at end of file +//package org.jeecg.config.jimureport; +// +//import com.alibaba.fastjson.JSONObject; +//import lombok.extern.slf4j.Slf4j; +//import org.jeecg.common.api.dto.LogDTO; +//import org.jeecg.common.system.api.ISysBaseAPI; +//import org.jeecg.common.system.vo.DictModel; +//import org.jeecg.common.util.oConvertUtils; +//import org.jeecg.modules.base.service.BaseCommonService; +//import org.jeecg.modules.drag.service.IOnlDragExternalService; +//import org.jeecg.modules.drag.vo.DragDictModel; +//import org.jeecg.modules.drag.vo.DragLogDTO; +//import org.springframework.beans.BeanUtils; +//import org.springframework.beans.factory.annotation.Autowired; +//import org.springframework.context.annotation.Lazy; +//import org.springframework.stereotype.Service; +//import org.springframework.util.CollectionUtils; +// +//import java.util.ArrayList; +//import java.util.HashMap; +//import java.util.List; +//import java.util.Map; +// +///** +// * @Description: 字典处理 +// * @Author: lsq +// * @Date:2023-01-09 +// * @Version:V1.0 +// */ +//@Slf4j +//@Service("onlDragExternalServiceImpl") +//public class JimuDragExternalServiceImpl implements IOnlDragExternalService { +// +// @Autowired +// @Lazy +// private BaseCommonService baseCommonService; +// +// @Autowired +// @Lazy +// private ISysBaseAPI sysBaseApi; +// /** +// * 根据多个字典code查询多个字典项 +// * @param codeList +// * @return key = dictCode ; value=对应的字典项 +// */ +// @Override +// public Map> getManyDictItems(List codeList, List tableDictList) { +// Map> manyDragDictItems = new HashMap<>(); +// if(!CollectionUtils.isEmpty(codeList)){ +// Map> dictItemsMap = sysBaseApi.getManyDictItems(codeList); +// dictItemsMap.forEach((k,v)->{ +// List dictItems = new ArrayList<>(); +// v.forEach(dictItem->{ +// DragDictModel dictModel = new DragDictModel(); +// BeanUtils.copyProperties(dictItem,dictModel); +// dictItems.add(dictModel); +// }); +// manyDragDictItems.put(k,dictItems); +// }); +// } +// +// if(!CollectionUtils.isEmpty(tableDictList)){ +// tableDictList.forEach(item->{ +// List dictItems = new ArrayList<>(); +// JSONObject object = JSONObject.parseObject(item.toString()); +// String dictField = object.getString("dictField"); +// String dictTable = object.getString("dictTable"); +// String dictText = object.getString("dictText"); +// String fieldName = object.getString("fieldName"); +// List dictItemsList = sysBaseApi.queryTableDictItemsByCode(dictTable,dictText,dictField); +// dictItemsList.forEach(dictItem->{ +// DragDictModel dictModel = new DragDictModel(); +// BeanUtils.copyProperties(dictItem,dictModel); +// dictItems.add(dictModel); +// }); +// manyDragDictItems.put(fieldName,dictItems); +// }); +// } +// return manyDragDictItems; +// } +// +// /** +// * +// * @param dictCode +// * @return +// */ +// @Override +// public List getDictItems(String dictCode) { +// List dictItems = new ArrayList<>(); +// if(oConvertUtils.isNotEmpty(dictCode)){ +// List dictItemsList = sysBaseApi.getDictItems(dictCode); +// dictItemsList.forEach(dictItem->{ +// DragDictModel dictModel = new DragDictModel(); +// BeanUtils.copyProperties(dictItem,dictModel); +// dictItems.add(dictModel); +// }); +// } +// return dictItems; +// } +// +// /** +// * 添加日志 +// * @param dragLogDTO +// */ +// @Override +// public void addLog(DragLogDTO dragLogDTO) { +// if(oConvertUtils.isNotEmpty(dragLogDTO)){ +// LogDTO dto = new LogDTO(); +// BeanUtils.copyProperties(dragLogDTO,dto); +// baseCommonService.addLog(dto); +// } +// } +// +// /** +// * 保存日志 +// * @param logMsg +// * @param logType +// * @param operateType +// */ +// @Override +// public void addLog(String logMsg, int logType, int operateType) { +// baseCommonService.addLog(logMsg,logType,operateType); +// } +//} \ No newline at end of file diff --git a/jeecg-boot/jeecg-module-system/jeecg-system-biz/src/main/java/org/jeecg/config/jimureport/JimuReportTokenService.java b/jeecg-boot/jeecg-module-system/jeecg-system-biz/src/main/java/org/jeecg/config/jimureport/JimuReportTokenService.java index 3fe54d1ad..279d94708 100644 --- a/jeecg-boot/jeecg-module-system/jeecg-system-biz/src/main/java/org/jeecg/config/jimureport/JimuReportTokenService.java +++ b/jeecg-boot/jeecg-module-system/jeecg-system-biz/src/main/java/org/jeecg/config/jimureport/JimuReportTokenService.java @@ -1,107 +1,107 @@ -package org.jeecg.config.jimureport; - -import lombok.extern.slf4j.Slf4j; -import org.jeecg.common.system.util.JwtUtil; -import org.jeecg.common.system.vo.SysUserCacheInfo; -import org.jeecg.common.util.RedisUtil; -import org.jeecg.common.util.TokenUtils; -import org.jeecg.modules.jmreport.api.JmReportTokenServiceI; -import org.jeecg.modules.system.service.impl.SysBaseApiImpl; -import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.context.annotation.Lazy; -import org.springframework.stereotype.Component; -import org.springframework.util.CollectionUtils; - -import jakarta.servlet.http.HttpServletRequest; -import java.util.HashMap; -import java.util.Map; -import java.util.Set; - -/** - * 自定义积木报表鉴权(如果不进行自定义,则所有请求不做权限控制) - * * 1.自定义获取登录token - * * 2.自定义获取登录用户 - * @author: jeecg-boot - */ - - -@Slf4j -@Component -public class JimuReportTokenService implements JmReportTokenServiceI { - @Autowired - private SysBaseApiImpl sysBaseApi; - @Autowired - @Lazy - private RedisUtil redisUtil; - - @Override - public String getToken(HttpServletRequest request) { - return TokenUtils.getTokenByRequest(request); - } - - @Override - public String getUsername(String token) { - return JwtUtil.getUsername(token); - } - - @Override - public String[] getRoles(String token) { - String username = JwtUtil.getUsername(token); - Set roles = sysBaseApi.getUserRoleSet(username); - if(CollectionUtils.isEmpty(roles)){ - return null; - } - return (String[]) roles.toArray(new String[roles.size()]); - } - - @Override - public Boolean verifyToken(String token) { - return TokenUtils.verifyToken(token, sysBaseApi, redisUtil); - } - - @Override - public Map getUserInfo(String token) { - Map map = new HashMap(5); - String username = JwtUtil.getUsername(token); - //此处通过token只能拿到一个信息 用户账号 后面的就是根据账号获取其他信息 查询数据或是走redis 用户根据自身业务可自定义 - SysUserCacheInfo userInfo = null; - try { - userInfo = sysBaseApi.getCacheUser(username); - } catch (Exception e) { - log.error("获取用户信息异常:"+ e.getMessage()); - return map; - } - //设置账号名 - map.put(SYS_USER_CODE, userInfo.getSysUserCode()); - //设置部门编码 - map.put(SYS_ORG_CODE, userInfo.getSysOrgCode()); - // 将所有信息存放至map 解析sql/api会根据map的键值解析 - return map; - } - - /** - * 将jeecgboot平台的权限传递给积木报表 - * @param token - * @return - */ - @Override - public String[] getPermissions(String token) { - // 获取用户信息 - String username = JwtUtil.getUsername(token); - SysUserCacheInfo userInfo = null; - try { - userInfo = sysBaseApi.getCacheUser(username); - } catch (Exception e) { - log.error("获取用户信息异常:"+ e.getMessage()); - } - if(userInfo == null){ - return null; - } - // 查询权限 - Set userPermissions = sysBaseApi.getUserPermissionSet(userInfo.getSysUserId()); - if(CollectionUtils.isEmpty(userPermissions)){ - return null; - } - return userPermissions.toArray(new String[0]); - } -} +//package org.jeecg.config.jimureport; +// +//import lombok.extern.slf4j.Slf4j; +//import org.jeecg.common.system.util.JwtUtil; +//import org.jeecg.common.system.vo.SysUserCacheInfo; +//import org.jeecg.common.util.RedisUtil; +//import org.jeecg.common.util.TokenUtils; +//import org.jeecg.modules.jmreport.api.JmReportTokenServiceI; +//import org.jeecg.modules.system.service.impl.SysBaseApiImpl; +//import org.springframework.beans.factory.annotation.Autowired; +//import org.springframework.context.annotation.Lazy; +//import org.springframework.stereotype.Component; +//import org.springframework.util.CollectionUtils; +// +//import jakarta.servlet.http.HttpServletRequest; +//import java.util.HashMap; +//import java.util.Map; +//import java.util.Set; +// +///** +// * 自定义积木报表鉴权(如果不进行自定义,则所有请求不做权限控制) +// * * 1.自定义获取登录token +// * * 2.自定义获取登录用户 +// * @author: jeecg-boot +// */ +// +// +//@Slf4j +//@Component +//public class JimuReportTokenService implements JmReportTokenServiceI { +// @Autowired +// private SysBaseApiImpl sysBaseApi; +// @Autowired +// @Lazy +// private RedisUtil redisUtil; +// +// @Override +// public String getToken(HttpServletRequest request) { +// return TokenUtils.getTokenByRequest(request); +// } +// +// @Override +// public String getUsername(String token) { +// return JwtUtil.getUsername(token); +// } +// +// @Override +// public String[] getRoles(String token) { +// String username = JwtUtil.getUsername(token); +// Set roles = sysBaseApi.getUserRoleSet(username); +// if(CollectionUtils.isEmpty(roles)){ +// return null; +// } +// return (String[]) roles.toArray(new String[roles.size()]); +// } +// +// @Override +// public Boolean verifyToken(String token) { +// return TokenUtils.verifyToken(token, sysBaseApi, redisUtil); +// } +// +// @Override +// public Map getUserInfo(String token) { +// Map map = new HashMap(5); +// String username = JwtUtil.getUsername(token); +// //此处通过token只能拿到一个信息 用户账号 后面的就是根据账号获取其他信息 查询数据或是走redis 用户根据自身业务可自定义 +// SysUserCacheInfo userInfo = null; +// try { +// userInfo = sysBaseApi.getCacheUser(username); +// } catch (Exception e) { +// log.error("获取用户信息异常:"+ e.getMessage()); +// return map; +// } +// //设置账号名 +// map.put(SYS_USER_CODE, userInfo.getSysUserCode()); +// //设置部门编码 +// map.put(SYS_ORG_CODE, userInfo.getSysOrgCode()); +// // 将所有信息存放至map 解析sql/api会根据map的键值解析 +// return map; +// } +// +// /** +// * 将jeecgboot平台的权限传递给积木报表 +// * @param token +// * @return +// */ +// @Override +// public String[] getPermissions(String token) { +// // 获取用户信息 +// String username = JwtUtil.getUsername(token); +// SysUserCacheInfo userInfo = null; +// try { +// userInfo = sysBaseApi.getCacheUser(username); +// } catch (Exception e) { +// log.error("获取用户信息异常:"+ e.getMessage()); +// } +// if(userInfo == null){ +// return null; +// } +// // 查询权限 +// Set userPermissions = sysBaseApi.getUserPermissionSet(userInfo.getSysUserId()); +// if(CollectionUtils.isEmpty(userPermissions)){ +// return null; +// } +// return userPermissions.toArray(new String[0]); +// } +//} diff --git a/jeecg-boot/jeecg-module-system/jeecg-system-biz/src/main/java/org/springframework/boot/autoconfigure/mongo/MongoAutoConfiguration.java b/jeecg-boot/jeecg-module-system/jeecg-system-biz/src/main/java/org/springframework/boot/autoconfigure/mongo/MongoAutoConfiguration.java index df0857543..beee8a92a 100644 --- a/jeecg-boot/jeecg-module-system/jeecg-system-biz/src/main/java/org/springframework/boot/autoconfigure/mongo/MongoAutoConfiguration.java +++ b/jeecg-boot/jeecg-module-system/jeecg-system-biz/src/main/java/org/springframework/boot/autoconfigure/mongo/MongoAutoConfiguration.java @@ -1,64 +1,56 @@ +//// +//// Source code recreated from a .class file by IntelliJ IDEA +//// (powered by Fernflower decompiler) +//// // -// Source code recreated from a .class file by IntelliJ IDEA -// (powered by Fernflower decompiler) +//package org.springframework.boot.autoconfigure.mongo; // - -package org.springframework.boot.autoconfigure.mongo; - -import com.mongodb.MongoClientSettings; -import com.mongodb.client.MongoClient; -import org.springframework.beans.factory.ObjectProvider; -import org.springframework.boot.autoconfigure.AutoConfiguration; -import org.springframework.boot.autoconfigure.condition.ConditionalOnClass; -import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean; -import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty; -import org.springframework.boot.autoconfigure.mongo.MongoClientFactory; -import org.springframework.boot.autoconfigure.mongo.MongoClientSettingsBuilderCustomizer; -import org.springframework.boot.autoconfigure.mongo.MongoProperties; -import org.springframework.boot.autoconfigure.mongo.MongoPropertiesClientSettingsBuilderCustomizer; -import org.springframework.boot.context.properties.EnableConfigurationProperties; -import org.springframework.context.annotation.Bean; -import org.springframework.context.annotation.Configuration; -import org.springframework.context.annotation.Primary; -import org.springframework.core.env.Environment; - -import java.util.List; -import java.util.stream.Collectors; - -@Primary -@AutoConfiguration -@ConditionalOnClass({MongoClient.class}) -@ConditionalOnProperty(name = "spring.data.mongodb.uri", havingValue = "", matchIfMissing = false) -@EnableConfigurationProperties({MongoProperties.class}) -@ConditionalOnMissingBean( - type = {"org.springframework.data.mongodb.MongoDatabaseFactory"} -) -public class MongoAutoConfiguration { - public MongoAutoConfiguration() { - } - - @Bean - @ConditionalOnMissingBean({MongoClient.class}) - public MongoClient mongo(ObjectProvider builderCustomizers, MongoClientSettings settings) { - return (MongoClient)(new MongoClientFactory((List)builderCustomizers.orderedStream().collect(Collectors.toList()))).createMongoClient(settings); - } - - @Configuration( - proxyBeanMethods = false - ) - @ConditionalOnMissingBean({MongoClientSettings.class}) - static class MongoClientSettingsConfiguration { - MongoClientSettingsConfiguration() { - } - - @Bean - MongoClientSettings mongoClientSettings() { - return MongoClientSettings.builder().build(); - } - - @Bean - MongoPropertiesClientSettingsBuilderCustomizer mongoPropertiesCustomizer(MongoProperties properties, Environment environment) { - return new MongoPropertiesClientSettingsBuilderCustomizer(properties); - } - } -} \ No newline at end of file +//import com.mongodb.MongoClientSettings; +//import com.mongodb.client.MongoClient; +//import org.springframework.beans.factory.ObjectProvider; +//import org.springframework.boot.autoconfigure.AutoConfiguration; +//import org.springframework.boot.autoconfigure.condition.ConditionalOnClass; +//import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean; +//import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty; +//import org.springframework.boot.context.properties.EnableConfigurationProperties; +//import org.springframework.context.annotation.Bean; +//import org.springframework.context.annotation.Configuration; +//import org.springframework.context.annotation.Primary; +//import org.springframework.core.env.Environment; +// +//import java.util.List; +//import java.util.stream.Collectors; +// +//@Primary +//@AutoConfiguration +//@ConditionalOnClass({MongoClient.class}) +//@ConditionalOnProperty(name = "spring.data.mongodb.uri", havingValue = "", matchIfMissing = false) +//@EnableConfigurationProperties({MongoProperties.class}) +//@ConditionalOnMissingBean( +// type = {"org.springframework.data.mongodb.MongoDatabaseFactory"} +//) +//public class MongoAutoConfiguration { +// public MongoAutoConfiguration() { +// } +// +// @Bean +// @ConditionalOnMissingBean({MongoClient.class}) +// public MongoClient mongo(ObjectProvider builderCustomizers, MongoClientSettings settings) { +// return (MongoClient)(new MongoClientFactory((List)builderCustomizers.orderedStream().collect(Collectors.toList()))).createMongoClient(settings); +// } +// +// @Configuration( +// proxyBeanMethods = false +// ) +// @ConditionalOnMissingBean({MongoClientSettings.class}) +// static class MongoClientSettingsConfiguration { +// MongoClientSettingsConfiguration() { +// } +// +// @Bean +// MongoClientSettings mongoClientSettings() { +// return MongoClientSettings.builder().build(); +// } +// +// } +//} \ No newline at end of file diff --git a/jeecg-boot/pom.xml b/jeecg-boot/pom.xml index 60806d090..cd0cac37d 100644 --- a/jeecg-boot/pom.xml +++ b/jeecg-boot/pom.xml @@ -23,7 +23,7 @@ org.springframework.boot spring-boot-starter-parent - 3.1.5 + 3.4.4 @@ -33,8 +33,8 @@ UTF-8 - 2022.0.4 - 2022.0.0.0 + 2024.0.1 + 2023.0.3.2 2.0.4 2.4.1 @@ -56,7 +56,7 @@ 1.9.4 - 3.5.3.2 + 3.5.11 4.1.3 1.2.24 @@ -79,7 +79,7 @@ - 1.4.12 + From 748331d64985e3392728f147d7c6db26325f18c2 Mon Sep 17 00:00:00 2001 From: EightMonth Date: Tue, 22 Apr 2025 16:00:17 +0800 Subject: [PATCH 02/11] =?UTF-8?q?=E5=A4=84=E7=90=86jsqlparser=E5=85=BC?= =?UTF-8?q?=E5=AE=B9=E9=97=AE=E9=A2=98?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../jeecg-system-biz/pom.xml | 20 +- .../impl/DictTableWhiteListHandlerImpl.java | 95 ++++--- .../JimuDragExternalServiceImpl.java | 248 +++++++++--------- .../jimureport/JimuReportTokenService.java | 214 +++++++-------- 4 files changed, 303 insertions(+), 274 deletions(-) diff --git a/jeecg-boot/jeecg-module-system/jeecg-system-biz/pom.xml b/jeecg-boot/jeecg-module-system/jeecg-system-biz/pom.xml index 84209ffe2..2b5967cc6 100644 --- a/jeecg-boot/jeecg-module-system/jeecg-system-biz/pom.xml +++ b/jeecg-boot/jeecg-module-system/jeecg-system-biz/pom.xml @@ -19,7 +19,7 @@ org.hibernate hibernate-core - @@ -30,19 +30,31 @@ weixin4j - org.jeecgframework.jimureport jimubi-spring-boot3-starter - --> + + + com.github.jsqlparser + jsqlparser + + + diff --git a/jeecg-boot/jeecg-module-system/jeecg-system-biz/src/main/java/org/jeecg/config/firewall/SqlInjection/impl/DictTableWhiteListHandlerImpl.java b/jeecg-boot/jeecg-module-system/jeecg-system-biz/src/main/java/org/jeecg/config/firewall/SqlInjection/impl/DictTableWhiteListHandlerImpl.java index b26dad02d..47003b5a4 100644 --- a/jeecg-boot/jeecg-module-system/jeecg-system-biz/src/main/java/org/jeecg/config/firewall/SqlInjection/impl/DictTableWhiteListHandlerImpl.java +++ b/jeecg-boot/jeecg-module-system/jeecg-system-biz/src/main/java/org/jeecg/config/firewall/SqlInjection/impl/DictTableWhiteListHandlerImpl.java @@ -1,6 +1,11 @@ package org.jeecg.config.firewall.SqlInjection.impl; import lombok.extern.slf4j.Slf4j; +import net.sf.jsqlparser.JSQLParserException; +import net.sf.jsqlparser.parser.CCJSqlParserUtil; +import net.sf.jsqlparser.schema.Table; +import net.sf.jsqlparser.statement.select.PlainSelect; +import net.sf.jsqlparser.statement.select.Select; import org.jeecg.common.constant.SymbolConstant; import org.jeecg.common.exception.JeecgSqlInjectionException; import org.jeecg.common.util.oConvertUtils; @@ -12,8 +17,11 @@ import org.jeecg.config.firewall.interceptor.LowCodeModeInterceptor; import org.jeecg.modules.system.entity.SysTableWhiteList; import org.jeecg.modules.system.security.DictQueryBlackListHandler; import org.jeecg.modules.system.service.ISysTableWhiteListService; +import org.jeecgframework.minidao.sqlparser.AbstractSqlProcessor; +import org.jeecgframework.minidao.sqlparser.impl.JsqlparserSqlProcessor; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Component; +import org.jeecgframework.minidao.util.MiniDaoUtil; import java.net.URLDecoder; import java.util.*; @@ -63,34 +71,42 @@ public class DictTableWhiteListHandlerImpl implements IDictTableWhiteListHandler @Override public boolean isPassBySql(String sql) { -// Map parsedMap = null; -// try { -// parsedMap = JSqlParserUtils.parseAllSelectTable(sql); -// } catch (Exception e) { -// log.warn("校验sql语句,解析报错:{}", e.getMessage()); -// } -// // 如果sql有问题,则肯定执行不了,所以直接返回true -// if (parsedMap == null) { -// return true; -// } -// log.info("获取select sql信息 :{} ", parsedMap); -// // 遍历当前sql中的所有表名,如果有其中一个表或表的字段不在白名单中,则不通过 -// for (Map.Entry entry : parsedMap.entrySet()) { -// SelectSqlInfo sqlInfo = entry.getValue(); -// if (sqlInfo.isSelectAll()) { -// log.warn("查询语句中包含 * 字段,暂时先通过"); -// continue; -// } -// Set queryFields = sqlInfo.getAllRealSelectFields(); -// // 校验表名和字段是否允许查询 -// String tableName = entry.getKey(); -// if (!this.checkWhiteList(tableName, queryFields)) { -// return false; -// } -// } + Select select = null; + + try { + select = (Select) CCJSqlParserUtil.parse(sql, (parser) -> { + parser.withSquareBracketQuotation(true); + }); + } catch (JSQLParserException var10) { + JSQLParserException jsqlParserException = var10; + jsqlParserException.printStackTrace(); + } + + String tableName = ((Table)((PlainSelect)select.getSelectBody()).getFromItem()).getName(); + + List> parsedMap = null; + try { + parsedMap = MiniDaoUtil.parseSqlFields(sql); + } catch (Exception e) { + log.warn("校验sql语句,解析报错:{}", e.getMessage()); + } + // 如果sql有问题,则肯定执行不了,所以直接返回true + if (parsedMap == null) { + return true; + } + log.info("获取select sql信息 :{} ", parsedMap); + // 遍历当前sql中的所有表名,如果有其中一个表或表的字段不在白名单中,则不通过 + if (!this.checkWhiteList(tableName, parsedMap.get(0).keySet())) { + return false; + } return true; } + public static void main(String[] args) { + String sql = "select id,name,page from dual;"; + System.out.println(MiniDaoUtil.parseSqlFields(sql)); + } + @Override public boolean isPassByDict(String dictCodeString) { if (oConvertUtils.isEmpty(dictCodeString)) { @@ -120,21 +136,22 @@ public class DictTableWhiteListHandlerImpl implements IDictTableWhiteListHandler if (oConvertUtils.isEmpty(tableName)) { return true; } -// if (fields == null || fields.length == 0) { -// fields = new String[]{"*"}; -// } -// String sql = "select " + String.join(",", fields) + " from " + tableName; -// log.info("字典拼接的查询SQL:{}", sql); -// try { -// // 进行SQL解析 + if (fields == null || fields.length == 0) { + fields = new String[]{"*"}; + } + String sql = "select " + String.join(",", fields) + " from " + tableName; + log.info("字典拼接的查询SQL:{}", sql); + try { + // 进行SQL解析 + MiniDaoUtil.parseSqlFields(sql); // JSqlParserUtils.parseSelectSqlInfo(sql); -// } catch (Exception e) { -// // 如果SQL解析失败,则通过字段名和表名进行校验 -// return checkWhiteList(tableName, new HashSet<>(Arrays.asList(fields))); -// } -// // 通过SQL解析进行校验,可防止SQL注入 -// return this.isPassBySql(sql); - return true; + } catch (Exception e) { + // 如果SQL解析失败,则通过字段名和表名进行校验 + return checkWhiteList(tableName, new HashSet<>(Arrays.asList(fields))); + } + // 通过SQL解析进行校验,可防止SQL注入 + return this.isPassBySql(sql); +// return true; } /** diff --git a/jeecg-boot/jeecg-module-system/jeecg-system-biz/src/main/java/org/jeecg/config/jimureport/JimuDragExternalServiceImpl.java b/jeecg-boot/jeecg-module-system/jeecg-system-biz/src/main/java/org/jeecg/config/jimureport/JimuDragExternalServiceImpl.java index 1e40a53db..eb865bb5b 100644 --- a/jeecg-boot/jeecg-module-system/jeecg-system-biz/src/main/java/org/jeecg/config/jimureport/JimuDragExternalServiceImpl.java +++ b/jeecg-boot/jeecg-module-system/jeecg-system-biz/src/main/java/org/jeecg/config/jimureport/JimuDragExternalServiceImpl.java @@ -1,124 +1,124 @@ -//package org.jeecg.config.jimureport; -// -//import com.alibaba.fastjson.JSONObject; -//import lombok.extern.slf4j.Slf4j; -//import org.jeecg.common.api.dto.LogDTO; -//import org.jeecg.common.system.api.ISysBaseAPI; -//import org.jeecg.common.system.vo.DictModel; -//import org.jeecg.common.util.oConvertUtils; -//import org.jeecg.modules.base.service.BaseCommonService; -//import org.jeecg.modules.drag.service.IOnlDragExternalService; -//import org.jeecg.modules.drag.vo.DragDictModel; -//import org.jeecg.modules.drag.vo.DragLogDTO; -//import org.springframework.beans.BeanUtils; -//import org.springframework.beans.factory.annotation.Autowired; -//import org.springframework.context.annotation.Lazy; -//import org.springframework.stereotype.Service; -//import org.springframework.util.CollectionUtils; -// -//import java.util.ArrayList; -//import java.util.HashMap; -//import java.util.List; -//import java.util.Map; -// -///** -// * @Description: 字典处理 -// * @Author: lsq -// * @Date:2023-01-09 -// * @Version:V1.0 -// */ -//@Slf4j -//@Service("onlDragExternalServiceImpl") -//public class JimuDragExternalServiceImpl implements IOnlDragExternalService { -// -// @Autowired -// @Lazy -// private BaseCommonService baseCommonService; -// -// @Autowired -// @Lazy -// private ISysBaseAPI sysBaseApi; -// /** -// * 根据多个字典code查询多个字典项 -// * @param codeList -// * @return key = dictCode ; value=对应的字典项 -// */ -// @Override -// public Map> getManyDictItems(List codeList, List tableDictList) { -// Map> manyDragDictItems = new HashMap<>(); -// if(!CollectionUtils.isEmpty(codeList)){ -// Map> dictItemsMap = sysBaseApi.getManyDictItems(codeList); -// dictItemsMap.forEach((k,v)->{ -// List dictItems = new ArrayList<>(); -// v.forEach(dictItem->{ -// DragDictModel dictModel = new DragDictModel(); -// BeanUtils.copyProperties(dictItem,dictModel); -// dictItems.add(dictModel); -// }); -// manyDragDictItems.put(k,dictItems); -// }); -// } -// -// if(!CollectionUtils.isEmpty(tableDictList)){ -// tableDictList.forEach(item->{ -// List dictItems = new ArrayList<>(); -// JSONObject object = JSONObject.parseObject(item.toString()); -// String dictField = object.getString("dictField"); -// String dictTable = object.getString("dictTable"); -// String dictText = object.getString("dictText"); -// String fieldName = object.getString("fieldName"); -// List dictItemsList = sysBaseApi.queryTableDictItemsByCode(dictTable,dictText,dictField); -// dictItemsList.forEach(dictItem->{ -// DragDictModel dictModel = new DragDictModel(); -// BeanUtils.copyProperties(dictItem,dictModel); -// dictItems.add(dictModel); -// }); -// manyDragDictItems.put(fieldName,dictItems); -// }); -// } -// return manyDragDictItems; -// } -// -// /** -// * -// * @param dictCode -// * @return -// */ -// @Override -// public List getDictItems(String dictCode) { -// List dictItems = new ArrayList<>(); -// if(oConvertUtils.isNotEmpty(dictCode)){ -// List dictItemsList = sysBaseApi.getDictItems(dictCode); -// dictItemsList.forEach(dictItem->{ -// DragDictModel dictModel = new DragDictModel(); -// BeanUtils.copyProperties(dictItem,dictModel); -// dictItems.add(dictModel); -// }); -// } -// return dictItems; -// } -// -// /** -// * 添加日志 -// * @param dragLogDTO -// */ -// @Override -// public void addLog(DragLogDTO dragLogDTO) { -// if(oConvertUtils.isNotEmpty(dragLogDTO)){ -// LogDTO dto = new LogDTO(); -// BeanUtils.copyProperties(dragLogDTO,dto); -// baseCommonService.addLog(dto); -// } -// } -// -// /** -// * 保存日志 -// * @param logMsg -// * @param logType -// * @param operateType -// */ -// @Override -// public void addLog(String logMsg, int logType, int operateType) { -// baseCommonService.addLog(logMsg,logType,operateType); -// } -//} \ No newline at end of file +package org.jeecg.config.jimureport; + +import com.alibaba.fastjson.JSONObject; +import lombok.extern.slf4j.Slf4j; +import org.jeecg.common.api.dto.LogDTO; +import org.jeecg.common.system.api.ISysBaseAPI; +import org.jeecg.common.system.vo.DictModel; +import org.jeecg.common.util.oConvertUtils; +import org.jeecg.modules.base.service.BaseCommonService; +import org.jeecg.modules.drag.service.IOnlDragExternalService; +import org.jeecg.modules.drag.vo.DragDictModel; +import org.jeecg.modules.drag.vo.DragLogDTO; +import org.springframework.beans.BeanUtils; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.context.annotation.Lazy; +import org.springframework.stereotype.Service; +import org.springframework.util.CollectionUtils; + +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +/** + * @Description: 字典处理 + * @Author: lsq + * @Date:2023-01-09 + * @Version:V1.0 + */ +@Slf4j +@Service("onlDragExternalServiceImpl") +public class JimuDragExternalServiceImpl implements IOnlDragExternalService { + + @Autowired + @Lazy + private BaseCommonService baseCommonService; + + @Autowired + @Lazy + private ISysBaseAPI sysBaseApi; + /** + * 根据多个字典code查询多个字典项 + * @param codeList + * @return key = dictCode ; value=对应的字典项 + */ + @Override + public Map> getManyDictItems(List codeList, List tableDictList) { + Map> manyDragDictItems = new HashMap<>(); + if(!CollectionUtils.isEmpty(codeList)){ + Map> dictItemsMap = sysBaseApi.getManyDictItems(codeList); + dictItemsMap.forEach((k,v)->{ + List dictItems = new ArrayList<>(); + v.forEach(dictItem->{ + DragDictModel dictModel = new DragDictModel(); + BeanUtils.copyProperties(dictItem,dictModel); + dictItems.add(dictModel); + }); + manyDragDictItems.put(k,dictItems); + }); + } + + if(!CollectionUtils.isEmpty(tableDictList)){ + tableDictList.forEach(item->{ + List dictItems = new ArrayList<>(); + JSONObject object = JSONObject.parseObject(item.toString()); + String dictField = object.getString("dictField"); + String dictTable = object.getString("dictTable"); + String dictText = object.getString("dictText"); + String fieldName = object.getString("fieldName"); + List dictItemsList = sysBaseApi.queryTableDictItemsByCode(dictTable,dictText,dictField); + dictItemsList.forEach(dictItem->{ + DragDictModel dictModel = new DragDictModel(); + BeanUtils.copyProperties(dictItem,dictModel); + dictItems.add(dictModel); + }); + manyDragDictItems.put(fieldName,dictItems); + }); + } + return manyDragDictItems; + } + + /** + * + * @param dictCode + * @return + */ + @Override + public List getDictItems(String dictCode) { + List dictItems = new ArrayList<>(); + if(oConvertUtils.isNotEmpty(dictCode)){ + List dictItemsList = sysBaseApi.getDictItems(dictCode); + dictItemsList.forEach(dictItem->{ + DragDictModel dictModel = new DragDictModel(); + BeanUtils.copyProperties(dictItem,dictModel); + dictItems.add(dictModel); + }); + } + return dictItems; + } + + /** + * 添加日志 + * @param dragLogDTO + */ + @Override + public void addLog(DragLogDTO dragLogDTO) { + if(oConvertUtils.isNotEmpty(dragLogDTO)){ + LogDTO dto = new LogDTO(); + BeanUtils.copyProperties(dragLogDTO,dto); + baseCommonService.addLog(dto); + } + } + + /** + * 保存日志 + * @param logMsg + * @param logType + * @param operateType + */ + @Override + public void addLog(String logMsg, int logType, int operateType) { + baseCommonService.addLog(logMsg,logType,operateType); + } +} \ No newline at end of file diff --git a/jeecg-boot/jeecg-module-system/jeecg-system-biz/src/main/java/org/jeecg/config/jimureport/JimuReportTokenService.java b/jeecg-boot/jeecg-module-system/jeecg-system-biz/src/main/java/org/jeecg/config/jimureport/JimuReportTokenService.java index 279d94708..3fe54d1ad 100644 --- a/jeecg-boot/jeecg-module-system/jeecg-system-biz/src/main/java/org/jeecg/config/jimureport/JimuReportTokenService.java +++ b/jeecg-boot/jeecg-module-system/jeecg-system-biz/src/main/java/org/jeecg/config/jimureport/JimuReportTokenService.java @@ -1,107 +1,107 @@ -//package org.jeecg.config.jimureport; -// -//import lombok.extern.slf4j.Slf4j; -//import org.jeecg.common.system.util.JwtUtil; -//import org.jeecg.common.system.vo.SysUserCacheInfo; -//import org.jeecg.common.util.RedisUtil; -//import org.jeecg.common.util.TokenUtils; -//import org.jeecg.modules.jmreport.api.JmReportTokenServiceI; -//import org.jeecg.modules.system.service.impl.SysBaseApiImpl; -//import org.springframework.beans.factory.annotation.Autowired; -//import org.springframework.context.annotation.Lazy; -//import org.springframework.stereotype.Component; -//import org.springframework.util.CollectionUtils; -// -//import jakarta.servlet.http.HttpServletRequest; -//import java.util.HashMap; -//import java.util.Map; -//import java.util.Set; -// -///** -// * 自定义积木报表鉴权(如果不进行自定义,则所有请求不做权限控制) -// * * 1.自定义获取登录token -// * * 2.自定义获取登录用户 -// * @author: jeecg-boot -// */ -// -// -//@Slf4j -//@Component -//public class JimuReportTokenService implements JmReportTokenServiceI { -// @Autowired -// private SysBaseApiImpl sysBaseApi; -// @Autowired -// @Lazy -// private RedisUtil redisUtil; -// -// @Override -// public String getToken(HttpServletRequest request) { -// return TokenUtils.getTokenByRequest(request); -// } -// -// @Override -// public String getUsername(String token) { -// return JwtUtil.getUsername(token); -// } -// -// @Override -// public String[] getRoles(String token) { -// String username = JwtUtil.getUsername(token); -// Set roles = sysBaseApi.getUserRoleSet(username); -// if(CollectionUtils.isEmpty(roles)){ -// return null; -// } -// return (String[]) roles.toArray(new String[roles.size()]); -// } -// -// @Override -// public Boolean verifyToken(String token) { -// return TokenUtils.verifyToken(token, sysBaseApi, redisUtil); -// } -// -// @Override -// public Map getUserInfo(String token) { -// Map map = new HashMap(5); -// String username = JwtUtil.getUsername(token); -// //此处通过token只能拿到一个信息 用户账号 后面的就是根据账号获取其他信息 查询数据或是走redis 用户根据自身业务可自定义 -// SysUserCacheInfo userInfo = null; -// try { -// userInfo = sysBaseApi.getCacheUser(username); -// } catch (Exception e) { -// log.error("获取用户信息异常:"+ e.getMessage()); -// return map; -// } -// //设置账号名 -// map.put(SYS_USER_CODE, userInfo.getSysUserCode()); -// //设置部门编码 -// map.put(SYS_ORG_CODE, userInfo.getSysOrgCode()); -// // 将所有信息存放至map 解析sql/api会根据map的键值解析 -// return map; -// } -// -// /** -// * 将jeecgboot平台的权限传递给积木报表 -// * @param token -// * @return -// */ -// @Override -// public String[] getPermissions(String token) { -// // 获取用户信息 -// String username = JwtUtil.getUsername(token); -// SysUserCacheInfo userInfo = null; -// try { -// userInfo = sysBaseApi.getCacheUser(username); -// } catch (Exception e) { -// log.error("获取用户信息异常:"+ e.getMessage()); -// } -// if(userInfo == null){ -// return null; -// } -// // 查询权限 -// Set userPermissions = sysBaseApi.getUserPermissionSet(userInfo.getSysUserId()); -// if(CollectionUtils.isEmpty(userPermissions)){ -// return null; -// } -// return userPermissions.toArray(new String[0]); -// } -//} +package org.jeecg.config.jimureport; + +import lombok.extern.slf4j.Slf4j; +import org.jeecg.common.system.util.JwtUtil; +import org.jeecg.common.system.vo.SysUserCacheInfo; +import org.jeecg.common.util.RedisUtil; +import org.jeecg.common.util.TokenUtils; +import org.jeecg.modules.jmreport.api.JmReportTokenServiceI; +import org.jeecg.modules.system.service.impl.SysBaseApiImpl; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.context.annotation.Lazy; +import org.springframework.stereotype.Component; +import org.springframework.util.CollectionUtils; + +import jakarta.servlet.http.HttpServletRequest; +import java.util.HashMap; +import java.util.Map; +import java.util.Set; + +/** + * 自定义积木报表鉴权(如果不进行自定义,则所有请求不做权限控制) + * * 1.自定义获取登录token + * * 2.自定义获取登录用户 + * @author: jeecg-boot + */ + + +@Slf4j +@Component +public class JimuReportTokenService implements JmReportTokenServiceI { + @Autowired + private SysBaseApiImpl sysBaseApi; + @Autowired + @Lazy + private RedisUtil redisUtil; + + @Override + public String getToken(HttpServletRequest request) { + return TokenUtils.getTokenByRequest(request); + } + + @Override + public String getUsername(String token) { + return JwtUtil.getUsername(token); + } + + @Override + public String[] getRoles(String token) { + String username = JwtUtil.getUsername(token); + Set roles = sysBaseApi.getUserRoleSet(username); + if(CollectionUtils.isEmpty(roles)){ + return null; + } + return (String[]) roles.toArray(new String[roles.size()]); + } + + @Override + public Boolean verifyToken(String token) { + return TokenUtils.verifyToken(token, sysBaseApi, redisUtil); + } + + @Override + public Map getUserInfo(String token) { + Map map = new HashMap(5); + String username = JwtUtil.getUsername(token); + //此处通过token只能拿到一个信息 用户账号 后面的就是根据账号获取其他信息 查询数据或是走redis 用户根据自身业务可自定义 + SysUserCacheInfo userInfo = null; + try { + userInfo = sysBaseApi.getCacheUser(username); + } catch (Exception e) { + log.error("获取用户信息异常:"+ e.getMessage()); + return map; + } + //设置账号名 + map.put(SYS_USER_CODE, userInfo.getSysUserCode()); + //设置部门编码 + map.put(SYS_ORG_CODE, userInfo.getSysOrgCode()); + // 将所有信息存放至map 解析sql/api会根据map的键值解析 + return map; + } + + /** + * 将jeecgboot平台的权限传递给积木报表 + * @param token + * @return + */ + @Override + public String[] getPermissions(String token) { + // 获取用户信息 + String username = JwtUtil.getUsername(token); + SysUserCacheInfo userInfo = null; + try { + userInfo = sysBaseApi.getCacheUser(username); + } catch (Exception e) { + log.error("获取用户信息异常:"+ e.getMessage()); + } + if(userInfo == null){ + return null; + } + // 查询权限 + Set userPermissions = sysBaseApi.getUserPermissionSet(userInfo.getSysUserId()); + if(CollectionUtils.isEmpty(userPermissions)){ + return null; + } + return userPermissions.toArray(new String[0]); + } +} From f78eabfc66bff8fb6f183e0fb362eacaf145d400 Mon Sep 17 00:00:00 2001 From: EightMonth Date: Fri, 25 Apr 2025 16:54:55 +0800 Subject: [PATCH 03/11] =?UTF-8?q?=E4=BD=BF=E7=94=A8minidao=E9=80=82?= =?UTF-8?q?=E9=85=8Djsqlparser?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../impl/DictTableWhiteListHandlerImpl.java | 13 +-- .../mongo/MongoAutoConfiguration.java | 108 +++++++++--------- 2 files changed, 55 insertions(+), 66 deletions(-) diff --git a/jeecg-boot/jeecg-module-system/jeecg-system-biz/src/main/java/org/jeecg/config/firewall/SqlInjection/impl/DictTableWhiteListHandlerImpl.java b/jeecg-boot/jeecg-module-system/jeecg-system-biz/src/main/java/org/jeecg/config/firewall/SqlInjection/impl/DictTableWhiteListHandlerImpl.java index 47003b5a4..d71b0d137 100644 --- a/jeecg-boot/jeecg-module-system/jeecg-system-biz/src/main/java/org/jeecg/config/firewall/SqlInjection/impl/DictTableWhiteListHandlerImpl.java +++ b/jeecg-boot/jeecg-module-system/jeecg-system-biz/src/main/java/org/jeecg/config/firewall/SqlInjection/impl/DictTableWhiteListHandlerImpl.java @@ -71,18 +71,7 @@ public class DictTableWhiteListHandlerImpl implements IDictTableWhiteListHandler @Override public boolean isPassBySql(String sql) { - Select select = null; - - try { - select = (Select) CCJSqlParserUtil.parse(sql, (parser) -> { - parser.withSquareBracketQuotation(true); - }); - } catch (JSQLParserException var10) { - JSQLParserException jsqlParserException = var10; - jsqlParserException.printStackTrace(); - } - - String tableName = ((Table)((PlainSelect)select.getSelectBody()).getFromItem()).getName(); + String tableName = MiniDaoUtil.parseTable(sql); List> parsedMap = null; try { diff --git a/jeecg-boot/jeecg-module-system/jeecg-system-biz/src/main/java/org/springframework/boot/autoconfigure/mongo/MongoAutoConfiguration.java b/jeecg-boot/jeecg-module-system/jeecg-system-biz/src/main/java/org/springframework/boot/autoconfigure/mongo/MongoAutoConfiguration.java index beee8a92a..7b8fd4c58 100644 --- a/jeecg-boot/jeecg-module-system/jeecg-system-biz/src/main/java/org/springframework/boot/autoconfigure/mongo/MongoAutoConfiguration.java +++ b/jeecg-boot/jeecg-module-system/jeecg-system-biz/src/main/java/org/springframework/boot/autoconfigure/mongo/MongoAutoConfiguration.java @@ -1,56 +1,56 @@ -//// -//// Source code recreated from a .class file by IntelliJ IDEA -//// (powered by Fernflower decompiler) -//// // -//package org.springframework.boot.autoconfigure.mongo; +// Source code recreated from a .class file by IntelliJ IDEA +// (powered by Fernflower decompiler) // -//import com.mongodb.MongoClientSettings; -//import com.mongodb.client.MongoClient; -//import org.springframework.beans.factory.ObjectProvider; -//import org.springframework.boot.autoconfigure.AutoConfiguration; -//import org.springframework.boot.autoconfigure.condition.ConditionalOnClass; -//import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean; -//import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty; -//import org.springframework.boot.context.properties.EnableConfigurationProperties; -//import org.springframework.context.annotation.Bean; -//import org.springframework.context.annotation.Configuration; -//import org.springframework.context.annotation.Primary; -//import org.springframework.core.env.Environment; -// -//import java.util.List; -//import java.util.stream.Collectors; -// -//@Primary -//@AutoConfiguration -//@ConditionalOnClass({MongoClient.class}) -//@ConditionalOnProperty(name = "spring.data.mongodb.uri", havingValue = "", matchIfMissing = false) -//@EnableConfigurationProperties({MongoProperties.class}) -//@ConditionalOnMissingBean( -// type = {"org.springframework.data.mongodb.MongoDatabaseFactory"} -//) -//public class MongoAutoConfiguration { -// public MongoAutoConfiguration() { -// } -// -// @Bean -// @ConditionalOnMissingBean({MongoClient.class}) -// public MongoClient mongo(ObjectProvider builderCustomizers, MongoClientSettings settings) { -// return (MongoClient)(new MongoClientFactory((List)builderCustomizers.orderedStream().collect(Collectors.toList()))).createMongoClient(settings); -// } -// -// @Configuration( -// proxyBeanMethods = false -// ) -// @ConditionalOnMissingBean({MongoClientSettings.class}) -// static class MongoClientSettingsConfiguration { -// MongoClientSettingsConfiguration() { -// } -// -// @Bean -// MongoClientSettings mongoClientSettings() { -// return MongoClientSettings.builder().build(); -// } -// -// } -//} \ No newline at end of file + +package org.springframework.boot.autoconfigure.mongo; + +import com.mongodb.MongoClientSettings; +import com.mongodb.client.MongoClient; +import org.springframework.beans.factory.ObjectProvider; +import org.springframework.boot.autoconfigure.AutoConfiguration; +import org.springframework.boot.autoconfigure.condition.ConditionalOnClass; +import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean; +import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty; +import org.springframework.boot.context.properties.EnableConfigurationProperties; +import org.springframework.context.annotation.Bean; +import org.springframework.context.annotation.Configuration; +import org.springframework.context.annotation.Primary; +import org.springframework.core.env.Environment; + +import java.util.List; +import java.util.stream.Collectors; + +@Primary +@AutoConfiguration +@ConditionalOnClass({MongoClient.class}) +@ConditionalOnProperty(name = "spring.data.mongodb.uri", havingValue = "", matchIfMissing = false) +@EnableConfigurationProperties({MongoProperties.class}) +@ConditionalOnMissingBean( + type = {"org.springframework.data.mongodb.MongoDatabaseFactory"} +) +public class MongoAutoConfiguration { + public MongoAutoConfiguration() { + } + + @Bean + @ConditionalOnMissingBean({MongoClient.class}) + public MongoClient mongo(ObjectProvider builderCustomizers, MongoClientSettings settings) { + return (MongoClient)(new MongoClientFactory((List)builderCustomizers.orderedStream().collect(Collectors.toList()))).createMongoClient(settings); + } + + @Configuration( + proxyBeanMethods = false + ) + @ConditionalOnMissingBean({MongoClientSettings.class}) + static class MongoClientSettingsConfiguration { + MongoClientSettingsConfiguration() { + } + + @Bean + MongoClientSettings mongoClientSettings() { + return MongoClientSettings.builder().build(); + } + + } +} \ No newline at end of file From 309c76d2688f1920a1f82977d9d909fbcba33596 Mon Sep 17 00:00:00 2001 From: EightMonth Date: Fri, 25 Apr 2025 18:08:45 +0800 Subject: [PATCH 04/11] =?UTF-8?q?=E4=BF=AE=E5=A4=8Dswagger=E6=8E=A5?= =?UTF-8?q?=E5=8F=A3=E6=96=87=E6=A1=A3=E6=AD=A3=E5=B8=B8=E6=98=BE=E7=A4=BA?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- jeecg-boot/jeecg-boot-base-core/pom.xml | 13 ++++++++++++- .../src/main/resources/static/favicon.ico | 0 2 files changed, 12 insertions(+), 1 deletion(-) create mode 100644 jeecg-boot/jeecg-boot-base-core/src/main/resources/static/favicon.ico diff --git a/jeecg-boot/jeecg-boot-base-core/pom.xml b/jeecg-boot/jeecg-boot-base-core/pom.xml index ba0bda318..d286f8e87 100644 --- a/jeecg-boot/jeecg-boot-base-core/pom.xml +++ b/jeecg-boot/jeecg-boot-base-core/pom.xml @@ -278,10 +278,21 @@ - + + + + com.github.xiaoymin + knife4j-openapi3-ui + ${knife4j-spring-boot-starter.version} + + + org.springdoc + springdoc-openapi-starter-webmvc-ui + 2.7.0 diff --git a/jeecg-boot/jeecg-boot-base-core/src/main/resources/static/favicon.ico b/jeecg-boot/jeecg-boot-base-core/src/main/resources/static/favicon.ico new file mode 100644 index 000000000..e69de29bb From 888a032266d7bf67d7060577b5d5419bcbe30ef7 Mon Sep 17 00:00:00 2001 From: EightMonth Date: Wed, 30 Apr 2025 10:00:02 +0800 Subject: [PATCH 05/11] =?UTF-8?q?=E4=BC=98=E5=8C=96bean=E6=97=A0=E6=B3=95?= =?UTF-8?q?=E8=A2=AB=E6=89=80=E6=9C=89beanpostprocessor=E5=A4=84=E7=90=86?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../src/main/java/org/jeecg/config/JeecgBaseConfig.java | 4 ++++ .../src/main/java/org/jeecg/config/shiro/ShiroConfig.java | 1 + .../src/main/java/org/jeecg/config/shiro/ShiroRealm.java | 3 +++ 3 files changed, 8 insertions(+) diff --git a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/config/JeecgBaseConfig.java b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/config/JeecgBaseConfig.java index 52ab417a4..59b84f45b 100644 --- a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/config/JeecgBaseConfig.java +++ b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/config/JeecgBaseConfig.java @@ -1,7 +1,10 @@ package org.jeecg.config; import org.jeecg.config.vo.*; +import org.springframework.beans.factory.config.BeanDefinition; import org.springframework.boot.context.properties.ConfigurationProperties; +import org.springframework.context.annotation.Bean; +import org.springframework.context.annotation.Role; import org.springframework.stereotype.Component; @@ -11,6 +14,7 @@ import org.springframework.stereotype.Component; */ @Component("jeecgBaseConfig") @ConfigurationProperties(prefix = "jeecg") +@Role(BeanDefinition.ROLE_INFRASTRUCTURE) public class JeecgBaseConfig { /** * 签名密钥串(字典等敏感接口) diff --git a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/config/shiro/ShiroConfig.java b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/config/shiro/ShiroConfig.java index d4a408aa3..877662fce 100644 --- a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/config/shiro/ShiroConfig.java +++ b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/config/shiro/ShiroConfig.java @@ -46,6 +46,7 @@ import java.util.*; @Slf4j @Configuration +@Role(BeanDefinition.ROLE_INFRASTRUCTURE) public class ShiroConfig { @Resource diff --git a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/config/shiro/ShiroRealm.java b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/config/shiro/ShiroRealm.java index 78b79361c..ae250b518 100644 --- a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/config/shiro/ShiroRealm.java +++ b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/config/shiro/ShiroRealm.java @@ -20,7 +20,9 @@ import org.jeecg.common.util.SpringContextUtils; import org.jeecg.common.util.TokenUtils; import org.jeecg.common.util.oConvertUtils; import org.jeecg.config.mybatis.MybatisPlusSaasConfig; +import org.springframework.beans.factory.config.BeanDefinition; import org.springframework.context.annotation.Lazy; +import org.springframework.context.annotation.Role; import org.springframework.stereotype.Component; import jakarta.annotation.Resource; @@ -35,6 +37,7 @@ import java.util.Set; */ @Component @Slf4j +@Role(BeanDefinition.ROLE_INFRASTRUCTURE) public class ShiroRealm extends AuthorizingRealm { @Lazy @Resource From 8a82141c957d040a3573c41cdbac9a899f7a0d41 Mon Sep 17 00:00:00 2001 From: JEECG <445654970@qq.com> Date: Thu, 8 May 2025 16:47:46 +0800 Subject: [PATCH 06/11] =?UTF-8?q?=E5=8D=87=E7=BA=A7jsqlparser=E5=88=B04.9?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- jeecg-boot/jeecg-boot-base-core/pom.xml | 59 ++++++++----------- .../impl/DictTableWhiteListHandlerImpl.java | 41 ++++++------- jeecg-boot/pom.xml | 30 ++++++++-- 3 files changed, 66 insertions(+), 64 deletions(-) diff --git a/jeecg-boot/jeecg-boot-base-core/pom.xml b/jeecg-boot/jeecg-boot-base-core/pom.xml index d286f8e87..e86532475 100644 --- a/jeecg-boot/jeecg-boot-base-core/pom.xml +++ b/jeecg-boot/jeecg-boot-base-core/pom.xml @@ -117,13 +117,14 @@ com.baomidou - - mybatis-plus-jsqlparser - - + mybatis-plus-jsqlparser-4.9 ${mybatis-plus.version} - + + + org.jeecgframework.boot3 + minidao-spring-boot-starter-jsqlparser-4.9 + com.alibaba @@ -199,8 +200,7 @@ java-jwt ${java-jwt.version} - - + org.apache.shiro shiro-spring-boot-starter @@ -212,34 +212,6 @@ - - - org.crazycake - shiro-redis - ${shiro-redis.version} - - - org.apache.shiro - shiro-core - - - checkstyle - com.puppycrawl.tools - - - - jedis - redis.clients - - - - - - redis.clients - jedis - ${jedis.version} - - org.apache.shiro shiro-spring @@ -257,7 +229,6 @@ - org.apache.shiro shiro-core @@ -276,6 +247,22 @@ + + + org.crazycake + shiro-redis + ${shiro-redis.version} + + + org.apache.shiro + shiro-core + + + checkstyle + com.puppycrawl.tools + + + 1.9.4 + 1.10.7 + 3.5.11 4.1.3 @@ -65,9 +67,9 @@ 2.1.0 3.17.3 - 1.12.0 + 1.13.0 + 3.2.3 3.11.0 - 3.2.2 1.4.9 1.4.11 8.5.7 @@ -384,7 +386,7 @@ org.jeecgframework weixin4j - 2.0.0 + 2.0.4 commons-beanutils @@ -422,6 +424,10 @@ druid com.alibaba + + org.jeecgframework.boot3 + minidao-spring-boot-starter + @@ -435,6 +441,22 @@ + + + org.jeecgframework.boot3 + minidao-spring-boot-starter-jsqlparser-4.9 + ${minidao.version} + + + druid + com.alibaba + + + jsqlparser + com.github.jsqlparser + + + org.jeecgframework.jimureport From 1e259c805e83070025ca7b0595d2a40da8b47a58 Mon Sep 17 00:00:00 2001 From: JEECG <445654970@qq.com> Date: Thu, 8 May 2025 22:39:57 +0800 Subject: [PATCH 07/11] =?UTF-8?q?fastjson=E5=8D=87=E7=BA=A7=E5=88=B02.0.57?= =?UTF-8?q?=EF=BC=9Bjimureport=E5=8D=87=E7=BA=A7=E5=88=B01.9.5=EF=BC=9Bmin?= =?UTF-8?q?idao=E5=8D=87=E7=BA=A7=E5=88=B01.10.8?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- jeecg-boot/pom.xml | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/jeecg-boot/pom.xml b/jeecg-boot/pom.xml index f9b8819d8..9f8512f29 100644 --- a/jeecg-boot/pom.xml +++ b/jeecg-boot/pom.xml @@ -38,7 +38,7 @@ 2.0.4 2.4.1 - 2.0.43 + 2.0.57 5.2.6 1.6.0 0.17.0 @@ -54,8 +54,8 @@ 8.1.1.49 - 1.9.4 - 1.10.7 + 1.9.5 + 1.10.8 3.5.11 @@ -433,7 +433,7 @@ org.jeecgframework.jimureport jimureport-nosql-starter - 1.9.4.1 + 1.9.5.2 org.apache.calcite From 56fbc2ed8f610d33033403593fc761807c12bebe Mon Sep 17 00:00:00 2001 From: MuShan Date: Tue, 13 May 2025 22:48:48 +0800 Subject: [PATCH 08/11] =?UTF-8?q?feat:=20=E5=8D=87=E7=BA=A7=20shiro=20?= =?UTF-8?q?=E5=88=B0=202.0.4=20=E7=89=88=E6=9C=AC=EF=BC=8C=E8=A7=A3?= =?UTF-8?q?=E5=86=B3Shiro=E8=8E=B7=E5=8F=96=20requestMappingHandlerMapping?= =?UTF-8?q?=20=E6=97=B6=20spring-boot-autoconfigure:3.4.5=20=E5=92=8C=20sp?= =?UTF-8?q?ring-boot-actuator-autoconfigure:3.4.5=20Bean=20=E4=BE=9D?= =?UTF-8?q?=E8=B5=96=E5=86=B2=E7=AA=81=EF=BC=8C?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- jeecg-boot/jeecg-boot-base-core/pom.xml | 1 + .../util/encryption/AesEncryptUtil.java | 2 +- .../org/jeecg/config/shiro/ShiroConfig.java | 25 +++++++++++++------ jeecg-boot/pom.xml | 2 +- 4 files changed, 20 insertions(+), 10 deletions(-) diff --git a/jeecg-boot/jeecg-boot-base-core/pom.xml b/jeecg-boot/jeecg-boot-base-core/pom.xml index e86532475..17ead3b53 100644 --- a/jeecg-boot/jeecg-boot-base-core/pom.xml +++ b/jeecg-boot/jeecg-boot-base-core/pom.xml @@ -204,6 +204,7 @@ org.apache.shiro shiro-spring-boot-starter + jakarta ${shiro.version} diff --git a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/encryption/AesEncryptUtil.java b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/encryption/AesEncryptUtil.java index 670f3ebd6..6a4db4215 100644 --- a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/encryption/AesEncryptUtil.java +++ b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/encryption/AesEncryptUtil.java @@ -1,6 +1,6 @@ package org.jeecg.common.util.encryption; -import org.apache.shiro.codec.Base64; +import org.apache.shiro.lang.codec.Base64; import javax.crypto.Cipher; import javax.crypto.spec.IvParameterSpec; diff --git a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/config/shiro/ShiroConfig.java b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/config/shiro/ShiroConfig.java index 877662fce..e46ce9bc7 100644 --- a/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/config/shiro/ShiroConfig.java +++ b/jeecg-boot/jeecg-boot-base-core/src/main/java/org/jeecg/config/shiro/ShiroConfig.java @@ -1,5 +1,8 @@ package org.jeecg.config.shiro; +import jakarta.annotation.Resource; +import jakarta.servlet.DispatcherType; +import jakarta.servlet.Filter; import lombok.extern.slf4j.Slf4j; import org.apache.commons.pool2.impl.GenericObjectPoolConfig; import org.apache.shiro.mgt.DefaultSessionStorageEvaluator; @@ -17,25 +20,20 @@ import org.jeecg.config.shiro.filters.CustomShiroFilterFactoryBean; import org.jeecg.config.shiro.filters.JwtFilter; import org.springframework.aop.framework.autoproxy.DefaultAdvisorAutoProxyCreator; import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.beans.factory.annotation.Qualifier; import org.springframework.beans.factory.config.BeanDefinition; +import org.springframework.boot.autoconfigure.data.redis.RedisProperties; import org.springframework.boot.web.servlet.FilterRegistrationBean; import org.springframework.context.annotation.*; -import org.springframework.core.annotation.AnnotationUtils; import org.springframework.core.env.Environment; -import org.springframework.core.type.filter.AnnotationTypeFilter; import org.springframework.data.redis.connection.lettuce.LettuceConnectionFactory; -import org.springframework.boot.autoconfigure.data.redis.RedisProperties; import org.springframework.util.CollectionUtils; import org.springframework.util.StringUtils; -import org.springframework.web.bind.annotation.*; import org.springframework.web.filter.DelegatingFilterProxy; +import org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping; import redis.clients.jedis.HostAndPort; import redis.clients.jedis.JedisCluster; -import jakarta.annotation.Resource; -import jakarta.servlet.Filter; -import jakarta.servlet.DispatcherType; -import java.lang.reflect.Method; import java.util.*; /** @@ -350,6 +348,17 @@ public class ShiroConfig { return manager; } + /** + * 解决 ShiroRequestMappingConfig 获取 requestMappingHandlerMapping Bean 冲突 + * spring-boot-autoconfigure:3.4.5 和 spring-boot-actuator-autoconfigure:3.4.5 + */ + @Primary + @Bean + public RequestMappingHandlerMapping shiroRequestMappingHandlerMapping( + @Qualifier("requestMappingHandlerMapping") RequestMappingHandlerMapping handlerMapping) { + return handlerMapping; + } + private List rebuildUrl(String[] bases, String[] uris) { List urls = new ArrayList<>(); for (String base : bases) { diff --git a/jeecg-boot/pom.xml b/jeecg-boot/pom.xml index 9f8512f29..fba760f04 100644 --- a/jeecg-boot/pom.xml +++ b/jeecg-boot/pom.xml @@ -67,7 +67,7 @@ 2.1.0 3.17.3 - 1.13.0 + 2.0.4 3.2.3 3.11.0 1.4.9 From 68f36cb1e5d92e2ec7c48a7a3828fcdf0c557438 Mon Sep 17 00:00:00 2001 From: JEECG <445654970@qq.com> Date: Wed, 14 May 2025 13:59:56 +0800 Subject: [PATCH 09/11] =?UTF-8?q?=E5=8D=87=E7=BA=A7online?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- jeecg-boot/jeecg-module-system/jeecg-system-biz/pom.xml | 4 ++-- jeecg-boot/pom.xml | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/jeecg-boot/jeecg-module-system/jeecg-system-biz/pom.xml b/jeecg-boot/jeecg-module-system/jeecg-system-biz/pom.xml index 2b5967cc6..d0dc97162 100644 --- a/jeecg-boot/jeecg-module-system/jeecg-system-biz/pom.xml +++ b/jeecg-boot/jeecg-module-system/jeecg-system-biz/pom.xml @@ -19,10 +19,10 @@ org.hibernate hibernate-core - + diff --git a/jeecg-boot/pom.xml b/jeecg-boot/pom.xml index 9f8512f29..80287994f 100644 --- a/jeecg-boot/pom.xml +++ b/jeecg-boot/pom.xml @@ -55,7 +55,7 @@ 1.9.5 - 1.10.8 + 1.10.9 3.5.11 @@ -257,7 +257,7 @@ org.jeecgframework.boot3 hibernate-re - 3.7.1-RC + 3.8.0-beta From 70cec8b5c619fcea6aedee52a52e206ab4503f2c Mon Sep 17 00:00:00 2001 From: MuShan Date: Fri, 16 May 2025 22:29:00 +0800 Subject: [PATCH 10/11] =?UTF-8?q?logging(level):=20=E8=AE=BE=E7=BD=AE=20Po?= =?UTF-8?q?stProcessorRegistrationDelegate=20=E6=97=A5=E5=BF=97=E7=BA=A7?= =?UTF-8?q?=E5=88=AB=E4=B8=BA=20error?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - 在 application-dev.yml 文件中添加了 org.springframework.context.support.PostProcessorRegistrationDelegate 的日志级别配置 - 此修改旨在减少不必要的日志输出,提高日志的可读性和性能 --- .../jeecg-system-start/src/main/resources/application-dev.yml | 1 + 1 file changed, 1 insertion(+) diff --git a/jeecg-boot/jeecg-module-system/jeecg-system-start/src/main/resources/application-dev.yml b/jeecg-boot/jeecg-module-system/jeecg-system-start/src/main/resources/application-dev.yml index 045658f52..530868ebb 100644 --- a/jeecg-boot/jeecg-module-system/jeecg-system-start/src/main/resources/application-dev.yml +++ b/jeecg-boot/jeecg-module-system/jeecg-system-start/src/main/resources/application-dev.yml @@ -306,6 +306,7 @@ logging: level: org.flywaydb: debug org.jeecg.modules.system.mapper: info + org.springframework.context.support.PostProcessorRegistrationDelegate: error knife4j: #开启增强配置 enable: true From e52538d304081b772adb9ede2c32c43432ffb403 Mon Sep 17 00:00:00 2001 From: JEECG <445654970@qq.com> Date: Sun, 18 May 2025 16:40:55 +0800 Subject: [PATCH 11/11] =?UTF-8?q?=E5=8D=87=E7=BA=A7spring3.4.5=E5=90=8E?= =?UTF-8?q?=EF=BC=8C=E4=BC=9A=E6=9C=89=E5=BE=88=E5=A4=9A=E8=AD=A6=E5=91=8A?= =?UTF-8?q?BeanPostProcessorChecker:437=20-=20Bean=20'org.springframework.?= =?UTF-8?q?boot.autoconfigure.data.redis.RedisAutoConfiguration'=20of=20ty?= =?UTF-8?q?pe=20[org.springframework.boot.autoconfigure.data.redis.RedisAu?= =?UTF-8?q?toConfiguration]=20is=20not=20eligible=20for=20getting=20proces?= =?UTF-8?q?sed=20by=20all=20BeanPostProcessors=20(for=20example:=20not=20e?= =?UTF-8?q?ligible=20for=20auto-proxying).=20Is=20this=20bean=20getting=20?= =?UTF-8?q?eagerly=20injected/applied=20to=20a=20currently=20created=20Bea?= =?UTF-8?q?nPostProcessor=20[defaultAdvisorAutoProxyCreator]=3F=20Check=20?= =?UTF-8?q?the=20corresponding=20BeanPostProcessor=20declaration=20and=20i?= =?UTF-8?q?ts=20dependencies/advisors.=20If=20this=20bean=20does=20not=20h?= =?UTF-8?q?ave=20to=20be=20post-processed,=20declare=20it=20with=20ROLE=5F?= =?UTF-8?q?INFRASTRUCTURE.?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../jeecg-system-start/src/main/resources/application-dev.yml | 2 +- .../jeecg-system-start/src/main/resources/application-dm8.yml | 1 + .../src/main/resources/application-kingbase8.yml | 1 + .../jeecg-system-start/src/main/resources/application-prod.yml | 1 + .../jeecg-system-start/src/main/resources/application-test.yml | 1 + 5 files changed, 5 insertions(+), 1 deletion(-) diff --git a/jeecg-boot/jeecg-module-system/jeecg-system-start/src/main/resources/application-dev.yml b/jeecg-boot/jeecg-module-system/jeecg-system-start/src/main/resources/application-dev.yml index 530868ebb..41d784f98 100644 --- a/jeecg-boot/jeecg-module-system/jeecg-system-start/src/main/resources/application-dev.yml +++ b/jeecg-boot/jeecg-module-system/jeecg-system-start/src/main/resources/application-dev.yml @@ -304,9 +304,9 @@ cas: #Mybatis输出sql日志 logging: level: + org.springframework.context.support.PostProcessorRegistrationDelegate: error org.flywaydb: debug org.jeecg.modules.system.mapper: info - org.springframework.context.support.PostProcessorRegistrationDelegate: error knife4j: #开启增强配置 enable: true diff --git a/jeecg-boot/jeecg-module-system/jeecg-system-start/src/main/resources/application-dm8.yml b/jeecg-boot/jeecg-module-system/jeecg-system-start/src/main/resources/application-dm8.yml index abafede67..39738ffb8 100644 --- a/jeecg-boot/jeecg-module-system/jeecg-system-start/src/main/resources/application-dm8.yml +++ b/jeecg-boot/jeecg-module-system/jeecg-system-start/src/main/resources/application-dm8.yml @@ -242,6 +242,7 @@ cas: #Mybatis输出sql日志 logging: level: + org.springframework.context.support.PostProcessorRegistrationDelegate: error org.flywaydb: debug org.jeecg.modules.system.mapper: info #swagger diff --git a/jeecg-boot/jeecg-module-system/jeecg-system-start/src/main/resources/application-kingbase8.yml b/jeecg-boot/jeecg-module-system/jeecg-system-start/src/main/resources/application-kingbase8.yml index e6945c051..c6829f873 100644 --- a/jeecg-boot/jeecg-module-system/jeecg-system-start/src/main/resources/application-kingbase8.yml +++ b/jeecg-boot/jeecg-module-system/jeecg-system-start/src/main/resources/application-kingbase8.yml @@ -256,6 +256,7 @@ cas: #Mybatis输出sql日志 logging: level: + org.springframework.context.support.PostProcessorRegistrationDelegate: error org.flywaydb: debug org.jeecg.modules.system.mapper: info #swagger diff --git a/jeecg-boot/jeecg-module-system/jeecg-system-start/src/main/resources/application-prod.yml b/jeecg-boot/jeecg-module-system/jeecg-system-start/src/main/resources/application-prod.yml index 525e86256..62a659ab1 100644 --- a/jeecg-boot/jeecg-module-system/jeecg-system-start/src/main/resources/application-prod.yml +++ b/jeecg-boot/jeecg-module-system/jeecg-system-start/src/main/resources/application-prod.yml @@ -305,6 +305,7 @@ cas: #Mybatis输出sql日志 logging: level: + org.springframework.context.support.PostProcessorRegistrationDelegate: error org.flywaydb: debug org.jeecg.modules.system.mapper: info #swagger diff --git a/jeecg-boot/jeecg-module-system/jeecg-system-start/src/main/resources/application-test.yml b/jeecg-boot/jeecg-module-system/jeecg-system-start/src/main/resources/application-test.yml index a07d01af0..b6d43593a 100644 --- a/jeecg-boot/jeecg-module-system/jeecg-system-start/src/main/resources/application-test.yml +++ b/jeecg-boot/jeecg-module-system/jeecg-system-start/src/main/resources/application-test.yml @@ -301,6 +301,7 @@ jeecg: #Mybatis输出sql日志 logging: level: + org.springframework.context.support.PostProcessorRegistrationDelegate: error org.flywaydb: debug org.jeecg.modules.system.mapper: info #cas单点登录