From cd11c659530ea08bd8919b49b70925968159d457 Mon Sep 17 00:00:00 2001 From: niyan Date: Sun, 7 Apr 2024 19:25:18 +0800 Subject: [PATCH 1/4] feat: support sqlParse --- arex-instrumentation-api/pom.xml | 1 - arex-third-party/pom.xml | 12 + .../thirdparty/util/JacksonHelperUtil.java | 23 + .../thirdparty/util/parse/sqlparse/Parse.java | 13 + .../util/parse/sqlparse/SqlParse.java | 26 + .../parse/sqlparse/action/ActionFactory.java | 37 ++ .../parse/sqlparse/action/DeleteParse.java | 47 ++ .../parse/sqlparse/action/ExecuteParse.java | 36 ++ .../parse/sqlparse/action/InsertParse.java | 37 ++ .../parse/sqlparse/action/ReplaceParse.java | 38 ++ .../parse/sqlparse/action/SelectParse.java | 34 + .../parse/sqlparse/action/UpdateParse.java | 59 ++ .../adapter/ArexExpressionVisitorAdapter.java | 587 ++++++++++++++++++ .../adapter/ArexFromItemVisitorAdapter.java | 94 +++ .../adapter/ArexItemsListVisitorAdapter.java | 71 +++ .../adapter/ArexOrderByVisitorAdapter.java | 24 + .../adapter/ArexSelectItemVisitorAdapter.java | 36 ++ .../adapter/ArexSelectVisitorAdapter.java | 107 ++++ .../sqlparse/constants/DbParseConstants.java | 66 ++ .../parse/sqlparse/parse/ColumnParse.java | 67 ++ .../parse/sqlparse/parse/CommonParse.java | 116 ++++ .../parse/sqlparse/parse/ExpressionParse.java | 83 +++ .../util/parse/sqlparse/parse/ItemParse.java | 41 ++ .../util/parse/sqlparse/parse/JoinParse.java | 38 ++ .../parse/sqlparse/parse/OrderByParse.java | 29 + .../util/parse/sqlparse/parse/TableParse.java | 44 ++ .../parse/sqlparse/parse/UpdateSetParse.java | 31 + .../sqlparse/util/ExpressionExtractor.java | 23 + .../parse/sqlparse/util/JoinParseUtil.java | 104 ++++ .../util/parse/sqlparse/util/ParseUtil.java | 82 +++ .../arex/parse/sqlparse/DeleteParseTest.java | 69 ++ .../arex/parse/sqlparse/ExecuteParseTest.java | 37 ++ .../arex/parse/sqlparse/InsertParseTest.java | 62 ++ .../arex/parse/sqlparse/ReplaceParseTest.java | 60 ++ .../arex/parse/sqlparse/SelectParseTest.java | 191 ++++++ .../arex/parse/sqlparse/UpdateParseTest.java | 63 ++ pom.xml | 11 + 37 files changed, 2498 insertions(+), 1 deletion(-) create mode 100644 arex-third-party/src/main/java/io/arex/agent/thirdparty/util/JacksonHelperUtil.java create mode 100644 arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/Parse.java create mode 100644 arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/SqlParse.java create mode 100644 arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/action/ActionFactory.java create mode 100644 arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/action/DeleteParse.java create mode 100644 arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/action/ExecuteParse.java create mode 100644 arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/action/InsertParse.java create mode 100644 arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/action/ReplaceParse.java create mode 100644 arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/action/SelectParse.java create mode 100644 arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/action/UpdateParse.java create mode 100644 arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/adapter/ArexExpressionVisitorAdapter.java create mode 100644 arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/adapter/ArexFromItemVisitorAdapter.java create mode 100644 arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/adapter/ArexItemsListVisitorAdapter.java create mode 100644 arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/adapter/ArexOrderByVisitorAdapter.java create mode 100644 arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/adapter/ArexSelectItemVisitorAdapter.java create mode 100644 arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/adapter/ArexSelectVisitorAdapter.java create mode 100644 arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/constants/DbParseConstants.java create mode 100644 arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/parse/ColumnParse.java create mode 100644 arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/parse/CommonParse.java create mode 100644 arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/parse/ExpressionParse.java create mode 100644 arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/parse/ItemParse.java create mode 100644 arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/parse/JoinParse.java create mode 100644 arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/parse/OrderByParse.java create mode 100644 arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/parse/TableParse.java create mode 100644 arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/parse/UpdateSetParse.java create mode 100644 arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/util/ExpressionExtractor.java create mode 100644 arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/util/JoinParseUtil.java create mode 100644 arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/util/ParseUtil.java create mode 100644 arex-third-party/src/test/java/io/arex/parse/sqlparse/DeleteParseTest.java create mode 100644 arex-third-party/src/test/java/io/arex/parse/sqlparse/ExecuteParseTest.java create mode 100644 arex-third-party/src/test/java/io/arex/parse/sqlparse/InsertParseTest.java create mode 100644 arex-third-party/src/test/java/io/arex/parse/sqlparse/ReplaceParseTest.java create mode 100644 arex-third-party/src/test/java/io/arex/parse/sqlparse/SelectParseTest.java create mode 100644 arex-third-party/src/test/java/io/arex/parse/sqlparse/UpdateParseTest.java diff --git a/arex-instrumentation-api/pom.xml b/arex-instrumentation-api/pom.xml index ce6ae7772..c0cbf5049 100644 --- a/arex-instrumentation-api/pom.xml +++ b/arex-instrumentation-api/pom.xml @@ -32,7 +32,6 @@ com.fasterxml.jackson.core jackson-databind ${jackson.version} - test com.google.code.gson diff --git a/arex-third-party/pom.xml b/arex-third-party/pom.xml index 0f89cec99..2c87d9207 100644 --- a/arex-third-party/pom.xml +++ b/arex-third-party/pom.xml @@ -7,6 +7,18 @@ io.arex ${revision} + + + com.fasterxml.jackson.core + jackson-databind + ${jackson.version} + + + com.github.jsqlparser + jsqlparser + ${jsqlparser.version} + + 4.0.0 arex-third-party diff --git a/arex-third-party/src/main/java/io/arex/agent/thirdparty/util/JacksonHelperUtil.java b/arex-third-party/src/main/java/io/arex/agent/thirdparty/util/JacksonHelperUtil.java new file mode 100644 index 000000000..229b35439 --- /dev/null +++ b/arex-third-party/src/main/java/io/arex/agent/thirdparty/util/JacksonHelperUtil.java @@ -0,0 +1,23 @@ +package io.arex.agent.thirdparty.util; + +import com.fasterxml.jackson.databind.ObjectMapper; +import com.fasterxml.jackson.databind.node.ArrayNode; +import com.fasterxml.jackson.databind.node.ObjectNode; + +/** + * @author niyan + * @date 2024/4/3 + * @since 1.0.0 + */ +public class JacksonHelperUtil { + + public static ObjectMapper objectMapper = new ObjectMapper(); + + public static ObjectNode getObjectNode() { + return objectMapper.createObjectNode(); + } + + public static ArrayNode getArrayNode() { + return objectMapper.createArrayNode(); + } +} diff --git a/arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/Parse.java b/arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/Parse.java new file mode 100644 index 000000000..eeb9f955d --- /dev/null +++ b/arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/Parse.java @@ -0,0 +1,13 @@ +package io.arex.agent.thirdparty.util.parse.sqlparse; + + +import com.fasterxml.jackson.databind.node.ObjectNode; + +/** + * @author niyan + * @date 2024/4/3 + * @since 1.0.0 + */ +public interface Parse { + ObjectNode parse(T parseObj); +} diff --git a/arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/SqlParse.java b/arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/SqlParse.java new file mode 100644 index 000000000..c0c41c967 --- /dev/null +++ b/arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/SqlParse.java @@ -0,0 +1,26 @@ +package io.arex.agent.thirdparty.util.parse.sqlparse; + +import com.fasterxml.jackson.databind.JsonNode; +import io.arex.agent.thirdparty.util.parse.sqlparse.action.ActionFactory; +import net.sf.jsqlparser.JSQLParserException; +import net.sf.jsqlparser.parser.CCJSqlParserUtil; +import net.sf.jsqlparser.statement.Statement; + +/** + * sql parse + * + * @author niyan + * @date 2024/4/3 + * @since 1.0.0 + */ +public class SqlParse { + public JsonNode parse(String sql) throws JSQLParserException { + if (sql == null || sql.isEmpty()) { + return null; + } + + Statement statement = CCJSqlParserUtil.parse(sql); + Parse matchParse = ActionFactory.selectParse(statement); + return matchParse.parse(statement); + } +} diff --git a/arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/action/ActionFactory.java b/arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/action/ActionFactory.java new file mode 100644 index 000000000..fb6c9e967 --- /dev/null +++ b/arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/action/ActionFactory.java @@ -0,0 +1,37 @@ +package io.arex.agent.thirdparty.util.parse.sqlparse.action; + +import io.arex.agent.thirdparty.util.parse.sqlparse.Parse; +import net.sf.jsqlparser.statement.delete.Delete; +import net.sf.jsqlparser.statement.execute.Execute; +import net.sf.jsqlparser.statement.insert.Insert; +import net.sf.jsqlparser.statement.replace.Replace; +import net.sf.jsqlparser.statement.select.Select; +import net.sf.jsqlparser.statement.update.Update; + +import net.sf.jsqlparser.statement.Statement; + + +/** + * @author niyan + * @date 2024/4/3 + * @since 1.0.0 + */ +public class ActionFactory { + public static Parse selectParse(Statement statement) { + if (statement instanceof Select) { + return new SelectParse(); + } else if (statement instanceof Execute) { + return new ExecuteParse(); + } else if (statement instanceof Delete) { + return new DeleteParse(); + } else if (statement instanceof Insert) { + return new InsertParse(); + } else if (statement instanceof Replace) { + return new ReplaceParse(); + } else if (statement instanceof Update) { + return new UpdateParse(); + } else { + throw new UnsupportedOperationException("not support"); + } + } +} diff --git a/arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/action/DeleteParse.java b/arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/action/DeleteParse.java new file mode 100644 index 000000000..19c241231 --- /dev/null +++ b/arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/action/DeleteParse.java @@ -0,0 +1,47 @@ +package io.arex.agent.thirdparty.util.parse.sqlparse.action; + +import com.fasterxml.jackson.databind.node.ObjectNode; +import io.arex.agent.thirdparty.util.JacksonHelperUtil; +import io.arex.agent.thirdparty.util.parse.sqlparse.Parse; +import io.arex.agent.thirdparty.util.parse.sqlparse.parse.CommonParse; +import io.arex.agent.thirdparty.util.parse.sqlparse.parse.ExpressionParse; +import io.arex.agent.thirdparty.util.parse.sqlparse.parse.JoinParse; +import io.arex.agent.thirdparty.util.parse.sqlparse.parse.OrderByParse; +import io.arex.agent.thirdparty.util.parse.sqlparse.parse.TableParse; +import io.arex.agent.thirdparty.util.parse.sqlparse.constants.DbParseConstants; +import net.sf.jsqlparser.statement.delete.Delete; + +/** + * @author niyan + * @date 2024/4/3 + * @since 1.0.0 + */ +public class DeleteParse implements Parse { + + private final ObjectNode sqlObjectNode; + public DeleteParse() { + sqlObjectNode = JacksonHelperUtil.getObjectNode(); + // action parse + sqlObjectNode.put(DbParseConstants.ACTION, DbParseConstants.DELETE); + } + @Override + public ObjectNode parse(Delete parseObj) { + + // tables parse + TableParse.parseDelTable(parseObj.getTables(), parseObj.getTable(), sqlObjectNode); + + // join parse + JoinParse.parse(parseObj.getJoins(), sqlObjectNode); + + // where parse + ExpressionParse.parseWhere(parseObj.getWhere(), sqlObjectNode); + + // orderBy parse + OrderByParse.parse(parseObj.getOrderByElements(), sqlObjectNode); + + // limit parse + CommonParse.parseLimit(parseObj.getLimit(), sqlObjectNode); + + return sqlObjectNode; + } +} diff --git a/arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/action/ExecuteParse.java b/arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/action/ExecuteParse.java new file mode 100644 index 000000000..4929a9fd4 --- /dev/null +++ b/arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/action/ExecuteParse.java @@ -0,0 +1,36 @@ +package io.arex.agent.thirdparty.util.parse.sqlparse.action; + +import com.fasterxml.jackson.databind.node.ObjectNode; +import io.arex.agent.thirdparty.util.JacksonHelperUtil; +import io.arex.agent.thirdparty.util.parse.sqlparse.Parse; +import io.arex.agent.thirdparty.util.parse.sqlparse.parse.CommonParse; +import io.arex.agent.thirdparty.util.parse.sqlparse.parse.ExpressionParse; +import io.arex.agent.thirdparty.util.parse.sqlparse.constants.DbParseConstants; +import net.sf.jsqlparser.statement.execute.Execute; + +/** + * @author niyan + * @date 2024/4/3 + * @since 1.0.0 + */ +public class ExecuteParse implements Parse { + + private final ObjectNode executeObj; + public ExecuteParse() { + executeObj = JacksonHelperUtil.getObjectNode(); + // action parse + executeObj.put(DbParseConstants.ACTION, DbParseConstants.EXECUTE); + } + + @Override + public ObjectNode parse(Execute parseObj) { + + // execute name parse + CommonParse.parseName(parseObj.getName(), executeObj); + + // expressions parse + ExpressionParse.parse(parseObj.getExprList(), executeObj); + + return executeObj; + } +} diff --git a/arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/action/InsertParse.java b/arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/action/InsertParse.java new file mode 100644 index 000000000..7206062f7 --- /dev/null +++ b/arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/action/InsertParse.java @@ -0,0 +1,37 @@ +package io.arex.agent.thirdparty.util.parse.sqlparse.action; + +import com.fasterxml.jackson.databind.node.ObjectNode; +import io.arex.agent.thirdparty.util.JacksonHelperUtil; +import io.arex.agent.thirdparty.util.parse.sqlparse.Parse; +import io.arex.agent.thirdparty.util.parse.sqlparse.parse.ColumnParse; +import io.arex.agent.thirdparty.util.parse.sqlparse.parse.TableParse; +import io.arex.agent.thirdparty.util.parse.sqlparse.constants.DbParseConstants; +import net.sf.jsqlparser.statement.insert.Insert; + +/** + * @author niyan + * @date 2024/4/3 + * @since 1.0.0 + */ +public class InsertParse implements Parse { + + private final ObjectNode insertObj; + public InsertParse() { + insertObj = JacksonHelperUtil.getObjectNode(); + // action parse + insertObj.put(DbParseConstants.ACTION, DbParseConstants.INSERT); + } + @Override + public ObjectNode parse(Insert parseObj) { + // table parse + TableParse.parse(parseObj.getTable(), insertObj); + + // columns parse + ColumnParse.parse(parseObj.getColumns(), parseObj.getItemsList(), insertObj); + + // setColumns parse + ColumnParse.parseSetColumns(parseObj.getSetColumns(), parseObj.getSetExpressionList(), insertObj); + + return insertObj; + } +} diff --git a/arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/action/ReplaceParse.java b/arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/action/ReplaceParse.java new file mode 100644 index 000000000..5388e35a7 --- /dev/null +++ b/arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/action/ReplaceParse.java @@ -0,0 +1,38 @@ +package io.arex.agent.thirdparty.util.parse.sqlparse.action; + +import com.fasterxml.jackson.databind.node.ObjectNode; +import io.arex.agent.thirdparty.util.JacksonHelperUtil; +import io.arex.agent.thirdparty.util.parse.sqlparse.Parse; +import io.arex.agent.thirdparty.util.parse.sqlparse.parse.ColumnParse; +import io.arex.agent.thirdparty.util.parse.sqlparse.parse.ExpressionParse; +import io.arex.agent.thirdparty.util.parse.sqlparse.parse.TableParse; +import io.arex.agent.thirdparty.util.parse.sqlparse.constants.DbParseConstants; +import net.sf.jsqlparser.statement.replace.Replace; + +/** + * @author niyan + * @date 2024/4/3 + * @since 1.0.0 + */ +public class ReplaceParse implements Parse { + + private final ObjectNode replaceObj; + public ReplaceParse() { + replaceObj = JacksonHelperUtil.getObjectNode(); + // action parse + replaceObj.put(DbParseConstants.ACTION, DbParseConstants.REPLACE); + } + @Override + public ObjectNode parse(Replace parseObj) { + // table parse + TableParse.parse(parseObj.getTable(), replaceObj); + + // columns parse + ColumnParse.parse(parseObj.getColumns(), parseObj.getItemsList(), replaceObj); + + // expressions parse + ExpressionParse.parse(parseObj.getExpressions(), parseObj.getColumns(), replaceObj); + + return replaceObj; + } +} diff --git a/arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/action/SelectParse.java b/arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/action/SelectParse.java new file mode 100644 index 000000000..dc2790e68 --- /dev/null +++ b/arex-third-party/src/main/java/io/arex/agent/thirdparty/util/parse/sqlparse/action/SelectParse.java @@ -0,0 +1,34 @@ +package io.arex.agent.thirdparty.util.parse.sqlparse.action; + +import com.fasterxml.jackson.databind.node.ObjectNode; +import io.arex.agent.thirdparty.util.JacksonHelperUtil; +import io.arex.agent.thirdparty.util.parse.sqlparse.Parse; +import io.arex.agent.thirdparty.util.parse.sqlparse.adapter.ArexSelectVisitorAdapter; +import io.arex.agent.thirdparty.util.parse.sqlparse.constants.DbParseConstants; +import net.sf.jsqlparser.statement.select.Select; +import net.sf.jsqlparser.statement.select.SelectBody; + +/** + * @author niyan + * @date 2024/4/3 + * @since 1.0.0 + */ +public class SelectParse implements Parse { +public class SelectParse extends AbstractParse