diff --git a/backend/src/main/java/io/dataease/controller/panel/PanelGroupController.java b/backend/src/main/java/io/dataease/controller/panel/PanelGroupController.java index 4b5164b44e..a980e44f5e 100644 --- a/backend/src/main/java/io/dataease/controller/panel/PanelGroupController.java +++ b/backend/src/main/java/io/dataease/controller/panel/PanelGroupController.java @@ -1,9 +1,12 @@ package io.dataease.controller.panel; +import com.auth0.jwt.JWT; +import com.auth0.jwt.interfaces.DecodedJWT; import com.github.xiaoymin.knife4j.annotations.ApiSupport; import io.dataease.auth.annotation.DePermission; import io.dataease.auth.annotation.DePermissionProxy; import io.dataease.auth.annotation.DePermissions; +import io.dataease.auth.filter.F2CLinkFilter; import io.dataease.auth.service.impl.ExtAuthServiceImpl; import io.dataease.commons.constants.DePermissionType; import io.dataease.commons.constants.PanelConstants; @@ -21,9 +24,12 @@ import io.swagger.annotations.ApiOperation; import org.apache.shiro.authz.annotation.Logical; import org.pentaho.di.core.util.UUIDUtil; import org.springframework.web.bind.annotation.*; +import org.springframework.web.context.request.RequestContextHolder; +import org.springframework.web.context.request.ServletRequestAttributes; import springfox.documentation.annotations.ApiIgnore; import javax.annotation.Resource; +import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; import java.io.IOException; import java.util.List; @@ -141,6 +147,12 @@ public class PanelGroupController { @PostMapping("/exportDetails") @I18n public void exportDetails(@RequestBody PanelViewDetailsRequest request, HttpServletResponse response) throws IOException { + HttpServletRequest httpServletRequest = ((ServletRequestAttributes) RequestContextHolder.getRequestAttributes()) + .getRequest(); + String linkToken = httpServletRequest.getHeader(F2CLinkFilter.LINK_TOKEN_KEY); + DecodedJWT jwt = JWT.decode(linkToken); + Long userId = jwt.getClaim("userId").asLong(); + request.setUserId(userId); panelGroupService.exportPanelViewDetails(request, response); } diff --git a/backend/src/main/java/io/dataease/controller/request/panel/PanelViewDetailsRequest.java b/backend/src/main/java/io/dataease/controller/request/panel/PanelViewDetailsRequest.java index ec9650c909..acbda314be 100644 --- a/backend/src/main/java/io/dataease/controller/request/panel/PanelViewDetailsRequest.java +++ b/backend/src/main/java/io/dataease/controller/request/panel/PanelViewDetailsRequest.java @@ -40,4 +40,6 @@ public class PanelViewDetailsRequest { @ApiModelProperty(hidden = true) private PermissionProxy proxy; + private Long userId; + } diff --git a/backend/src/main/java/io/dataease/provider/engine/mysql/MysqlQueryProvider.java b/backend/src/main/java/io/dataease/provider/engine/mysql/MysqlQueryProvider.java index 484ba4c14f..4c8591d85b 100644 --- a/backend/src/main/java/io/dataease/provider/engine/mysql/MysqlQueryProvider.java +++ b/backend/src/main/java/io/dataease/provider/engine/mysql/MysqlQueryProvider.java @@ -1,1367 +1,1366 @@ -package io.dataease.provider.engine.mysql; - -import com.alibaba.fastjson.JSONArray; -import io.dataease.plugins.common.base.domain.ChartViewWithBLOBs; -import io.dataease.plugins.common.base.domain.DatasetTableField; -import io.dataease.plugins.common.base.domain.DatasetTableFieldExample; -import io.dataease.plugins.common.base.domain.Datasource; -import io.dataease.plugins.common.base.mapper.DatasetTableFieldMapper; -import io.dataease.plugins.common.constants.DeTypeConstants; -import io.dataease.plugins.common.constants.datasource.SQLConstants; -import io.dataease.plugins.common.constants.engine.MysqlConstants; -import io.dataease.plugins.common.dto.chart.ChartCustomFilterItemDTO; -import io.dataease.plugins.common.dto.chart.ChartFieldCustomFilterDTO; -import io.dataease.plugins.common.dto.chart.ChartViewFieldDTO; -import io.dataease.plugins.common.dto.datasource.DeSortField; -import io.dataease.plugins.common.dto.sqlObj.SQLObj; -import io.dataease.plugins.common.request.chart.ChartExtFilterRequest; -import io.dataease.plugins.common.request.permission.DataSetRowPermissionsTreeDTO; -import io.dataease.plugins.common.request.permission.DatasetRowPermissionsTreeItem; -import io.dataease.plugins.datasource.entity.Dateformat; -import io.dataease.plugins.datasource.entity.PageInfo; -import io.dataease.plugins.datasource.query.QueryProvider; -import io.dataease.plugins.datasource.query.Utils; -import org.apache.commons.collections4.CollectionUtils; -import org.apache.commons.lang3.ObjectUtils; -import org.apache.commons.lang3.StringUtils; -import org.springframework.stereotype.Service; -import org.stringtemplate.v4.ST; -import org.stringtemplate.v4.STGroup; -import org.stringtemplate.v4.STGroupFile; - -import javax.annotation.Resource; -import java.text.MessageFormat; -import java.text.SimpleDateFormat; -import java.util.*; -import java.util.regex.Matcher; -import java.util.regex.Pattern; -import java.util.stream.Collectors; - -import static io.dataease.plugins.common.constants.datasource.SQLConstants.TABLE_ALIAS_PREFIX; - -/** - * @Author gin - * @Date 2021/5/17 4:11 下午 - */ -@Service("engine_mysqlQueryProvider") -public class MysqlQueryProvider extends QueryProvider { - @Resource - private DatasetTableFieldMapper datasetTableFieldMapper; - - @Override - public Integer transFieldType(String field) { - switch (field) { - case "CHAR": - case "VARCHAR": - case "TEXT": - case "TINYTEXT": - case "MEDIUMTEXT": - case "LONGTEXT": - case "ENUM": - return 0;// 文本 - case "DATE": - case "TIME": - case "YEAR": - case "DATETIME": - case "TIMESTAMP": - return 1;// 时间 - case "INT": - case "SMALLINT": - case "MEDIUMINT": - case "INTEGER": - case "BIGINT": - case "LONG": //增加了LONG类型 - return 2;// 整型 - case "FLOAT": - case "DOUBLE": - case "DECIMAL": - return 3;// 浮点 - case "BIT": - case "TINYINT": - return 4;// 布尔 - default: - return 0; - } - } - - @Override - public String createSQLPreview(String sql, String orderBy) { - return "SELECT * FROM (" + sqlFix(sql) + ") AS tmp LIMIT 0,1000"; - } - - @Override - public String createQuerySQL(String table, List fields, boolean isGroup, Datasource ds, List fieldCustomFilter, List rowPermissionsTree) { - return createQuerySQL(table, fields, isGroup, ds, fieldCustomFilter, rowPermissionsTree, null); - } - - @Override - public String createQuerySQL(String table, List fields, boolean isGroup, Datasource ds, List fieldCustomFilter, List rowPermissionsTree, List sortFields) { - SQLObj tableObj = SQLObj.builder() - .tableName((table.startsWith("(") && table.endsWith(")")) ? table : String.format(MysqlConstants.KEYWORD_TABLE, table)) - .tableAlias(String.format(TABLE_ALIAS_PREFIX, 0)) - .build(); - List xFields = new ArrayList<>(); - List xOrders = new ArrayList<>(); - if (CollectionUtils.isNotEmpty(fields)) { - for (int i = 0; i < fields.size(); i++) { - DatasetTableField f = fields.get(i); - String originField; - if (ObjectUtils.isNotEmpty(f.getExtField()) && f.getExtField() == 2) { - // 解析origin name中有关联的字段生成sql表达式 - originField = calcFieldRegex(f.getOriginName(), tableObj); - } else if (ObjectUtils.isNotEmpty(f.getExtField()) && f.getExtField() == 1) { - originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), f.getDataeaseName()); - } else { - originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), f.getDataeaseName()); - } - String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_X_PREFIX, i); - String fieldName = ""; - // 处理横轴字段 - if (f.getDeExtractType() == 1) { - if (f.getDeType() == 2 || f.getDeType() == 3) { - fieldName = String.format(MysqlConstants.UNIX_TIMESTAMP, originField) + "*1000"; - } else { - fieldName = originField; - } - } else if (f.getDeExtractType() == 0) { - if (f.getDeType() == 2) { - fieldName = String.format(MysqlConstants.CAST, originField, MysqlConstants.DEFAULT_INT_FORMAT); - } else if (f.getDeType() == 3) { - fieldName = String.format(MysqlConstants.CAST, originField, MysqlConstants.DEFAULT_FLOAT_FORMAT); - } else if (f.getDeType() == 1) { - fieldName = StringUtils.isEmpty(f.getDateFormat()) ? String.format(MysqlConstants.STR_TO_DATE, originField, MysqlConstants.DEFAULT_DATE_FORMAT) : - String.format(MysqlConstants.DATE_FORMAT, String.format(MysqlConstants.STR_TO_DATE, originField, f.getDateFormat()), MysqlConstants.DEFAULT_DATE_FORMAT); - } else { - fieldName = originField; - } - } else { - if (f.getDeType() == 1) { - String cast = String.format(MysqlConstants.CAST, originField, MysqlConstants.DEFAULT_INT_FORMAT) + "/1000"; - fieldName = String.format(MysqlConstants.FROM_UNIXTIME, cast, MysqlConstants.DEFAULT_DATE_FORMAT); - } else if (f.getDeType() == 2) { - fieldName = String.format(MysqlConstants.CAST, originField, MysqlConstants.DEFAULT_INT_FORMAT); - } else if (f.getDeType() == 3) { - fieldName = String.format(MysqlConstants.CAST, originField, MysqlConstants.DEFAULT_FLOAT_FORMAT); - } else { - fieldName = originField; - } - } - xFields.add(SQLObj.builder() - .fieldName(fieldName) - .fieldAlias(fieldAlias) - .build()); - } - } - - STGroup stg = new STGroupFile(SQLConstants.SQL_TEMPLATE); - ST st_sql = stg.getInstanceOf("previewSql"); - st_sql.add("isGroup", isGroup); - if (CollectionUtils.isNotEmpty(xFields)) st_sql.add("groups", xFields); - if (ObjectUtils.isNotEmpty(tableObj)) st_sql.add("table", tableObj); - String customWheres = transCustomFilterList(tableObj, fieldCustomFilter); - String whereTrees = transFilterTrees(tableObj, rowPermissionsTree); - List wheres = new ArrayList<>(); - if (customWheres != null) wheres.add(customWheres); - if (whereTrees != null) wheres.add(whereTrees); - if (CollectionUtils.isNotEmpty(wheres)) st_sql.add("filters", wheres); - - if (CollectionUtils.isNotEmpty(sortFields)) { - int step = fields.size(); - for (int i = step; i < (step + sortFields.size()); i++) { - DeSortField deSortField = sortFields.get(i - step); - SQLObj order = buildSortField(deSortField, tableObj, i); - xOrders.add(order); - } - } - if (ObjectUtils.isNotEmpty(xOrders)) { - st_sql.add("orders", xOrders); - } - - return st_sql.render(); - } - - private SQLObj buildSortField(DeSortField f, SQLObj tableObj, int i) { - String originField; - if (ObjectUtils.isNotEmpty(f.getExtField()) && f.getExtField() == 2) { - // 解析origin name中有关联的字段生成sql表达式 - originField = calcFieldRegex(f.getOriginName(), tableObj); - } else if (ObjectUtils.isNotEmpty(f.getExtField()) && f.getExtField() == 1) { - originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), f.getDataeaseName()); - } else { - originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), f.getDataeaseName()); - } - String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_X_PREFIX, i); - String fieldName = ""; - // 处理横轴字段 - if (f.getDeExtractType() == 1) { - if (f.getDeType() == 2 || f.getDeType() == 3) { - fieldName = String.format(MysqlConstants.UNIX_TIMESTAMP, originField) + "*1000"; - } else { - fieldName = originField; - } - } else if (f.getDeExtractType() == 0) { - if (f.getDeType() == 2) { - fieldName = String.format(MysqlConstants.CAST, originField, MysqlConstants.DEFAULT_INT_FORMAT); - } else if (f.getDeType() == 3) { - fieldName = String.format(MysqlConstants.CAST, originField, MysqlConstants.DEFAULT_FLOAT_FORMAT); - } else if (f.getDeType() == 1) { - fieldName = StringUtils.isEmpty(f.getDateFormat()) ? String.format(MysqlConstants.STR_TO_DATE, originField, MysqlConstants.DEFAULT_DATE_FORMAT) : - String.format(MysqlConstants.DATE_FORMAT, String.format(MysqlConstants.STR_TO_DATE, originField, f.getDateFormat()), MysqlConstants.DEFAULT_DATE_FORMAT); - } else { - fieldName = originField; - } - } else { - if (f.getDeType() == 1) { - String cast = String.format(MysqlConstants.CAST, originField, MysqlConstants.DEFAULT_INT_FORMAT) + "/1000"; - fieldName = String.format(MysqlConstants.FROM_UNIXTIME, cast, MysqlConstants.DEFAULT_DATE_FORMAT); - } else if (f.getDeType() == 2) { - fieldName = String.format(MysqlConstants.CAST, originField, MysqlConstants.DEFAULT_INT_FORMAT); - } else if (f.getDeType() == 3) { - fieldName = String.format(MysqlConstants.CAST, originField, MysqlConstants.DEFAULT_FLOAT_FORMAT); - } else { - fieldName = originField; - } - } - SQLObj result = SQLObj.builder().orderField(originField).orderAlias(originField).orderDirection(f.getOrderDirection()).build(); - return result; - } - - @Override - public String createQuerySQLAsTmp(String sql, List fields, boolean isGroup, List fieldCustomFilter, List rowPermissionsTree, List sortFields) { - return createQuerySQL("(" + sql + ")", fields, isGroup, null, fieldCustomFilter, rowPermissionsTree, sortFields); - } - - @Override - public String createQuerySQLAsTmp(String sql, List fields, boolean isGroup, List fieldCustomFilter, List rowPermissionsTree) { - return createQuerySQL("(" + sql + ")", fields, isGroup, null, fieldCustomFilter, rowPermissionsTree); - } - - @Override - public String createQueryTableWithPage(String table, List fields, Integer page, Integer pageSize, Integer realSize, boolean isGroup, Datasource ds, List fieldCustomFilter, List rowPermissionsTree) { - return createQuerySQL(table, fields, isGroup, null, fieldCustomFilter, rowPermissionsTree) + " LIMIT " + (page - 1) * pageSize + "," + realSize; - } - - @Override - public String createQueryTableWithLimit(String table, List fields, Integer limit, boolean isGroup, Datasource ds, List fieldCustomFilter, List rowPermissionsTree) { - return createQuerySQL(table, fields, isGroup, null, fieldCustomFilter, rowPermissionsTree) + " LIMIT 0," + limit; - } - - @Override - public String createQuerySqlWithLimit(String sql, List fields, Integer limit, boolean isGroup, List fieldCustomFilter, List rowPermissionsTree) { - return createQuerySQLAsTmp(sql, fields, isGroup, fieldCustomFilter, rowPermissionsTree) + " LIMIT 0," + limit; - } - - @Override - public String createQuerySQLWithPage(String sql, List fields, Integer page, Integer pageSize, Integer realSize, boolean isGroup, List fieldCustomFilter, List rowPermissionsTree) { - return createQuerySQLAsTmp(sql, fields, isGroup, fieldCustomFilter, rowPermissionsTree) + " LIMIT " + (page - 1) * pageSize + "," + realSize; - } - - @Override - public String getSQL(String table, List xAxis, List yAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, Datasource ds, ChartViewWithBLOBs view) { - SQLObj tableObj = SQLObj.builder() - .tableName((table.startsWith("(") && table.endsWith(")")) ? table : String.format(MysqlConstants.KEYWORD_TABLE, table)) - .tableAlias(String.format(TABLE_ALIAS_PREFIX, 0)) - .build(); - List xFields = new ArrayList<>(); - List xOrders = new ArrayList<>(); - if (CollectionUtils.isNotEmpty(xAxis)) { - for (int i = 0; i < xAxis.size(); i++) { - ChartViewFieldDTO x = xAxis.get(i); - String originField; - if (ObjectUtils.isNotEmpty(x.getExtField()) && x.getExtField() == 2) { -// 计算字段和视图字段,规则为 函数([原始字段id]),这边把[原始字段id] 换成 表名.原始字段id -// 解析origin name中有关联的字段生成sql表达式 - originField = calcFieldRegex(x.getOriginName(), tableObj); - } else if (ObjectUtils.isNotEmpty(x.getExtField()) && x.getExtField() == 1) { - originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), x.getDataeaseName()); - } else { - originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), x.getDataeaseName()); - } - String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_X_PREFIX, i); - // 处理横轴字段 - xFields.add(getXFields(x, originField, fieldAlias)); - - // 处理横轴排序 - if (StringUtils.isNotEmpty(x.getSort()) && Utils.joinSort(x.getSort())) { - xOrders.add(SQLObj.builder() - .orderField(originField) - .orderAlias(fieldAlias) - .orderDirection(x.getSort()) - .build()); - } - } - } - List yFields = new ArrayList<>(); - List yWheres = new ArrayList<>(); - List yOrders = new ArrayList<>(); - if (CollectionUtils.isNotEmpty(yAxis)) { - for (int i = 0; i < yAxis.size(); i++) { - ChartViewFieldDTO y = yAxis.get(i); - String originField; - if (ObjectUtils.isNotEmpty(y.getExtField()) && y.getExtField() == 2) { - // 解析origin name中有关联的字段生成sql表达式 - originField = calcFieldRegex(y.getOriginName(), tableObj); - } else if (ObjectUtils.isNotEmpty(y.getExtField()) && y.getExtField() == 1) { - originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), y.getDataeaseName()); - } else { - originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), y.getDataeaseName()); - } - String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_Y_PREFIX, i); - // 处理纵轴字段 - yFields.add(getYFields(y, originField, fieldAlias)); - // 处理纵轴过滤 - yWheres.add(getYWheres(y, originField, fieldAlias)); - // 处理纵轴排序 - if (StringUtils.isNotEmpty(y.getSort()) && Utils.joinSort(y.getSort())) { - yOrders.add(SQLObj.builder() - .orderField(originField) - .orderAlias(fieldAlias) - .orderDirection(y.getSort()) - .build()); - } - } - } - // 处理视图中字段过滤 - String customWheres = transCustomFilterList(tableObj, fieldCustomFilter); - // 处理仪表板字段过滤 - String extWheres = transExtFilterList(tableObj, extFilterRequestList); - // row permissions tree - String whereTrees = transFilterTrees(tableObj, rowPermissionsTree); - // 构建sql所有参数 - List fields = new ArrayList<>(); - fields.addAll(xFields); - fields.addAll(yFields); - List wheres = new ArrayList<>(); - if (customWheres != null) wheres.add(customWheres); - if (extWheres != null) wheres.add(extWheres); - if (whereTrees != null) wheres.add(whereTrees); - List groups = new ArrayList<>(); - groups.addAll(xFields); - // 外层再次套sql - List orders = new ArrayList<>(); - orders.addAll(xOrders); - orders.addAll(yOrders); - List aggWheres = new ArrayList<>(); - aggWheres.addAll(yWheres.stream().filter(ObjectUtils::isNotEmpty).collect(Collectors.toList())); - - STGroup stg = new STGroupFile(SQLConstants.SQL_TEMPLATE); - ST st_sql = stg.getInstanceOf("querySql"); - if (CollectionUtils.isNotEmpty(xFields)) st_sql.add("groups", xFields); - if (CollectionUtils.isNotEmpty(yFields)) st_sql.add("aggregators", yFields); - if (CollectionUtils.isNotEmpty(wheres)) st_sql.add("filters", wheres); - if (ObjectUtils.isNotEmpty(tableObj)) st_sql.add("table", tableObj); - String sql = st_sql.render(); - - ST st = stg.getInstanceOf("querySql"); - SQLObj tableSQL = SQLObj.builder() - .tableName(String.format(MysqlConstants.BRACKETS, sql)) - .tableAlias(String.format(TABLE_ALIAS_PREFIX, 1)) - .build(); - if (CollectionUtils.isNotEmpty(aggWheres)) st.add("filters", aggWheres); - if (CollectionUtils.isNotEmpty(orders)) st.add("orders", orders); - if (ObjectUtils.isNotEmpty(tableSQL)) st.add("table", tableSQL); - return sqlLimit(st.render(), view); - } - - @Override - public String getSQLWithPage(boolean isTable, String table, List xAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, Datasource ds, ChartViewWithBLOBs view, PageInfo pageInfo) { - String limit = ((pageInfo.getGoPage() != null && pageInfo.getPageSize() != null) ? " LIMIT " + (pageInfo.getGoPage() - 1) * pageInfo.getPageSize() + "," + pageInfo.getPageSize() : ""); - if (isTable) { - return originalTableInfo(table, xAxis, fieldCustomFilter, rowPermissionsTree, extFilterRequestList, ds, view) + limit; - } else { - return originalTableInfo("(" + sqlFix(table) + ")", xAxis, fieldCustomFilter, rowPermissionsTree, extFilterRequestList, ds, view) + limit; - } - } - - private String originalTableInfo(String table, List xAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, Datasource ds, ChartViewWithBLOBs view) { - SQLObj tableObj = SQLObj.builder() - .tableName((table.startsWith("(") && table.endsWith(")")) ? table : String.format(MysqlConstants.KEYWORD_TABLE, table)) - .tableAlias(String.format(TABLE_ALIAS_PREFIX, 0)) - .build(); - List xFields = new ArrayList<>(); - List xOrders = new ArrayList<>(); - if (CollectionUtils.isNotEmpty(xAxis)) { - for (int i = 0; i < xAxis.size(); i++) { - ChartViewFieldDTO x = xAxis.get(i); - String originField; - if (ObjectUtils.isNotEmpty(x.getExtField()) && x.getExtField() == 2) { - // 解析origin name中有关联的字段生成sql表达式 - originField = calcFieldRegex(x.getOriginName(), tableObj); - } else if (ObjectUtils.isNotEmpty(x.getExtField()) && x.getExtField() == 1) { - originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), x.getDataeaseName()); - } else { - if (x.getDeType() == 2 || x.getDeType() == 3) { - originField = String.format(MysqlConstants.CAST, String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), x.getDataeaseName()), MysqlConstants.DEFAULT_FLOAT_FORMAT); - } else { - originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), x.getDataeaseName()); - } - } - String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_X_PREFIX, i); - // 处理横轴字段 - xFields.add(getXFields(x, originField, fieldAlias)); - - // 处理横轴排序 - if (StringUtils.isNotEmpty(x.getSort()) && Utils.joinSort(x.getSort())) { - xOrders.add(SQLObj.builder() - .orderField(originField) - .orderAlias(fieldAlias) - .orderDirection(x.getSort()) - .build()); - } - } - } - // 处理视图中字段过滤 - String customWheres = transCustomFilterList(tableObj, fieldCustomFilter); - // 处理仪表板字段过滤 - String extWheres = transExtFilterList(tableObj, extFilterRequestList); - // row permissions tree - String whereTrees = transFilterTrees(tableObj, rowPermissionsTree); - // 构建sql所有参数 - List fields = new ArrayList<>(); - fields.addAll(xFields); - List wheres = new ArrayList<>(); - if (customWheres != null) wheres.add(customWheres); - if (extWheres != null) wheres.add(extWheres); - if (whereTrees != null) wheres.add(whereTrees); - List groups = new ArrayList<>(); - groups.addAll(xFields); - // 外层再次套sql - List orders = new ArrayList<>(); - orders.addAll(xOrders); - - STGroup stg = new STGroupFile(SQLConstants.SQL_TEMPLATE); - ST st_sql = stg.getInstanceOf("previewSql"); - st_sql.add("isGroup", false); - if (CollectionUtils.isNotEmpty(xFields)) st_sql.add("groups", xFields); - if (CollectionUtils.isNotEmpty(wheres)) st_sql.add("filters", wheres); - if (ObjectUtils.isNotEmpty(tableObj)) st_sql.add("table", tableObj); - String sql = st_sql.render(); - - ST st = stg.getInstanceOf("previewSql"); - st.add("isGroup", false); - SQLObj tableSQL = SQLObj.builder() - .tableName(String.format(MysqlConstants.BRACKETS, sql)) - .tableAlias(String.format(TABLE_ALIAS_PREFIX, 1)) - .build(); - if (CollectionUtils.isNotEmpty(orders)) st.add("orders", orders); - if (ObjectUtils.isNotEmpty(tableSQL)) st.add("table", tableSQL); - return st.render(); - } - - @Override - public String getSQLTableInfo(String table, List xAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, Datasource ds, ChartViewWithBLOBs view) { - return sqlLimit(originalTableInfo(table, xAxis, fieldCustomFilter, rowPermissionsTree, extFilterRequestList, ds, view), view); - } - - @Override - public String getSQLAsTmpTableInfo(String sql, List xAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, Datasource ds, ChartViewWithBLOBs view) { - return getSQLTableInfo("(" + sqlFix(sql) + ")", xAxis, fieldCustomFilter, rowPermissionsTree, extFilterRequestList, null, view); - } - - @Override - public String getSQLAsTmp(String sql, List xAxis, List yAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, ChartViewWithBLOBs view) { - return getSQL("(" + sql + ")", xAxis, yAxis, fieldCustomFilter, rowPermissionsTree, extFilterRequestList, null, view); - } - - @Override - public String getSQLStack(String table, List xAxis, List yAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, List extStack, Datasource ds, ChartViewWithBLOBs view) { - SQLObj tableObj = SQLObj.builder() - .tableName((table.startsWith("(") && table.endsWith(")")) ? table : String.format(MysqlConstants.KEYWORD_TABLE, table)) - .tableAlias(String.format(TABLE_ALIAS_PREFIX, 0)) - .build(); - List xFields = new ArrayList<>(); - List xOrders = new ArrayList<>(); - List xList = new ArrayList<>(); - xList.addAll(xAxis); - xList.addAll(extStack); - if (CollectionUtils.isNotEmpty(xList)) { - for (int i = 0; i < xList.size(); i++) { - ChartViewFieldDTO x = xList.get(i); - String originField; - if (ObjectUtils.isNotEmpty(x.getExtField()) && x.getExtField() == 2) { - // 解析origin name中有关联的字段生成sql表达式 - originField = calcFieldRegex(x.getOriginName(), tableObj); - } else if (ObjectUtils.isNotEmpty(x.getExtField()) && x.getExtField() == 1) { - originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), x.getDataeaseName()); - } else { - originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), x.getDataeaseName()); - } - String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_X_PREFIX, i); - // 处理横轴字段 - xFields.add(getXFields(x, originField, fieldAlias)); - - // 处理横轴排序 - if (StringUtils.isNotEmpty(x.getSort()) && Utils.joinSort(x.getSort())) { - xOrders.add(SQLObj.builder() - .orderField(originField) - .orderAlias(fieldAlias) - .orderDirection(x.getSort()) - .build()); - } - } - } - List yFields = new ArrayList<>(); - List yWheres = new ArrayList<>(); - List yOrders = new ArrayList<>(); - if (CollectionUtils.isNotEmpty(yAxis)) { - for (int i = 0; i < yAxis.size(); i++) { - ChartViewFieldDTO y = yAxis.get(i); - String originField; - if (ObjectUtils.isNotEmpty(y.getExtField()) && y.getExtField() == 2) { - // 解析origin name中有关联的字段生成sql表达式 - originField = calcFieldRegex(y.getOriginName(), tableObj); - } else if (ObjectUtils.isNotEmpty(y.getExtField()) && y.getExtField() == 1) { - originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), y.getDataeaseName()); - } else { - originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), y.getDataeaseName()); - } - String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_Y_PREFIX, i); - // 处理纵轴字段 - yFields.add(getYFields(y, originField, fieldAlias)); - // 处理纵轴过滤 - yWheres.add(getYWheres(y, originField, fieldAlias)); - // 处理纵轴排序 - if (StringUtils.isNotEmpty(y.getSort()) && Utils.joinSort(y.getSort())) { - yOrders.add(SQLObj.builder() - .orderField(originField) - .orderAlias(fieldAlias) - .orderDirection(y.getSort()) - .build()); - } - } - } - // 处理视图中字段过滤 - String customWheres = transCustomFilterList(tableObj, fieldCustomFilter); - // 处理仪表板字段过滤 - String extWheres = transExtFilterList(tableObj, extFilterRequestList); - // row permissions tree - String whereTrees = transFilterTrees(tableObj, rowPermissionsTree); - // 构建sql所有参数 - List fields = new ArrayList<>(); - fields.addAll(xFields); - fields.addAll(yFields); - List wheres = new ArrayList<>(); - if (customWheres != null) wheres.add(customWheres); - if (extWheres != null) wheres.add(extWheres); - if (whereTrees != null) wheres.add(whereTrees); - List groups = new ArrayList<>(); - groups.addAll(xFields); - // 外层再次套sql - List orders = new ArrayList<>(); - orders.addAll(xOrders); - orders.addAll(yOrders); - List aggWheres = new ArrayList<>(); - aggWheres.addAll(yWheres.stream().filter(ObjectUtils::isNotEmpty).collect(Collectors.toList())); - - STGroup stg = new STGroupFile(SQLConstants.SQL_TEMPLATE); - ST st_sql = stg.getInstanceOf("querySql"); - if (CollectionUtils.isNotEmpty(xFields)) st_sql.add("groups", xFields); - if (CollectionUtils.isNotEmpty(yFields)) st_sql.add("aggregators", yFields); - if (CollectionUtils.isNotEmpty(wheres)) st_sql.add("filters", wheres); - if (ObjectUtils.isNotEmpty(tableObj)) st_sql.add("table", tableObj); - String sql = st_sql.render(); - - ST st = stg.getInstanceOf("querySql"); - SQLObj tableSQL = SQLObj.builder() - .tableName(String.format(MysqlConstants.BRACKETS, sql)) - .tableAlias(String.format(TABLE_ALIAS_PREFIX, 1)) - .build(); - if (CollectionUtils.isNotEmpty(aggWheres)) st.add("filters", aggWheres); - if (CollectionUtils.isNotEmpty(orders)) st.add("orders", orders); - if (ObjectUtils.isNotEmpty(tableSQL)) st.add("table", tableSQL); - return sqlLimit(st.render(), view); - } - - @Override - public String getSQLAsTmpStack(String table, List xAxis, List yAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, List extStack, ChartViewWithBLOBs view) { - return getSQLStack("(" + table + ")", xAxis, yAxis, fieldCustomFilter, rowPermissionsTree, extFilterRequestList, extStack, null, view); - } - - @Override - public String getSQLScatter(String table, List xAxis, List yAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, List extBubble, Datasource ds, ChartViewWithBLOBs view) { - SQLObj tableObj = SQLObj.builder() - .tableName((table.startsWith("(") && table.endsWith(")")) ? table : String.format(MysqlConstants.KEYWORD_TABLE, table)) - .tableAlias(String.format(TABLE_ALIAS_PREFIX, 0)) - .build(); - List xFields = new ArrayList<>(); - List xOrders = new ArrayList<>(); - if (CollectionUtils.isNotEmpty(xAxis)) { - for (int i = 0; i < xAxis.size(); i++) { - ChartViewFieldDTO x = xAxis.get(i); - String originField; - if (ObjectUtils.isNotEmpty(x.getExtField()) && x.getExtField() == 2) { - // 解析origin name中有关联的字段生成sql表达式 - originField = calcFieldRegex(x.getOriginName(), tableObj); - } else if (ObjectUtils.isNotEmpty(x.getExtField()) && x.getExtField() == 1) { - originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), x.getDataeaseName()); - } else { - originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), x.getDataeaseName()); - } - String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_X_PREFIX, i); - // 处理横轴字段 - xFields.add(getXFields(x, originField, fieldAlias)); - - // 处理横轴排序 - if (StringUtils.isNotEmpty(x.getSort()) && Utils.joinSort(x.getSort())) { - xOrders.add(SQLObj.builder() - .orderField(originField) - .orderAlias(fieldAlias) - .orderDirection(x.getSort()) - .build()); - } - } - } - List yFields = new ArrayList<>(); - List yWheres = new ArrayList<>(); - List yOrders = new ArrayList<>(); - List yList = new ArrayList<>(); - yList.addAll(yAxis); - yList.addAll(extBubble); - if (CollectionUtils.isNotEmpty(yList)) { - for (int i = 0; i < yList.size(); i++) { - ChartViewFieldDTO y = yList.get(i); - String originField; - if (ObjectUtils.isNotEmpty(y.getExtField()) && y.getExtField() == 2) { - // 解析origin name中有关联的字段生成sql表达式 - originField = calcFieldRegex(y.getOriginName(), tableObj); - } else if (ObjectUtils.isNotEmpty(y.getExtField()) && y.getExtField() == 1) { - originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), y.getDataeaseName()); - } else { - originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), y.getDataeaseName()); - } - String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_Y_PREFIX, i); - // 处理纵轴字段 - yFields.add(getYFields(y, originField, fieldAlias)); - // 处理纵轴过滤 - yWheres.add(getYWheres(y, originField, fieldAlias)); - // 处理纵轴排序 - if (StringUtils.isNotEmpty(y.getSort()) && Utils.joinSort(y.getSort())) { - yOrders.add(SQLObj.builder() - .orderField(originField) - .orderAlias(fieldAlias) - .orderDirection(y.getSort()) - .build()); - } - } - } - // 处理视图中字段过滤 - String customWheres = transCustomFilterList(tableObj, fieldCustomFilter); - // 处理仪表板字段过滤 - String extWheres = transExtFilterList(tableObj, extFilterRequestList); - // row permissions tree - String whereTrees = transFilterTrees(tableObj, rowPermissionsTree); - // 构建sql所有参数 - List fields = new ArrayList<>(); - fields.addAll(xFields); - fields.addAll(yFields); - List wheres = new ArrayList<>(); - if (customWheres != null) wheres.add(customWheres); - if (extWheres != null) wheres.add(extWheres); - if (whereTrees != null) wheres.add(whereTrees); - List groups = new ArrayList<>(); - groups.addAll(xFields); - // 外层再次套sql - List orders = new ArrayList<>(); - orders.addAll(xOrders); - orders.addAll(yOrders); - List aggWheres = new ArrayList<>(); - aggWheres.addAll(yWheres.stream().filter(ObjectUtils::isNotEmpty).collect(Collectors.toList())); - - STGroup stg = new STGroupFile(SQLConstants.SQL_TEMPLATE); - ST st_sql = stg.getInstanceOf("querySql"); - if (CollectionUtils.isNotEmpty(xFields)) st_sql.add("groups", xFields); - if (CollectionUtils.isNotEmpty(yFields)) st_sql.add("aggregators", yFields); - if (CollectionUtils.isNotEmpty(wheres)) st_sql.add("filters", wheres); - if (ObjectUtils.isNotEmpty(tableObj)) st_sql.add("table", tableObj); - String sql = st_sql.render(); - - ST st = stg.getInstanceOf("querySql"); - SQLObj tableSQL = SQLObj.builder() - .tableName(String.format(MysqlConstants.BRACKETS, sql)) - .tableAlias(String.format(TABLE_ALIAS_PREFIX, 1)) - .build(); - if (CollectionUtils.isNotEmpty(aggWheres)) st.add("filters", aggWheres); - if (CollectionUtils.isNotEmpty(orders)) st.add("orders", orders); - if (ObjectUtils.isNotEmpty(tableSQL)) st.add("table", tableSQL); - return sqlLimit(st.render(), view); - } - - @Override - public String getSQLAsTmpScatter(String table, List xAxis, List yAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, List extBubble, ChartViewWithBLOBs view) { - return getSQLScatter("(" + table + ")", xAxis, yAxis, fieldCustomFilter, rowPermissionsTree, extFilterRequestList, extBubble, null, view); - } - - @Override - public String searchTable(String table) { - return "SELECT table_name FROM information_schema.TABLES WHERE table_name ='" + table + "'"; - } - - @Override - public String getSQLSummary(String table, List yAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, ChartViewWithBLOBs view, Datasource ds) { - // 字段汇总 排序等 - SQLObj tableObj = SQLObj.builder() - .tableName((table.startsWith("(") && table.endsWith(")")) ? table : String.format(MysqlConstants.KEYWORD_TABLE, table)) - .tableAlias(String.format(TABLE_ALIAS_PREFIX, 0)) - .build(); - List yFields = new ArrayList<>(); - List yWheres = new ArrayList<>(); - List yOrders = new ArrayList<>(); - if (CollectionUtils.isNotEmpty(yAxis)) { - for (int i = 0; i < yAxis.size(); i++) { - ChartViewFieldDTO y = yAxis.get(i); - String originField; - if (ObjectUtils.isNotEmpty(y.getExtField()) && y.getExtField() == 2) { - // 解析origin name中有关联的字段生成sql表达式 - originField = calcFieldRegex(y.getOriginName(), tableObj); - } else if (ObjectUtils.isNotEmpty(y.getExtField()) && y.getExtField() == 1) { - originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), y.getDataeaseName()); - } else { - originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), y.getDataeaseName()); - } - String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_Y_PREFIX, i); - // 处理纵轴字段 - yFields.add(getYFields(y, originField, fieldAlias)); - // 处理纵轴过滤 - yWheres.add(getYWheres(y, originField, fieldAlias)); - // 处理纵轴排序 - if (StringUtils.isNotEmpty(y.getSort()) && Utils.joinSort(y.getSort())) { - yOrders.add(SQLObj.builder() - .orderField(originField) - .orderAlias(fieldAlias) - .orderDirection(y.getSort()) - .build()); - } - } - } - // 处理视图中字段过滤 - String customWheres = transCustomFilterList(tableObj, fieldCustomFilter); - // 处理仪表板字段过滤 - String extWheres = transExtFilterList(tableObj, extFilterRequestList); - // row permissions tree - String whereTrees = transFilterTrees(tableObj, rowPermissionsTree); - // 构建sql所有参数 - List fields = new ArrayList<>(); - fields.addAll(yFields); - List wheres = new ArrayList<>(); - if (customWheres != null) wheres.add(customWheres); - if (extWheres != null) wheres.add(extWheres); - if (whereTrees != null) wheres.add(whereTrees); - List groups = new ArrayList<>(); - // 外层再次套sql - List orders = new ArrayList<>(); - orders.addAll(yOrders); - List aggWheres = new ArrayList<>(); - aggWheres.addAll(yWheres.stream().filter(ObjectUtils::isNotEmpty).collect(Collectors.toList())); - - STGroup stg = new STGroupFile(SQLConstants.SQL_TEMPLATE); - ST st_sql = stg.getInstanceOf("querySql"); - if (CollectionUtils.isNotEmpty(yFields)) st_sql.add("aggregators", yFields); - if (CollectionUtils.isNotEmpty(wheres)) st_sql.add("filters", wheres); - if (ObjectUtils.isNotEmpty(tableObj)) st_sql.add("table", tableObj); - String sql = st_sql.render(); - - ST st = stg.getInstanceOf("querySql"); - SQLObj tableSQL = SQLObj.builder() - .tableName(String.format(MysqlConstants.BRACKETS, sql)) - .tableAlias(String.format(TABLE_ALIAS_PREFIX, 1)) - .build(); - if (CollectionUtils.isNotEmpty(aggWheres)) st.add("filters", aggWheres); - if (CollectionUtils.isNotEmpty(orders)) st.add("orders", orders); - if (ObjectUtils.isNotEmpty(tableSQL)) st.add("table", tableSQL); - return sqlLimit(st.render(), view); - } - - @Override - public String getSQLSummaryAsTmp(String sql, List yAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, ChartViewWithBLOBs view) { - return getSQLSummary("(" + sql + ")", yAxis, fieldCustomFilter, rowPermissionsTree, extFilterRequestList, view, null); - } - - @Override - public String wrapSql(String sql) { - sql = sql.trim(); - if (sql.lastIndexOf(";") == (sql.length() - 1)) { - sql = sql.substring(0, sql.length() - 1); - } - String tmpSql = "SELECT * FROM (" + sql + ") AS tmp " + " LIMIT 0"; - return tmpSql; - } - - @Override - public String createRawQuerySQL(String table, List fields, Datasource ds) { - String[] array = fields.stream().map(f -> { - StringBuilder stringBuilder = new StringBuilder(); - stringBuilder.append("`").append(f.getDataeaseName()).append("` AS ").append(f.getDataeaseName()); - return stringBuilder.toString(); - }).toArray(String[]::new); - return MessageFormat.format("SELECT {0} FROM {1} ORDER BY null", StringUtils.join(array, ","), table); - } - - @Override - public String createRawQuerySQLAsTmp(String sql, List fields) { - return createRawQuerySQL(" (" + sqlFix(sql) + ") AS tmp ", fields, null); - } - - @Override - public String transTreeItem(SQLObj tableObj, DatasetRowPermissionsTreeItem item) { - String res = null; - DatasetTableField field = item.getField(); - if (ObjectUtils.isEmpty(field)) { - return null; - } - String whereName = ""; - String originName; - if (ObjectUtils.isNotEmpty(field.getExtField()) && field.getExtField() == 2) { - // 解析origin name中有关联的字段生成sql表达式 - originName = calcFieldRegex(field.getOriginName(), tableObj); - } else if (ObjectUtils.isNotEmpty(field.getExtField()) && field.getExtField() == 1) { - originName = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), field.getDataeaseName()); - } else { - originName = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), field.getDataeaseName()); - } - - if (field.getDeType() == 1) { - if (field.getDeExtractType() == 0 || field.getDeExtractType() == 5 || field.getDeExtractType() == 1) { - whereName = String.format(MysqlConstants.STR_TO_DATE, originName, StringUtils.isNotEmpty(field.getDateFormat()) ? field.getDateFormat() : MysqlConstants.DEFAULT_DATE_FORMAT); - } - if (field.getDeExtractType() == 2 || field.getDeExtractType() == 3 || field.getDeExtractType() == 4) { - String cast = String.format(MysqlConstants.CAST, originName, MysqlConstants.DEFAULT_INT_FORMAT) + "/1000"; - whereName = String.format(MysqlConstants.FROM_UNIXTIME, cast, MysqlConstants.DEFAULT_DATE_FORMAT); - } - } else if (field.getDeType() == 2 || field.getDeType() == 3) { - if (field.getDeExtractType() == 0 || field.getDeExtractType() == 5) { - whereName = String.format(MysqlConstants.CAST, originName, MysqlConstants.DEFAULT_FLOAT_FORMAT); - } - if (field.getDeExtractType() == 1) { - whereName = String.format(MysqlConstants.UNIX_TIMESTAMP, originName) + "*1000"; - } - if (field.getDeExtractType() == 2 || field.getDeExtractType() == 3 || field.getDeExtractType() == 4) { - whereName = originName; - } - } else if (field.getDeType() == 0 && field.getDeExtractType() == 0) { - whereName = String.format(MysqlConstants.CAST, originName, MysqlConstants.CHAR); - } else { - whereName = originName; - } - - if (StringUtils.equalsIgnoreCase(item.getFilterType(), "enum")) { - if (CollectionUtils.isNotEmpty(item.getEnumValue())) { - res = "(" + whereName + " IN ('" + String.join("','", item.getEnumValue()) + "'))"; - } - } else { - String value = item.getValue(); - String whereTerm = transMysqlFilterTerm(item.getTerm()); - String whereValue = ""; - - if (StringUtils.equalsIgnoreCase(item.getTerm(), "null")) { - whereValue = ""; - } else if (StringUtils.equalsIgnoreCase(item.getTerm(), "not_null")) { - whereValue = ""; - } else if (StringUtils.equalsIgnoreCase(item.getTerm(), "empty")) { - whereValue = "''"; - } else if (StringUtils.equalsIgnoreCase(item.getTerm(), "not_empty")) { - whereValue = "''"; - } else if (StringUtils.containsIgnoreCase(item.getTerm(), "in")) { - whereValue = "('" + StringUtils.join(value, "','") + "')"; - } else if (StringUtils.containsIgnoreCase(item.getTerm(), "like")) { - whereValue = "'%" + value + "%'"; - } else { - whereValue = String.format(MysqlConstants.WHERE_VALUE_VALUE, value); - } - SQLObj build = SQLObj.builder() - .whereField(whereName) - .whereTermAndValue(whereTerm + whereValue) - .build(); - res = build.getWhereField() + " " + build.getWhereTermAndValue(); - } - return res; - } - - @Override - public String convertTableToSql(String tableName, Datasource ds) { - return createSQLPreview("SELECT * FROM " + String.format(MysqlConstants.KEYWORD_TABLE, tableName), null); - } - - private String sqlFix(String sql) { - if (sql.lastIndexOf(";") == (sql.length() - 1)) { - sql = sql.substring(0, sql.length() - 1); - } - return sql; - } - - public String transMysqlFilterTerm(String term) { - switch (term) { - case "eq": - return " = "; - case "not_eq": - return " <> "; - case "lt": - return " < "; - case "le": - return " <= "; - case "gt": - return " > "; - case "ge": - return " >= "; - case "in": - return " IN "; - case "not in": - return " NOT IN "; - case "like": - return " LIKE "; - case "not like": - return " NOT LIKE "; - case "null": - return " IS NULL "; - case "not_null": - return " IS NOT NULL "; - case "empty": - return " = "; - case "not_empty": - return " <> "; - case "between": - return " BETWEEN "; - default: - return ""; - } - } - - public String transCustomFilterList(SQLObj tableObj, List requestList) { - if (CollectionUtils.isEmpty(requestList)) { - return null; - } - List res = new ArrayList<>(); - - for (ChartFieldCustomFilterDTO request : requestList) { - List list = new ArrayList<>(); - DatasetTableField field = request.getField(); - - if (ObjectUtils.isEmpty(field)) { - continue; - } - String whereName = ""; - String originName; - if (ObjectUtils.isNotEmpty(field.getExtField()) && field.getExtField() == 2) { - // 解析origin name中有关联的字段生成sql表达式 - originName = calcFieldRegex(field.getOriginName(), tableObj); - } else if (ObjectUtils.isNotEmpty(field.getExtField()) && field.getExtField() == 1) { - originName = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), field.getDataeaseName()); - } else { - originName = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), field.getDataeaseName()); - } - - if (field.getDeType() == 1) { - if (field.getDeExtractType() == 0 || field.getDeExtractType() == 5 || field.getDeExtractType() == 1) { - whereName = String.format(MysqlConstants.STR_TO_DATE, originName, StringUtils.isNotEmpty(field.getDateFormat()) ? field.getDateFormat() : MysqlConstants.DEFAULT_DATE_FORMAT); - } - if (field.getDeExtractType() == 2 || field.getDeExtractType() == 3 || field.getDeExtractType() == 4) { - String cast = String.format(MysqlConstants.CAST, originName, MysqlConstants.DEFAULT_INT_FORMAT) + "/1000"; - whereName = String.format(MysqlConstants.FROM_UNIXTIME, cast, MysqlConstants.DEFAULT_DATE_FORMAT); - } - } else if (field.getDeType() == 2 || field.getDeType() == 3) { - if (field.getDeExtractType() == 0 || field.getDeExtractType() == 5) { - whereName = String.format(MysqlConstants.CAST, originName, MysqlConstants.DEFAULT_FLOAT_FORMAT); - } - if (field.getDeExtractType() == 1) { - whereName = String.format(MysqlConstants.UNIX_TIMESTAMP, originName) + "*1000"; - } - if (field.getDeExtractType() == 2 || field.getDeExtractType() == 3 || field.getDeExtractType() == 4) { - whereName = originName; - } - } else if (field.getDeType() == 0 && field.getDeExtractType() == 0) { - whereName = String.format(MysqlConstants.CAST, originName, MysqlConstants.CHAR); - } else { - whereName = originName; - } - - if (StringUtils.equalsIgnoreCase(request.getFilterType(), "enum")) { - if (CollectionUtils.isNotEmpty(request.getEnumCheckField())) { - res.add("(" + whereName + " IN ('" + String.join("','", request.getEnumCheckField()) + "'))"); - } - } else { - List filter = request.getFilter(); - for (ChartCustomFilterItemDTO filterItemDTO : filter) { - String value = filterItemDTO.getValue(); - String whereTerm = transMysqlFilterTerm(filterItemDTO.getTerm()); - String whereValue = ""; - - if (StringUtils.equalsIgnoreCase(filterItemDTO.getTerm(), "null")) { - whereValue = ""; - } else if (StringUtils.equalsIgnoreCase(filterItemDTO.getTerm(), "not_null")) { - whereValue = ""; - } else if (StringUtils.equalsIgnoreCase(filterItemDTO.getTerm(), "empty")) { - whereValue = "''"; - } else if (StringUtils.equalsIgnoreCase(filterItemDTO.getTerm(), "not_empty")) { - whereValue = "''"; - } else if (StringUtils.containsIgnoreCase(filterItemDTO.getTerm(), "in")) { - whereValue = "('" + StringUtils.join(value, "','") + "')"; - } else if (StringUtils.containsIgnoreCase(filterItemDTO.getTerm(), "like")) { - whereValue = "'%" + value + "%'"; - } else { - // Doris field type test - /*if (field.getDeExtractType() == 2 || field.getDeExtractType() == 3 || field.getDeExtractType() == 4) { - whereValue = String.format(MysqlConstants.WHERE_NUMBER_VALUE, value); - } else { - whereValue = String.format(MysqlConstants.WHERE_VALUE_VALUE, value); - }*/ - whereValue = String.format(MysqlConstants.WHERE_VALUE_VALUE, value); - } - list.add(SQLObj.builder() - .whereField(whereName) - .whereTermAndValue(whereTerm + whereValue) - .build()); - } - - List strList = new ArrayList<>(); - list.forEach(ele -> strList.add(ele.getWhereField() + " " + ele.getWhereTermAndValue())); - if (CollectionUtils.isNotEmpty(list)) { - res.add("(" + String.join(" " + getLogic(request.getLogic()) + " ", strList) + ")"); - } - } - } - return CollectionUtils.isNotEmpty(res) ? "(" + String.join(" AND ", res) + ")" : null; - } - - private String reflectFieldName(DatasetTableField field) { - return field.getDataeaseName(); - } - - public String transExtFilterList(SQLObj tableObj, List requestList) { - if (CollectionUtils.isEmpty(requestList)) { - return null; - } - List list = new ArrayList<>(); - for (ChartExtFilterRequest request : requestList) { - List value = request.getValue(); - - List whereNameList = new ArrayList<>(); - List fieldList = new ArrayList<>(); - if (request.getIsTree()) { - fieldList.addAll(request.getDatasetTableFieldList()); - } else { - fieldList.add(request.getDatasetTableField()); - } - - for (DatasetTableField field : fieldList) { - if (CollectionUtils.isEmpty(value) || ObjectUtils.isEmpty(field)) { - continue; - } - String whereName = ""; - - - String originName; - if (ObjectUtils.isNotEmpty(field.getExtField()) && field.getExtField() == 2) { - // 解析origin name中有关联的字段生成sql表达式 - originName = calcFieldRegex(field.getOriginName(), tableObj); - } else if (ObjectUtils.isNotEmpty(field.getExtField()) && field.getExtField() == 1) { - originName = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), field.getDataeaseName()); - } else { - originName = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), field.getDataeaseName()); - } - - if (field.getDeType() == 1) { - String format = transDateFormat(request.getDateStyle(), request.getDatePattern()); - if (field.getDeExtractType() == 0 || field.getDeExtractType() == 5 || field.getDeExtractType() == 1) { - whereName = String.format(MysqlConstants.DATE_FORMAT, originName, format); - } - if (field.getDeExtractType() == 2 || field.getDeExtractType() == 3 || field.getDeExtractType() == 4) { - String cast = String.format(MysqlConstants.CAST, originName, MysqlConstants.DEFAULT_INT_FORMAT) + "/1000"; - whereName = String.format(MysqlConstants.FROM_UNIXTIME, cast, format); - } - } else if (field.getDeType() == 0 && field.getDeExtractType() == 0) { - whereName = String.format(MysqlConstants.CAST, originName, MysqlConstants.CHAR); - } else if (field.getDeType() == 2 || field.getDeType() == 3) { - if (field.getDeExtractType() == 0 || field.getDeExtractType() == 5) { - whereName = String.format(MysqlConstants.CAST, originName, MysqlConstants.DEFAULT_FLOAT_FORMAT); - } - if (field.getDeExtractType() == 1) { - whereName = String.format(MysqlConstants.UNIX_TIMESTAMP, originName) + "*1000"; - } - if (field.getDeExtractType() == 2 || field.getDeExtractType() == 3 || field.getDeExtractType() == 4) { - whereName = originName; - } - } else { - whereName = originName; - } - whereNameList.add(whereName); - } - - String whereName = ""; - if (request.getIsTree()) { - whereName = "CONCAT(" + StringUtils.join(whereNameList, ",',',") + ")"; - } else { - whereName = whereNameList.get(0); - } - String whereTerm = transMysqlFilterTerm(request.getOperator()); - String whereValue = ""; - - if (StringUtils.containsIgnoreCase(request.getOperator(), "in")) { - whereValue = "('" + StringUtils.join(value, "','") + "')"; - } else if (StringUtils.containsIgnoreCase(request.getOperator(), "like")) { - whereValue = "'%" + value.get(0) + "%'"; - } else if (StringUtils.containsIgnoreCase(request.getOperator(), "between")) { - if (request.getDatasetTableField().getDeType() == 1) { - SimpleDateFormat simpleDateFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss"); - String startTime = simpleDateFormat.format(new Date(Long.parseLong(value.get(0)))); - String endTime = simpleDateFormat.format(new Date(Long.parseLong(value.get(1)))); - whereValue = String.format(MysqlConstants.WHERE_BETWEEN, startTime, endTime); - } else { - whereValue = String.format(MysqlConstants.WHERE_BETWEEN, value.get(0), value.get(1)); - } - } else { - // doris field type test - /*if (field.getDeExtractType() == 2 || field.getDeExtractType() == 3 || field.getDeExtractType() == 4) { - whereValue = String.format(MysqlConstants.WHERE_NUMBER_VALUE, value.get(0)); - } else { - whereValue = String.format(MysqlConstants.WHERE_VALUE_VALUE, value.get(0)); - }*/ - whereValue = String.format(MysqlConstants.WHERE_VALUE_VALUE, value.get(0)); - } - list.add(SQLObj.builder() - .whereField(whereName) - .whereTermAndValue(whereTerm + whereValue) - .build()); - } - List strList = new ArrayList<>(); - list.forEach(ele -> strList.add(ele.getWhereField() + " " + ele.getWhereTermAndValue())); - return CollectionUtils.isNotEmpty(list) ? "(" + String.join(" AND ", strList) + ")" : null; - } - - private String transDateFormat(String dateStyle, String datePattern) { - String split = "-"; - if (StringUtils.equalsIgnoreCase(datePattern, "date_sub")) { - split = "-"; - } else if (StringUtils.equalsIgnoreCase(datePattern, "date_split")) { - split = "/"; - } else { - split = "-"; - } - - if (StringUtils.isEmpty(dateStyle)) { - return "%Y-%m-%d %H:%i:%S"; - } - - switch (dateStyle) { - case "y": - return "%Y"; - case "y_Q": - return "CONCAT(%s,'" + split + "',%s)"; - case "y_M": - return "%Y" + split + "%m"; - case "y_W": - return "%Y" + split + "%u"; - case "y_M_d": - return "%Y" + split + "%m" + split + "%d"; - case "H_m_s": - return "%H:%i:%S"; - case "y_M_d_H_m": - return "%Y" + split + "%m" + split + "%d" + " %H:%i"; - case "y_M_d_H_m_s": - return "%Y" + split + "%m" + split + "%d" + " %H:%i:%S"; - default: - return "%Y-%m-%d %H:%i:%S"; - } - } - - private SQLObj getXFields(ChartViewFieldDTO x, String originField, String fieldAlias) { - String fieldName = ""; - if (x.getDeExtractType() == 1) { - if (x.getDeType() == 2 || x.getDeType() == 3) { - fieldName = String.format(MysqlConstants.UNIX_TIMESTAMP, originField) + "*1000"; - } else if (x.getDeType() == 1) { - String format = transDateFormat(x.getDateStyle(), x.getDatePattern()); - if (StringUtils.equalsIgnoreCase(x.getDateStyle(), "y_Q")) { - fieldName = String.format(format, - String.format(MysqlConstants.DATE_FORMAT, originField, "%Y"), - String.format(MysqlConstants.QUARTER, originField)); - } else { - fieldName = String.format(MysqlConstants.DATE_FORMAT, originField, format); - } - } else { - fieldName = originField; - } - } else { - if (x.getDeType() == 1) { - String format = transDateFormat(x.getDateStyle(), x.getDatePattern()); - if (x.getDeExtractType() == 0) { - if (StringUtils.equalsIgnoreCase(x.getDateStyle(), "y_Q")) { - fieldName = String.format(format, - String.format(MysqlConstants.DATE_FORMAT, String.format(MysqlConstants.STR_TO_DATE, originField, MysqlConstants.DEFAULT_DATE_FORMAT), "%Y"), - String.format(MysqlConstants.QUARTER, String.format(MysqlConstants.STR_TO_DATE, originField, MysqlConstants.DEFAULT_DATE_FORMAT))); - } else { - fieldName = String.format(MysqlConstants.DATE_FORMAT, originField, format); - } - } else { - String cast = String.format(MysqlConstants.CAST, originField, MysqlConstants.DEFAULT_INT_FORMAT) + "/1000"; - String from_unixtime = String.format(MysqlConstants.FROM_UNIXTIME, cast, MysqlConstants.DEFAULT_DATE_FORMAT); - if (StringUtils.equalsIgnoreCase(x.getDateStyle(), "y_Q")) { - fieldName = String.format(format, - String.format(MysqlConstants.DATE_FORMAT, from_unixtime, "%Y"), - String.format(MysqlConstants.QUARTER, from_unixtime)); - } else { - fieldName = String.format(MysqlConstants.DATE_FORMAT, from_unixtime, format); - } - } - } else if (x.getDeType() == 0 && x.getDeExtractType() == 0) { - fieldName = String.format(MysqlConstants.CAST, originField, MysqlConstants.CHAR); - } else { - if (x.getDeType() == DeTypeConstants.DE_INT) { - fieldName = String.format(MysqlConstants.CAST, originField, MysqlConstants.DEFAULT_INT_FORMAT); - } else if (x.getDeType() == DeTypeConstants.DE_FLOAT) { - fieldName = String.format(MysqlConstants.CAST, originField, MysqlConstants.DEFAULT_FLOAT_FORMAT); - } else { - fieldName = originField; - } - } - } - return SQLObj.builder() - .fieldName(fieldName) - .fieldAlias(fieldAlias) - .build(); - } - - private List getXWheres(ChartViewFieldDTO x, String originField, String fieldAlias) { - List list = new ArrayList<>(); - if (CollectionUtils.isNotEmpty(x.getFilter()) && x.getFilter().size() > 0) { - x.getFilter().forEach(f -> { - String whereName = ""; - String whereTerm = transMysqlFilterTerm(f.getTerm()); - String whereValue = ""; - if (x.getDeType() == 1 && x.getDeExtractType() != 1) { - String cast = String.format(MysqlConstants.CAST, originField, MysqlConstants.DEFAULT_INT_FORMAT) + "/1000"; - whereName = String.format(MysqlConstants.FROM_UNIXTIME, cast, MysqlConstants.DEFAULT_DATE_FORMAT); - } else { - whereName = originField; - } - if (StringUtils.equalsIgnoreCase(f.getTerm(), "null")) { - whereValue = ""; - } else if (StringUtils.equalsIgnoreCase(f.getTerm(), "not_null")) { - whereValue = ""; - } else if (StringUtils.equalsIgnoreCase(f.getTerm(), "empty")) { - whereValue = "''"; - } else if (StringUtils.equalsIgnoreCase(f.getTerm(), "not_empty")) { - whereValue = "''"; - } else if (StringUtils.containsIgnoreCase(f.getTerm(), "in")) { - whereValue = "('" + StringUtils.join(f.getValue(), "','") + "')"; - } else if (StringUtils.containsIgnoreCase(f.getTerm(), "like")) { - whereValue = "'%" + f.getValue() + "%'"; - } else { - whereValue = String.format(MysqlConstants.WHERE_VALUE_VALUE, f.getValue()); - } - list.add(SQLObj.builder() - .whereField(whereName) - .whereAlias(fieldAlias) - .whereTermAndValue(whereTerm + whereValue) - .build()); - }); - } - return list; - } - - private SQLObj getYFields(ChartViewFieldDTO y, String originField, String fieldAlias) { - String fieldName = ""; - if (StringUtils.equalsIgnoreCase(y.getDataeaseName(), "*")) { - fieldName = MysqlConstants.AGG_COUNT; - } else if (SQLConstants.DIMENSION_TYPE.contains(y.getDeType())) { - if (StringUtils.equalsIgnoreCase(y.getSummary(), "count_distinct")) { - fieldName = String.format(MysqlConstants.AGG_FIELD, "COUNT", "DISTINCT " + originField); - } else { - fieldName = String.format(MysqlConstants.AGG_FIELD, y.getSummary(), originField); - } - } else { - if (StringUtils.equalsIgnoreCase(y.getSummary(), "avg") || StringUtils.containsIgnoreCase(y.getSummary(), "pop")) { - String cast = String.format(MysqlConstants.CAST, originField, y.getDeType() == 2 ? MysqlConstants.DEFAULT_INT_FORMAT : MysqlConstants.DEFAULT_FLOAT_FORMAT); - String agg = String.format(MysqlConstants.AGG_FIELD, y.getSummary(), cast); - String cast1 = String.format(MysqlConstants.CAST, agg, MysqlConstants.DEFAULT_FLOAT_FORMAT); - fieldName = String.format(MysqlConstants.ROUND, cast1, "8"); - } else { - String cast = String.format(MysqlConstants.CAST, originField, y.getDeType() == 2 ? MysqlConstants.DEFAULT_INT_FORMAT : MysqlConstants.DEFAULT_FLOAT_FORMAT); - if (StringUtils.equalsIgnoreCase(y.getSummary(), "count_distinct")) { - fieldName = String.format(MysqlConstants.AGG_FIELD, "COUNT", "DISTINCT " + cast); - } else { - fieldName = String.format(MysqlConstants.AGG_FIELD, y.getSummary(), cast); - } - } - } - return SQLObj.builder() - .fieldName(fieldName) - .fieldAlias(fieldAlias) - .build(); - } - - private String getYWheres(ChartViewFieldDTO y, String originField, String fieldAlias) { - List list = new ArrayList<>(); - if (CollectionUtils.isNotEmpty(y.getFilter()) && y.getFilter().size() > 0) { - y.getFilter().forEach(f -> { - String whereTerm = transMysqlFilterTerm(f.getTerm()); - String whereValue = ""; - // 原始类型不是时间,在de中被转成时间的字段做处理 - if (StringUtils.equalsIgnoreCase(f.getTerm(), "null")) { - whereValue = ""; - } else if (StringUtils.equalsIgnoreCase(f.getTerm(), "not_null")) { - whereValue = ""; - } else if (StringUtils.equalsIgnoreCase(f.getTerm(), "empty")) { - whereValue = "''"; - } else if (StringUtils.equalsIgnoreCase(f.getTerm(), "not_empty")) { - whereValue = "''"; - } else if (StringUtils.containsIgnoreCase(f.getTerm(), "in")) { - whereValue = "('" + StringUtils.join(f.getValue(), "','") + "')"; - } else if (StringUtils.containsIgnoreCase(f.getTerm(), "like")) { - whereValue = "'%" + f.getValue() + "%'"; - } else { - whereValue = String.format(MysqlConstants.WHERE_VALUE_VALUE, f.getValue()); - } - list.add(SQLObj.builder() - .whereField(fieldAlias) - .whereAlias(fieldAlias) - .whereTermAndValue(whereTerm + whereValue) - .build()); - }); - } - List strList = new ArrayList<>(); - list.forEach(ele -> strList.add(ele.getWhereField() + " " + ele.getWhereTermAndValue())); - return CollectionUtils.isNotEmpty(list) ? "(" + String.join(" " + getLogic(y.getLogic()) + " ", strList) + ")" : null; - } - - private String calcFieldRegex(String originField, SQLObj tableObj) { - originField = originField.replaceAll("[\\t\\n\\r]]", ""); - // 正则提取[xxx] - String regex = "\\[(.*?)]"; - Pattern pattern = Pattern.compile(regex); - Matcher matcher = pattern.matcher(originField); - Set ids = new HashSet<>(); - while (matcher.find()) { - String id = matcher.group(1); - ids.add(id); - } - if (CollectionUtils.isEmpty(ids)) { - return originField; - } - DatasetTableFieldExample datasetTableFieldExample = new DatasetTableFieldExample(); - datasetTableFieldExample.createCriteria().andIdIn(new ArrayList<>(ids)); - List calcFields = datasetTableFieldMapper.selectByExample(datasetTableFieldExample); - for (DatasetTableField ele : calcFields) { - originField = originField.replaceAll("\\[" + ele.getId() + "]", - String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), ele.getDataeaseName())); - } - return originField; - } - - private String sqlLimit(String sql, ChartViewWithBLOBs view) { - if (StringUtils.equalsIgnoreCase(view.getResultMode(), "custom")) { - return sql + " LIMIT 0," + view.getResultCount(); - } else { - return sql; - } - } - - public List dateformat() { - return JSONArray.parseArray("[\n" + - "{\"dateformat\": \"%Y-%m-%d\"},\n" + - "{\"dateformat\": \"%Y/%m/%d\"},\n" + - "{\"dateformat\": \"%Y%m%d\"},\n" + - "{\"dateformat\": \"%Y-%m-%d %H:%i:%S\"},\n" + - "{\"dateformat\": \"%Y/%m/%d %H:%i:%S\"},\n" + - "{\"dateformat\": \"%Y%m%d %H:%i:%S\"}\n" + - "]", Dateformat.class); - } -} +package io.dataease.provider.engine.mysql; + +import com.alibaba.fastjson.JSONArray; +import io.dataease.plugins.common.base.domain.ChartViewWithBLOBs; +import io.dataease.plugins.common.base.domain.DatasetTableField; +import io.dataease.plugins.common.base.domain.DatasetTableFieldExample; +import io.dataease.plugins.common.base.domain.Datasource; +import io.dataease.plugins.common.base.mapper.DatasetTableFieldMapper; +import io.dataease.plugins.common.constants.DeTypeConstants; +import io.dataease.plugins.common.constants.datasource.SQLConstants; +import io.dataease.plugins.common.constants.engine.MysqlConstants; +import io.dataease.plugins.common.dto.chart.ChartCustomFilterItemDTO; +import io.dataease.plugins.common.dto.chart.ChartFieldCustomFilterDTO; +import io.dataease.plugins.common.dto.chart.ChartViewFieldDTO; +import io.dataease.plugins.common.dto.datasource.DeSortField; +import io.dataease.plugins.common.dto.sqlObj.SQLObj; +import io.dataease.plugins.common.request.chart.ChartExtFilterRequest; +import io.dataease.plugins.common.request.permission.DataSetRowPermissionsTreeDTO; +import io.dataease.plugins.common.request.permission.DatasetRowPermissionsTreeItem; +import io.dataease.plugins.datasource.entity.Dateformat; +import io.dataease.plugins.datasource.entity.PageInfo; +import io.dataease.plugins.datasource.query.QueryProvider; +import io.dataease.plugins.datasource.query.Utils; +import org.apache.commons.collections4.CollectionUtils; +import org.apache.commons.lang3.ObjectUtils; +import org.apache.commons.lang3.StringUtils; +import org.springframework.stereotype.Service; +import org.stringtemplate.v4.ST; +import org.stringtemplate.v4.STGroup; +import org.stringtemplate.v4.STGroupFile; + +import javax.annotation.Resource; +import java.text.MessageFormat; +import java.text.SimpleDateFormat; +import java.util.*; +import java.util.regex.Matcher; +import java.util.regex.Pattern; +import java.util.stream.Collectors; + +import static io.dataease.plugins.common.constants.datasource.SQLConstants.TABLE_ALIAS_PREFIX; + +/** + * @Author gin + * @Date 2021/5/17 4:11 下午 + */ +@Service("engine_mysqlQueryProvider") +public class MysqlQueryProvider extends QueryProvider { + @Resource + private DatasetTableFieldMapper datasetTableFieldMapper; + + @Override + public Integer transFieldType(String field) { + switch (field) { + case "CHAR": + case "VARCHAR": + case "TEXT": + case "TINYTEXT": + case "MEDIUMTEXT": + case "LONGTEXT": + case "ENUM": + return 0;// 文本 + case "DATE": + case "TIME": + case "YEAR": + case "DATETIME": + case "TIMESTAMP": + return 1;// 时间 + case "INT": + case "SMALLINT": + case "MEDIUMINT": + case "INTEGER": + case "BIGINT": + case "LONG": //增加了LONG类型 + return 2;// 整型 + case "FLOAT": + case "DOUBLE": + case "DECIMAL": + return 3;// 浮点 + case "BIT": + case "TINYINT": + return 4;// 布尔 + default: + return 0; + } + } + + @Override + public String createSQLPreview(String sql, String orderBy) { + return "SELECT * FROM (" + sqlFix(sql) + ") AS tmp LIMIT 0,1000"; + } + + @Override + public String createQuerySQL(String table, List fields, boolean isGroup, Datasource ds, List fieldCustomFilter, List rowPermissionsTree) { + return createQuerySQL(table, fields, isGroup, ds, fieldCustomFilter, rowPermissionsTree, null); + } + + @Override + public String createQuerySQL(String table, List fields, boolean isGroup, Datasource ds, List fieldCustomFilter, List rowPermissionsTree, List sortFields) { + SQLObj tableObj = SQLObj.builder() + .tableName((table.startsWith("(") && table.endsWith(")")) ? table : String.format(MysqlConstants.KEYWORD_TABLE, table)) + .tableAlias(String.format(TABLE_ALIAS_PREFIX, 0)) + .build(); + List xFields = new ArrayList<>(); + List xOrders = new ArrayList<>(); + if (CollectionUtils.isNotEmpty(fields)) { + for (int i = 0; i < fields.size(); i++) { + DatasetTableField f = fields.get(i); + String originField; + if (ObjectUtils.isNotEmpty(f.getExtField()) && f.getExtField() == 2) { + // 解析origin name中有关联的字段生成sql表达式 + originField = calcFieldRegex(f.getOriginName(), tableObj); + } else if (ObjectUtils.isNotEmpty(f.getExtField()) && f.getExtField() == 1) { + originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), f.getDataeaseName()); + } else { + originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), f.getDataeaseName()); + } + String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_X_PREFIX, i); + String fieldName = ""; + // 处理横轴字段 + if (f.getDeExtractType() == 1) { + if (f.getDeType() == 2 || f.getDeType() == 3) { + fieldName = String.format(MysqlConstants.UNIX_TIMESTAMP, originField) + "*1000"; + } else { + fieldName = originField; + } + } else if (f.getDeExtractType() == 0) { + if (f.getDeType() == 2) { + fieldName = String.format(MysqlConstants.CAST, originField, MysqlConstants.DEFAULT_INT_FORMAT); + } else if (f.getDeType() == 3) { + fieldName = String.format(MysqlConstants.CAST, originField, MysqlConstants.DEFAULT_FLOAT_FORMAT); + } else if (f.getDeType() == 1) { + fieldName = StringUtils.isEmpty(f.getDateFormat()) ? String.format(MysqlConstants.STR_TO_DATE, originField, MysqlConstants.DEFAULT_DATE_FORMAT) : + String.format(MysqlConstants.DATE_FORMAT, String.format(MysqlConstants.STR_TO_DATE, originField, f.getDateFormat()), MysqlConstants.DEFAULT_DATE_FORMAT); + } else { + fieldName = originField; + } + } else { + if (f.getDeType() == 1) { + String cast = String.format(MysqlConstants.CAST, originField, MysqlConstants.DEFAULT_INT_FORMAT) + "/1000"; + fieldName = String.format(MysqlConstants.FROM_UNIXTIME, cast, MysqlConstants.DEFAULT_DATE_FORMAT); + } else if (f.getDeType() == 2) { + fieldName = String.format(MysqlConstants.CAST, originField, MysqlConstants.DEFAULT_INT_FORMAT); + } else if (f.getDeType() == 3) { + fieldName = String.format(MysqlConstants.CAST, originField, MysqlConstants.DEFAULT_FLOAT_FORMAT); + } else { + fieldName = originField; + } + } + xFields.add(SQLObj.builder() + .fieldName(fieldName) + .fieldAlias(fieldAlias) + .build()); + } + } + + STGroup stg = new STGroupFile(SQLConstants.SQL_TEMPLATE); + ST st_sql = stg.getInstanceOf("previewSql"); + st_sql.add("isGroup", isGroup); + if (CollectionUtils.isNotEmpty(xFields)) st_sql.add("groups", xFields); + if (ObjectUtils.isNotEmpty(tableObj)) st_sql.add("table", tableObj); + String customWheres = transCustomFilterList(tableObj, fieldCustomFilter); + String whereTrees = transFilterTrees(tableObj, rowPermissionsTree); + List wheres = new ArrayList<>(); + if (customWheres != null) wheres.add(customWheres); + if (whereTrees != null) wheres.add(whereTrees); + if (CollectionUtils.isNotEmpty(wheres)) st_sql.add("filters", wheres); + + if (CollectionUtils.isNotEmpty(sortFields)) { + int step = fields.size(); + for (int i = step; i < (step + sortFields.size()); i++) { + DeSortField deSortField = sortFields.get(i - step); + SQLObj order = buildSortField(deSortField, tableObj, i); + xOrders.add(order); + } + } + if (ObjectUtils.isNotEmpty(xOrders)) { + st_sql.add("orders", xOrders); + } + + return st_sql.render(); + } + + private SQLObj buildSortField(DeSortField f, SQLObj tableObj, int i) { + String originField; + if (ObjectUtils.isNotEmpty(f.getExtField()) && f.getExtField() == 2) { + // 解析origin name中有关联的字段生成sql表达式 + originField = calcFieldRegex(f.getOriginName(), tableObj); + } else if (ObjectUtils.isNotEmpty(f.getExtField()) && f.getExtField() == 1) { + originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), f.getDataeaseName()); + } else { + originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), f.getDataeaseName()); + } + String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_X_PREFIX, i); + String fieldName = ""; + // 处理横轴字段 + if (f.getDeExtractType() == 1) { + if (f.getDeType() == 2 || f.getDeType() == 3) { + fieldName = String.format(MysqlConstants.UNIX_TIMESTAMP, originField) + "*1000"; + } else { + fieldName = originField; + } + } else if (f.getDeExtractType() == 0) { + if (f.getDeType() == 2) { + fieldName = String.format(MysqlConstants.CAST, originField, MysqlConstants.DEFAULT_INT_FORMAT); + } else if (f.getDeType() == 3) { + fieldName = String.format(MysqlConstants.CAST, originField, MysqlConstants.DEFAULT_FLOAT_FORMAT); + } else if (f.getDeType() == 1) { + fieldName = StringUtils.isEmpty(f.getDateFormat()) ? String.format(MysqlConstants.STR_TO_DATE, originField, MysqlConstants.DEFAULT_DATE_FORMAT) : + String.format(MysqlConstants.DATE_FORMAT, String.format(MysqlConstants.STR_TO_DATE, originField, f.getDateFormat()), MysqlConstants.DEFAULT_DATE_FORMAT); + } else { + fieldName = originField; + } + } else { + if (f.getDeType() == 1) { + String cast = String.format(MysqlConstants.CAST, originField, MysqlConstants.DEFAULT_INT_FORMAT) + "/1000"; + fieldName = String.format(MysqlConstants.FROM_UNIXTIME, cast, MysqlConstants.DEFAULT_DATE_FORMAT); + } else if (f.getDeType() == 2) { + fieldName = String.format(MysqlConstants.CAST, originField, MysqlConstants.DEFAULT_INT_FORMAT); + } else if (f.getDeType() == 3) { + fieldName = String.format(MysqlConstants.CAST, originField, MysqlConstants.DEFAULT_FLOAT_FORMAT); + } else { + fieldName = originField; + } + } + SQLObj result = SQLObj.builder().orderField(originField).orderAlias(originField).orderDirection(f.getOrderDirection()).build(); + return result; + } + + @Override + public String createQuerySQLAsTmp(String sql, List fields, boolean isGroup, List fieldCustomFilter, List rowPermissionsTree, List sortFields) { + return createQuerySQL("(" + sql + ")", fields, isGroup, null, fieldCustomFilter, rowPermissionsTree, sortFields); + } + + @Override + public String createQuerySQLAsTmp(String sql, List fields, boolean isGroup, List fieldCustomFilter, List rowPermissionsTree) { + return createQuerySQL("(" + sql + ")", fields, isGroup, null, fieldCustomFilter, rowPermissionsTree); + } + + @Override + public String createQueryTableWithPage(String table, List fields, Integer page, Integer pageSize, Integer realSize, boolean isGroup, Datasource ds, List fieldCustomFilter, List rowPermissionsTree) { + return createQuerySQL(table, fields, isGroup, null, fieldCustomFilter, rowPermissionsTree) + " LIMIT " + (page - 1) * pageSize + "," + realSize; + } + + @Override + public String createQueryTableWithLimit(String table, List fields, Integer limit, boolean isGroup, Datasource ds, List fieldCustomFilter, List rowPermissionsTree) { + return createQuerySQL(table, fields, isGroup, null, fieldCustomFilter, rowPermissionsTree) + " LIMIT 0," + limit; + } + + @Override + public String createQuerySqlWithLimit(String sql, List fields, Integer limit, boolean isGroup, List fieldCustomFilter, List rowPermissionsTree) { + return createQuerySQLAsTmp(sql, fields, isGroup, fieldCustomFilter, rowPermissionsTree) + " LIMIT 0," + limit; + } + + @Override + public String createQuerySQLWithPage(String sql, List fields, Integer page, Integer pageSize, Integer realSize, boolean isGroup, List fieldCustomFilter, List rowPermissionsTree) { + return createQuerySQLAsTmp(sql, fields, isGroup, fieldCustomFilter, rowPermissionsTree) + " LIMIT " + (page - 1) * pageSize + "," + realSize; + } + + @Override + public String getSQL(String table, List xAxis, List yAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, Datasource ds, ChartViewWithBLOBs view) { + SQLObj tableObj = SQLObj.builder() + .tableName((table.startsWith("(") && table.endsWith(")")) ? table : String.format(MysqlConstants.KEYWORD_TABLE, table)) + .tableAlias(String.format(TABLE_ALIAS_PREFIX, 0)) + .build(); + List xFields = new ArrayList<>(); + List xOrders = new ArrayList<>(); + if (CollectionUtils.isNotEmpty(xAxis)) { + for (int i = 0; i < xAxis.size(); i++) { + ChartViewFieldDTO x = xAxis.get(i); + String originField; + if (ObjectUtils.isNotEmpty(x.getExtField()) && x.getExtField() == 2) { +// 计算字段和视图字段,规则为 函数([原始字段id]),这边把[原始字段id] 换成 表名.原始字段id +// 解析origin name中有关联的字段生成sql表达式 + originField = calcFieldRegex(x.getOriginName(), tableObj); + } else if (ObjectUtils.isNotEmpty(x.getExtField()) && x.getExtField() == 1) { + originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), x.getDataeaseName()); + } else { + originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), x.getDataeaseName()); + } + String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_X_PREFIX, i); + // 处理横轴字段 + xFields.add(getXFields(x, originField, fieldAlias)); + + // 处理横轴排序 + if (StringUtils.isNotEmpty(x.getSort()) && Utils.joinSort(x.getSort())) { + xOrders.add(SQLObj.builder() + .orderField(originField) + .orderAlias(fieldAlias) + .orderDirection(x.getSort()) + .build()); + } + } + } + List yFields = new ArrayList<>(); + List yWheres = new ArrayList<>(); + List yOrders = new ArrayList<>(); + if (CollectionUtils.isNotEmpty(yAxis)) { + for (int i = 0; i < yAxis.size(); i++) { + ChartViewFieldDTO y = yAxis.get(i); + String originField; + if (ObjectUtils.isNotEmpty(y.getExtField()) && y.getExtField() == 2) { + // 解析origin name中有关联的字段生成sql表达式 + originField = calcFieldRegex(y.getOriginName(), tableObj); + } else if (ObjectUtils.isNotEmpty(y.getExtField()) && y.getExtField() == 1) { + originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), y.getDataeaseName()); + } else { + originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), y.getDataeaseName()); + } + String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_Y_PREFIX, i); + // 处理纵轴字段 + yFields.add(getYFields(y, originField, fieldAlias)); + // 处理纵轴过滤 + yWheres.add(getYWheres(y, originField, fieldAlias)); + // 处理纵轴排序 + if (StringUtils.isNotEmpty(y.getSort()) && Utils.joinSort(y.getSort())) { + yOrders.add(SQLObj.builder() + .orderField(originField) + .orderAlias(fieldAlias) + .orderDirection(y.getSort()) + .build()); + } + } + } + // 处理视图中字段过滤 + String customWheres = transCustomFilterList(tableObj, fieldCustomFilter); + // 处理仪表板字段过滤 + String extWheres = transExtFilterList(tableObj, extFilterRequestList); + // row permissions tree + String whereTrees = transFilterTrees(tableObj, rowPermissionsTree); + // 构建sql所有参数 + List fields = new ArrayList<>(); + fields.addAll(xFields); + fields.addAll(yFields); + List wheres = new ArrayList<>(); + if (customWheres != null) wheres.add(customWheres); + if (extWheres != null) wheres.add(extWheres); + if (whereTrees != null) wheres.add(whereTrees); + List groups = new ArrayList<>(); + groups.addAll(xFields); + // 外层再次套sql + List orders = new ArrayList<>(); + orders.addAll(xOrders); + orders.addAll(yOrders); + List aggWheres = new ArrayList<>(); + aggWheres.addAll(yWheres.stream().filter(ObjectUtils::isNotEmpty).collect(Collectors.toList())); + + STGroup stg = new STGroupFile(SQLConstants.SQL_TEMPLATE); + ST st_sql = stg.getInstanceOf("querySql"); + if (CollectionUtils.isNotEmpty(xFields)) st_sql.add("groups", xFields); + if (CollectionUtils.isNotEmpty(yFields)) st_sql.add("aggregators", yFields); + if (CollectionUtils.isNotEmpty(wheres)) st_sql.add("filters", wheres); + if (ObjectUtils.isNotEmpty(tableObj)) st_sql.add("table", tableObj); + String sql = st_sql.render(); + + ST st = stg.getInstanceOf("querySql"); + SQLObj tableSQL = SQLObj.builder() + .tableName(String.format(MysqlConstants.BRACKETS, sql)) + .tableAlias(String.format(TABLE_ALIAS_PREFIX, 1)) + .build(); + if (CollectionUtils.isNotEmpty(aggWheres)) st.add("filters", aggWheres); + if (CollectionUtils.isNotEmpty(orders)) st.add("orders", orders); + if (ObjectUtils.isNotEmpty(tableSQL)) st.add("table", tableSQL); + return sqlLimit(st.render(), view); + } + + @Override + public String getSQLWithPage(boolean isTable, String table, List xAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, Datasource ds, ChartViewWithBLOBs view, PageInfo pageInfo) { + String limit = ((pageInfo.getGoPage() != null && pageInfo.getPageSize() != null) ? " LIMIT " + (pageInfo.getGoPage() - 1) * pageInfo.getPageSize() + "," + pageInfo.getPageSize() : ""); + if (isTable) { + return originalTableInfo(table, xAxis, fieldCustomFilter, rowPermissionsTree, extFilterRequestList, ds, view) + limit; + } else { + return originalTableInfo("(" + sqlFix(table) + ")", xAxis, fieldCustomFilter, rowPermissionsTree, extFilterRequestList, ds, view) + limit; + } + } + + private String originalTableInfo(String table, List xAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, Datasource ds, ChartViewWithBLOBs view) { + SQLObj tableObj = SQLObj.builder() + .tableName((table.startsWith("(") && table.endsWith(")")) ? table : String.format(MysqlConstants.KEYWORD_TABLE, table)) + .tableAlias(String.format(TABLE_ALIAS_PREFIX, 0)) + .build(); + List xFields = new ArrayList<>(); + List xOrders = new ArrayList<>(); + if (CollectionUtils.isNotEmpty(xAxis)) { + for (int i = 0; i < xAxis.size(); i++) { + ChartViewFieldDTO x = xAxis.get(i); + String originField; + if (ObjectUtils.isNotEmpty(x.getExtField()) && x.getExtField() == 2) { + // 解析origin name中有关联的字段生成sql表达式 + originField = calcFieldRegex(x.getOriginName(), tableObj); + } else if (ObjectUtils.isNotEmpty(x.getExtField()) && x.getExtField() == 1) { + originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), x.getDataeaseName()); + } else { + if (x.getDeType() == 2 || x.getDeType() == 3) { + originField = String.format(MysqlConstants.CAST, String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), x.getDataeaseName()), MysqlConstants.DEFAULT_FLOAT_FORMAT); + } else { + originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), x.getDataeaseName()); + } + } + String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_X_PREFIX, i); + // 处理横轴字段 + xFields.add(getXFields(x, originField, fieldAlias)); + + // 处理横轴排序 + if (StringUtils.isNotEmpty(x.getSort()) && Utils.joinSort(x.getSort())) { + xOrders.add(SQLObj.builder() + .orderField(originField) + .orderAlias(fieldAlias) + .orderDirection(x.getSort()) + .build()); + } + } + } + // 处理视图中字段过滤 + String customWheres = transCustomFilterList(tableObj, fieldCustomFilter); + // 处理仪表板字段过滤 + String extWheres = transExtFilterList(tableObj, extFilterRequestList); + // row permissions tree + String whereTrees = transFilterTrees(tableObj, rowPermissionsTree); + // 构建sql所有参数 + List fields = new ArrayList<>(); + fields.addAll(xFields); + List wheres = new ArrayList<>(); + if (customWheres != null) wheres.add(customWheres); + if (extWheres != null) wheres.add(extWheres); + if (whereTrees != null) wheres.add(whereTrees); + List groups = new ArrayList<>(); + groups.addAll(xFields); + // 外层再次套sql + List orders = new ArrayList<>(); + orders.addAll(xOrders); + + STGroup stg = new STGroupFile(SQLConstants.SQL_TEMPLATE); + ST st_sql = stg.getInstanceOf("previewSql"); + st_sql.add("isGroup", false); + if (CollectionUtils.isNotEmpty(xFields)) st_sql.add("groups", xFields); + if (CollectionUtils.isNotEmpty(wheres)) st_sql.add("filters", wheres); + if (ObjectUtils.isNotEmpty(tableObj)) st_sql.add("table", tableObj); + String sql = st_sql.render(); + + ST st = stg.getInstanceOf("previewSql"); + st.add("isGroup", false); + SQLObj tableSQL = SQLObj.builder() + .tableName(String.format(MysqlConstants.BRACKETS, sql)) + .tableAlias(String.format(TABLE_ALIAS_PREFIX, 1)) + .build(); + if (CollectionUtils.isNotEmpty(orders)) st.add("orders", orders); + if (ObjectUtils.isNotEmpty(tableSQL)) st.add("table", tableSQL); + return st.render(); + } + + @Override + public String getSQLTableInfo(String table, List xAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, Datasource ds, ChartViewWithBLOBs view) { + return sqlLimit(originalTableInfo(table, xAxis, fieldCustomFilter, rowPermissionsTree, extFilterRequestList, ds, view), view); + } + + @Override + public String getSQLAsTmpTableInfo(String sql, List xAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, Datasource ds, ChartViewWithBLOBs view) { + return getSQLTableInfo("(" + sqlFix(sql) + ")", xAxis, fieldCustomFilter, rowPermissionsTree, extFilterRequestList, null, view); + } + + @Override + public String getSQLAsTmp(String sql, List xAxis, List yAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, ChartViewWithBLOBs view) { + return getSQL("(" + sql + ")", xAxis, yAxis, fieldCustomFilter, rowPermissionsTree, extFilterRequestList, null, view); + } + + @Override + public String getSQLStack(String table, List xAxis, List yAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, List extStack, Datasource ds, ChartViewWithBLOBs view) { + SQLObj tableObj = SQLObj.builder() + .tableName((table.startsWith("(") && table.endsWith(")")) ? table : String.format(MysqlConstants.KEYWORD_TABLE, table)) + .tableAlias(String.format(TABLE_ALIAS_PREFIX, 0)) + .build(); + List xFields = new ArrayList<>(); + List xOrders = new ArrayList<>(); + List xList = new ArrayList<>(); + xList.addAll(xAxis); + xList.addAll(extStack); + if (CollectionUtils.isNotEmpty(xList)) { + for (int i = 0; i < xList.size(); i++) { + ChartViewFieldDTO x = xList.get(i); + String originField; + if (ObjectUtils.isNotEmpty(x.getExtField()) && x.getExtField() == 2) { + // 解析origin name中有关联的字段生成sql表达式 + originField = calcFieldRegex(x.getOriginName(), tableObj); + } else if (ObjectUtils.isNotEmpty(x.getExtField()) && x.getExtField() == 1) { + originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), x.getDataeaseName()); + } else { + originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), x.getDataeaseName()); + } + String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_X_PREFIX, i); + // 处理横轴字段 + xFields.add(getXFields(x, originField, fieldAlias)); + + // 处理横轴排序 + if (StringUtils.isNotEmpty(x.getSort()) && Utils.joinSort(x.getSort())) { + xOrders.add(SQLObj.builder() + .orderField(originField) + .orderAlias(fieldAlias) + .orderDirection(x.getSort()) + .build()); + } + } + } + List yFields = new ArrayList<>(); + List yWheres = new ArrayList<>(); + List yOrders = new ArrayList<>(); + if (CollectionUtils.isNotEmpty(yAxis)) { + for (int i = 0; i < yAxis.size(); i++) { + ChartViewFieldDTO y = yAxis.get(i); + String originField; + if (ObjectUtils.isNotEmpty(y.getExtField()) && y.getExtField() == 2) { + // 解析origin name中有关联的字段生成sql表达式 + originField = calcFieldRegex(y.getOriginName(), tableObj); + } else if (ObjectUtils.isNotEmpty(y.getExtField()) && y.getExtField() == 1) { + originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), y.getDataeaseName()); + } else { + originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), y.getDataeaseName()); + } + String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_Y_PREFIX, i); + // 处理纵轴字段 + yFields.add(getYFields(y, originField, fieldAlias)); + // 处理纵轴过滤 + yWheres.add(getYWheres(y, originField, fieldAlias)); + // 处理纵轴排序 + if (StringUtils.isNotEmpty(y.getSort()) && Utils.joinSort(y.getSort())) { + yOrders.add(SQLObj.builder() + .orderField(originField) + .orderAlias(fieldAlias) + .orderDirection(y.getSort()) + .build()); + } + } + } + // 处理视图中字段过滤 + String customWheres = transCustomFilterList(tableObj, fieldCustomFilter); + // 处理仪表板字段过滤 + String extWheres = transExtFilterList(tableObj, extFilterRequestList); + // row permissions tree + String whereTrees = transFilterTrees(tableObj, rowPermissionsTree); + // 构建sql所有参数 + List fields = new ArrayList<>(); + fields.addAll(xFields); + fields.addAll(yFields); + List wheres = new ArrayList<>(); + if (customWheres != null) wheres.add(customWheres); + if (extWheres != null) wheres.add(extWheres); + if (whereTrees != null) wheres.add(whereTrees); + List groups = new ArrayList<>(); + groups.addAll(xFields); + // 外层再次套sql + List orders = new ArrayList<>(); + orders.addAll(xOrders); + orders.addAll(yOrders); + List aggWheres = new ArrayList<>(); + aggWheres.addAll(yWheres.stream().filter(ObjectUtils::isNotEmpty).collect(Collectors.toList())); + + STGroup stg = new STGroupFile(SQLConstants.SQL_TEMPLATE); + ST st_sql = stg.getInstanceOf("querySql"); + if (CollectionUtils.isNotEmpty(xFields)) st_sql.add("groups", xFields); + if (CollectionUtils.isNotEmpty(yFields)) st_sql.add("aggregators", yFields); + if (CollectionUtils.isNotEmpty(wheres)) st_sql.add("filters", wheres); + if (ObjectUtils.isNotEmpty(tableObj)) st_sql.add("table", tableObj); + String sql = st_sql.render(); + + ST st = stg.getInstanceOf("querySql"); + SQLObj tableSQL = SQLObj.builder() + .tableName(String.format(MysqlConstants.BRACKETS, sql)) + .tableAlias(String.format(TABLE_ALIAS_PREFIX, 1)) + .build(); + if (CollectionUtils.isNotEmpty(aggWheres)) st.add("filters", aggWheres); + if (CollectionUtils.isNotEmpty(orders)) st.add("orders", orders); + if (ObjectUtils.isNotEmpty(tableSQL)) st.add("table", tableSQL); + return sqlLimit(st.render(), view); + } + + @Override + public String getSQLAsTmpStack(String table, List xAxis, List yAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, List extStack, ChartViewWithBLOBs view) { + return getSQLStack("(" + table + ")", xAxis, yAxis, fieldCustomFilter, rowPermissionsTree, extFilterRequestList, extStack, null, view); + } + + @Override + public String getSQLScatter(String table, List xAxis, List yAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, List extBubble, Datasource ds, ChartViewWithBLOBs view) { + SQLObj tableObj = SQLObj.builder() + .tableName((table.startsWith("(") && table.endsWith(")")) ? table : String.format(MysqlConstants.KEYWORD_TABLE, table)) + .tableAlias(String.format(TABLE_ALIAS_PREFIX, 0)) + .build(); + List xFields = new ArrayList<>(); + List xOrders = new ArrayList<>(); + if (CollectionUtils.isNotEmpty(xAxis)) { + for (int i = 0; i < xAxis.size(); i++) { + ChartViewFieldDTO x = xAxis.get(i); + String originField; + if (ObjectUtils.isNotEmpty(x.getExtField()) && x.getExtField() == 2) { + // 解析origin name中有关联的字段生成sql表达式 + originField = calcFieldRegex(x.getOriginName(), tableObj); + } else if (ObjectUtils.isNotEmpty(x.getExtField()) && x.getExtField() == 1) { + originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), x.getDataeaseName()); + } else { + originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), x.getDataeaseName()); + } + String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_X_PREFIX, i); + // 处理横轴字段 + xFields.add(getXFields(x, originField, fieldAlias)); + + // 处理横轴排序 + if (StringUtils.isNotEmpty(x.getSort()) && Utils.joinSort(x.getSort())) { + xOrders.add(SQLObj.builder() + .orderField(originField) + .orderAlias(fieldAlias) + .orderDirection(x.getSort()) + .build()); + } + } + } + List yFields = new ArrayList<>(); + List yWheres = new ArrayList<>(); + List yOrders = new ArrayList<>(); + List yList = new ArrayList<>(); + yList.addAll(yAxis); + yList.addAll(extBubble); + if (CollectionUtils.isNotEmpty(yList)) { + for (int i = 0; i < yList.size(); i++) { + ChartViewFieldDTO y = yList.get(i); + String originField; + if (ObjectUtils.isNotEmpty(y.getExtField()) && y.getExtField() == 2) { + // 解析origin name中有关联的字段生成sql表达式 + originField = calcFieldRegex(y.getOriginName(), tableObj); + } else if (ObjectUtils.isNotEmpty(y.getExtField()) && y.getExtField() == 1) { + originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), y.getDataeaseName()); + } else { + originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), y.getDataeaseName()); + } + String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_Y_PREFIX, i); + // 处理纵轴字段 + yFields.add(getYFields(y, originField, fieldAlias)); + // 处理纵轴过滤 + yWheres.add(getYWheres(y, originField, fieldAlias)); + // 处理纵轴排序 + if (StringUtils.isNotEmpty(y.getSort()) && Utils.joinSort(y.getSort())) { + yOrders.add(SQLObj.builder() + .orderField(originField) + .orderAlias(fieldAlias) + .orderDirection(y.getSort()) + .build()); + } + } + } + // 处理视图中字段过滤 + String customWheres = transCustomFilterList(tableObj, fieldCustomFilter); + // 处理仪表板字段过滤 + String extWheres = transExtFilterList(tableObj, extFilterRequestList); + // row permissions tree + String whereTrees = transFilterTrees(tableObj, rowPermissionsTree); + // 构建sql所有参数 + List fields = new ArrayList<>(); + fields.addAll(xFields); + fields.addAll(yFields); + List wheres = new ArrayList<>(); + if (customWheres != null) wheres.add(customWheres); + if (extWheres != null) wheres.add(extWheres); + if (whereTrees != null) wheres.add(whereTrees); + List groups = new ArrayList<>(); + groups.addAll(xFields); + // 外层再次套sql + List orders = new ArrayList<>(); + orders.addAll(xOrders); + orders.addAll(yOrders); + List aggWheres = new ArrayList<>(); + aggWheres.addAll(yWheres.stream().filter(ObjectUtils::isNotEmpty).collect(Collectors.toList())); + + STGroup stg = new STGroupFile(SQLConstants.SQL_TEMPLATE); + ST st_sql = stg.getInstanceOf("querySql"); + if (CollectionUtils.isNotEmpty(xFields)) st_sql.add("groups", xFields); + if (CollectionUtils.isNotEmpty(yFields)) st_sql.add("aggregators", yFields); + if (CollectionUtils.isNotEmpty(wheres)) st_sql.add("filters", wheres); + if (ObjectUtils.isNotEmpty(tableObj)) st_sql.add("table", tableObj); + String sql = st_sql.render(); + + ST st = stg.getInstanceOf("querySql"); + SQLObj tableSQL = SQLObj.builder() + .tableName(String.format(MysqlConstants.BRACKETS, sql)) + .tableAlias(String.format(TABLE_ALIAS_PREFIX, 1)) + .build(); + if (CollectionUtils.isNotEmpty(aggWheres)) st.add("filters", aggWheres); + if (CollectionUtils.isNotEmpty(orders)) st.add("orders", orders); + if (ObjectUtils.isNotEmpty(tableSQL)) st.add("table", tableSQL); + return sqlLimit(st.render(), view); + } + + @Override + public String getSQLAsTmpScatter(String table, List xAxis, List yAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, List extBubble, ChartViewWithBLOBs view) { + return getSQLScatter("(" + table + ")", xAxis, yAxis, fieldCustomFilter, rowPermissionsTree, extFilterRequestList, extBubble, null, view); + } + + @Override + public String searchTable(String table) { + return "SELECT table_name FROM information_schema.TABLES WHERE table_name ='" + table + "'"; + } + + @Override + public String getSQLSummary(String table, List yAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, ChartViewWithBLOBs view, Datasource ds) { + // 字段汇总 排序等 + SQLObj tableObj = SQLObj.builder() + .tableName((table.startsWith("(") && table.endsWith(")")) ? table : String.format(MysqlConstants.KEYWORD_TABLE, table)) + .tableAlias(String.format(TABLE_ALIAS_PREFIX, 0)) + .build(); + List yFields = new ArrayList<>(); + List yWheres = new ArrayList<>(); + List yOrders = new ArrayList<>(); + if (CollectionUtils.isNotEmpty(yAxis)) { + for (int i = 0; i < yAxis.size(); i++) { + ChartViewFieldDTO y = yAxis.get(i); + String originField; + if (ObjectUtils.isNotEmpty(y.getExtField()) && y.getExtField() == 2) { + // 解析origin name中有关联的字段生成sql表达式 + originField = calcFieldRegex(y.getOriginName(), tableObj); + } else if (ObjectUtils.isNotEmpty(y.getExtField()) && y.getExtField() == 1) { + originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), y.getDataeaseName()); + } else { + originField = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), y.getDataeaseName()); + } + String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_Y_PREFIX, i); + // 处理纵轴字段 + yFields.add(getYFields(y, originField, fieldAlias)); + // 处理纵轴过滤 + yWheres.add(getYWheres(y, originField, fieldAlias)); + // 处理纵轴排序 + if (StringUtils.isNotEmpty(y.getSort()) && Utils.joinSort(y.getSort())) { + yOrders.add(SQLObj.builder() + .orderField(originField) + .orderAlias(fieldAlias) + .orderDirection(y.getSort()) + .build()); + } + } + } + // 处理视图中字段过滤 + String customWheres = transCustomFilterList(tableObj, fieldCustomFilter); + // 处理仪表板字段过滤 + String extWheres = transExtFilterList(tableObj, extFilterRequestList); + // row permissions tree + String whereTrees = transFilterTrees(tableObj, rowPermissionsTree); + // 构建sql所有参数 + List fields = new ArrayList<>(); + fields.addAll(yFields); + List wheres = new ArrayList<>(); + if (customWheres != null) wheres.add(customWheres); + if (extWheres != null) wheres.add(extWheres); + if (whereTrees != null) wheres.add(whereTrees); + List groups = new ArrayList<>(); + // 外层再次套sql + List orders = new ArrayList<>(); + orders.addAll(yOrders); + List aggWheres = new ArrayList<>(); + aggWheres.addAll(yWheres.stream().filter(ObjectUtils::isNotEmpty).collect(Collectors.toList())); + + STGroup stg = new STGroupFile(SQLConstants.SQL_TEMPLATE); + ST st_sql = stg.getInstanceOf("querySql"); + if (CollectionUtils.isNotEmpty(yFields)) st_sql.add("aggregators", yFields); + if (CollectionUtils.isNotEmpty(wheres)) st_sql.add("filters", wheres); + if (ObjectUtils.isNotEmpty(tableObj)) st_sql.add("table", tableObj); + String sql = st_sql.render(); + + ST st = stg.getInstanceOf("querySql"); + SQLObj tableSQL = SQLObj.builder() + .tableName(String.format(MysqlConstants.BRACKETS, sql)) + .tableAlias(String.format(TABLE_ALIAS_PREFIX, 1)) + .build(); + if (CollectionUtils.isNotEmpty(aggWheres)) st.add("filters", aggWheres); + if (CollectionUtils.isNotEmpty(orders)) st.add("orders", orders); + if (ObjectUtils.isNotEmpty(tableSQL)) st.add("table", tableSQL); + return sqlLimit(st.render(), view); + } + + @Override + public String getSQLSummaryAsTmp(String sql, List yAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, ChartViewWithBLOBs view) { + return getSQLSummary("(" + sql + ")", yAxis, fieldCustomFilter, rowPermissionsTree, extFilterRequestList, view, null); + } + + @Override + public String wrapSql(String sql) { + sql = sql.trim(); + if (sql.lastIndexOf(";") == (sql.length() - 1)) { + sql = sql.substring(0, sql.length() - 1); + } + String tmpSql = "SELECT * FROM (" + sql + ") AS tmp " + " LIMIT 0"; + return tmpSql; + } + + @Override + public String createRawQuerySQL(String table, List fields, Datasource ds) { + String[] array = fields.stream().map(f -> { + StringBuilder stringBuilder = new StringBuilder(); + stringBuilder.append("`").append(f.getDataeaseName()).append("` AS ").append(f.getDataeaseName()); + return stringBuilder.toString(); + }).toArray(String[]::new); + return MessageFormat.format("SELECT {0} FROM {1} ORDER BY null", StringUtils.join(array, ","), table); + } + + @Override + public String createRawQuerySQLAsTmp(String sql, List fields) { + return createRawQuerySQL(" (" + sqlFix(sql) + ") AS tmp ", fields, null); + } + + @Override + public String transTreeItem(SQLObj tableObj, DatasetRowPermissionsTreeItem item) { + String res = null; + DatasetTableField field = item.getField(); + if (ObjectUtils.isEmpty(field)) { + return null; + } + String whereName = ""; + String originName; + if (ObjectUtils.isNotEmpty(field.getExtField()) && field.getExtField() == 2) { + // 解析origin name中有关联的字段生成sql表达式 + originName = calcFieldRegex(field.getOriginName(), tableObj); + } else if (ObjectUtils.isNotEmpty(field.getExtField()) && field.getExtField() == 1) { + originName = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), field.getDataeaseName()); + } else { + originName = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), field.getDataeaseName()); + } + + if (field.getDeType() == 1) { + if (field.getDeExtractType() == 0 || field.getDeExtractType() == 5 || field.getDeExtractType() == 1) { + whereName = String.format(MysqlConstants.STR_TO_DATE, originName, StringUtils.isNotEmpty(field.getDateFormat()) ? field.getDateFormat() : MysqlConstants.DEFAULT_DATE_FORMAT); + } + if (field.getDeExtractType() == 2 || field.getDeExtractType() == 3 || field.getDeExtractType() == 4) { + String cast = String.format(MysqlConstants.CAST, originName, MysqlConstants.DEFAULT_INT_FORMAT) + "/1000"; + whereName = String.format(MysqlConstants.FROM_UNIXTIME, cast, MysqlConstants.DEFAULT_DATE_FORMAT); + } + } else if (field.getDeType() == 2 || field.getDeType() == 3) { + if (field.getDeExtractType() == 0 || field.getDeExtractType() == 5) { + whereName = String.format(MysqlConstants.CAST, originName, MysqlConstants.DEFAULT_FLOAT_FORMAT); + } + if (field.getDeExtractType() == 1) { + whereName = String.format(MysqlConstants.UNIX_TIMESTAMP, originName) + "*1000"; + } + if (field.getDeExtractType() == 2 || field.getDeExtractType() == 3 || field.getDeExtractType() == 4) { + whereName = originName; + } + } else if (field.getDeType() == 0 && field.getDeExtractType() == 0) { + whereName = String.format(MysqlConstants.CAST, originName, MysqlConstants.CHAR); + } else { + whereName = originName; + } + + if (StringUtils.equalsIgnoreCase(item.getFilterType(), "enum")) { + if (CollectionUtils.isNotEmpty(item.getEnumValue())) { + res = "(" + whereName + " IN ('" + String.join("','", item.getEnumValue()) + "'))"; + } + } else { + String value = item.getValue(); + String whereTerm = transMysqlFilterTerm(item.getTerm()); + String whereValue = ""; + + if (StringUtils.equalsIgnoreCase(item.getTerm(), "null")) { + whereValue = ""; + } else if (StringUtils.equalsIgnoreCase(item.getTerm(), "not_null")) { + whereValue = ""; + } else if (StringUtils.equalsIgnoreCase(item.getTerm(), "empty")) { + whereValue = "''"; + } else if (StringUtils.equalsIgnoreCase(item.getTerm(), "not_empty")) { + whereValue = "''"; + } else if (StringUtils.containsIgnoreCase(item.getTerm(), "in")) { + whereValue = "('" + StringUtils.join(value, "','") + "')"; + } else if (StringUtils.containsIgnoreCase(item.getTerm(), "like")) { + whereValue = "'%" + value + "%'"; + } else { + whereValue = String.format(MysqlConstants.WHERE_VALUE_VALUE, value); + } + SQLObj build = SQLObj.builder() + .whereField(whereName) + .whereTermAndValue(whereTerm + whereValue) + .build(); + res = build.getWhereField() + " " + build.getWhereTermAndValue(); + } + return res; + } + + @Override + public String convertTableToSql(String tableName, Datasource ds) { + return createSQLPreview("SELECT * FROM " + String.format(MysqlConstants.KEYWORD_TABLE, tableName), null); + } + + private String sqlFix(String sql) { + if (sql.lastIndexOf(";") == (sql.length() - 1)) { + sql = sql.substring(0, sql.length() - 1); + } + return sql; + } + + public String transMysqlFilterTerm(String term) { + switch (term) { + case "eq": + return " = "; + case "not_eq": + return " <> "; + case "lt": + return " < "; + case "le": + return " <= "; + case "gt": + return " > "; + case "ge": + return " >= "; + case "in": + return " IN "; + case "not in": + return " NOT IN "; + case "like": + return " LIKE "; + case "not like": + return " NOT LIKE "; + case "null": + return " IS NULL "; + case "not_null": + return " IS NOT NULL "; + case "empty": + return " = "; + case "not_empty": + return " <> "; + case "between": + return " BETWEEN "; + default: + return ""; + } + } + + public String transCustomFilterList(SQLObj tableObj, List requestList) { + if (CollectionUtils.isEmpty(requestList)) { + return null; + } + List res = new ArrayList<>(); + + for (ChartFieldCustomFilterDTO request : requestList) { + List list = new ArrayList<>(); + DatasetTableField field = request.getField(); + + if (ObjectUtils.isEmpty(field)) { + continue; + } + String whereName = ""; + String originName; + if (ObjectUtils.isNotEmpty(field.getExtField()) && field.getExtField() == 2) { + // 解析origin name中有关联的字段生成sql表达式 + originName = calcFieldRegex(field.getOriginName(), tableObj); + } else if (ObjectUtils.isNotEmpty(field.getExtField()) && field.getExtField() == 1) { + originName = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), field.getDataeaseName()); + } else { + originName = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), field.getDataeaseName()); + } + + if (field.getDeType() == 1) { + if (field.getDeExtractType() == 0 || field.getDeExtractType() == 5 || field.getDeExtractType() == 1) { + whereName = String.format(MysqlConstants.STR_TO_DATE, originName, StringUtils.isNotEmpty(field.getDateFormat()) ? field.getDateFormat() : MysqlConstants.DEFAULT_DATE_FORMAT); + } + if (field.getDeExtractType() == 2 || field.getDeExtractType() == 3 || field.getDeExtractType() == 4) { + String cast = String.format(MysqlConstants.CAST, originName, MysqlConstants.DEFAULT_INT_FORMAT) + "/1000"; + whereName = String.format(MysqlConstants.FROM_UNIXTIME, cast, MysqlConstants.DEFAULT_DATE_FORMAT); + } + } else if (field.getDeType() == 2 || field.getDeType() == 3) { + if (field.getDeExtractType() == 0 || field.getDeExtractType() == 5) { + whereName = String.format(MysqlConstants.CAST, originName, MysqlConstants.DEFAULT_FLOAT_FORMAT); + } + if (field.getDeExtractType() == 1) { + whereName = String.format(MysqlConstants.UNIX_TIMESTAMP, originName) + "*1000"; + } + if (field.getDeExtractType() == 2 || field.getDeExtractType() == 3 || field.getDeExtractType() == 4) { + whereName = originName; + } + } else if (field.getDeType() == 0 && field.getDeExtractType() == 0) { + whereName = String.format(MysqlConstants.CAST, originName, MysqlConstants.CHAR); + } else { + whereName = originName; + } + + if (StringUtils.equalsIgnoreCase(request.getFilterType(), "enum")) { + if (CollectionUtils.isNotEmpty(request.getEnumCheckField())) { + res.add("(" + whereName + " IN ('" + String.join("','", request.getEnumCheckField()) + "'))"); + } + } else { + List filter = request.getFilter(); + for (ChartCustomFilterItemDTO filterItemDTO : filter) { + String value = filterItemDTO.getValue(); + String whereTerm = transMysqlFilterTerm(filterItemDTO.getTerm()); + String whereValue = ""; + + if (StringUtils.equalsIgnoreCase(filterItemDTO.getTerm(), "null")) { + whereValue = ""; + } else if (StringUtils.equalsIgnoreCase(filterItemDTO.getTerm(), "not_null")) { + whereValue = ""; + } else if (StringUtils.equalsIgnoreCase(filterItemDTO.getTerm(), "empty")) { + whereValue = "''"; + } else if (StringUtils.equalsIgnoreCase(filterItemDTO.getTerm(), "not_empty")) { + whereValue = "''"; + } else if (StringUtils.containsIgnoreCase(filterItemDTO.getTerm(), "in")) { + whereValue = "('" + StringUtils.join(value, "','") + "')"; + } else if (StringUtils.containsIgnoreCase(filterItemDTO.getTerm(), "like")) { + whereValue = "'%" + value + "%'"; + } else { + // Doris field type test + /*if (field.getDeExtractType() == 2 || field.getDeExtractType() == 3 || field.getDeExtractType() == 4) { + whereValue = String.format(MysqlConstants.WHERE_NUMBER_VALUE, value); + } else { + whereValue = String.format(MysqlConstants.WHERE_VALUE_VALUE, value); + }*/ + whereValue = String.format(MysqlConstants.WHERE_VALUE_VALUE, value); + } + list.add(SQLObj.builder() + .whereField(whereName) + .whereTermAndValue(whereTerm + whereValue) + .build()); + } + + List strList = new ArrayList<>(); + list.forEach(ele -> strList.add(ele.getWhereField() + " " + ele.getWhereTermAndValue())); + if (CollectionUtils.isNotEmpty(list)) { + res.add("(" + String.join(" " + getLogic(request.getLogic()) + " ", strList) + ")"); + } + } + } + return CollectionUtils.isNotEmpty(res) ? "(" + String.join(" AND ", res) + ")" : null; + } + + private String reflectFieldName(DatasetTableField field) { + return field.getDataeaseName(); + } + + public String transExtFilterList(SQLObj tableObj, List requestList) { + if (CollectionUtils.isEmpty(requestList)) { + return null; + } + List list = new ArrayList<>(); + for (ChartExtFilterRequest request : requestList) { + List value = request.getValue(); + + List whereNameList = new ArrayList<>(); + List fieldList = new ArrayList<>(); + if (request.getIsTree()) { + fieldList.addAll(request.getDatasetTableFieldList()); + } else { + fieldList.add(request.getDatasetTableField()); + } + + for (DatasetTableField field : fieldList) { + if (CollectionUtils.isEmpty(value) || ObjectUtils.isEmpty(field)) { + continue; + } + String whereName = ""; + + + String originName; + if (ObjectUtils.isNotEmpty(field.getExtField()) && field.getExtField() == 2) { + // 解析origin name中有关联的字段生成sql表达式 + originName = calcFieldRegex(field.getOriginName(), tableObj); + } else if (ObjectUtils.isNotEmpty(field.getExtField()) && field.getExtField() == 1) { + originName = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), field.getDataeaseName()); + } else { + originName = String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), field.getDataeaseName()); + } + + if (field.getDeType() == 1) { + String format = transDateFormat(request.getDateStyle(), request.getDatePattern()); + if (field.getDeExtractType() == 0 || field.getDeExtractType() == 5 || field.getDeExtractType() == 1) { + whereName = String.format(MysqlConstants.DATE_FORMAT, originName, format); + } + if (field.getDeExtractType() == 2 || field.getDeExtractType() == 3 || field.getDeExtractType() == 4) { + whereName = originName; + } + } else if (field.getDeType() == 0 && field.getDeExtractType() == 0) { + whereName = String.format(MysqlConstants.CAST, originName, MysqlConstants.CHAR); + } else if (field.getDeType() == 2 || field.getDeType() == 3) { + if (field.getDeExtractType() == 0 || field.getDeExtractType() == 5) { + whereName = String.format(MysqlConstants.CAST, originName, MysqlConstants.DEFAULT_FLOAT_FORMAT); + } + if (field.getDeExtractType() == 1) { + whereName = String.format(MysqlConstants.UNIX_TIMESTAMP, originName) + "*1000"; + } + if (field.getDeExtractType() == 2 || field.getDeExtractType() == 3 || field.getDeExtractType() == 4) { + whereName = originName; + } + } else { + whereName = originName; + } + whereNameList.add(whereName); + } + + String whereName = ""; + if (request.getIsTree()) { + whereName = "CONCAT(" + StringUtils.join(whereNameList, ",',',") + ")"; + } else { + whereName = whereNameList.get(0); + } + String whereTerm = transMysqlFilterTerm(request.getOperator()); + String whereValue = ""; + + if (StringUtils.containsIgnoreCase(request.getOperator(), "in")) { + whereValue = "('" + StringUtils.join(value, "','") + "')"; + } else if (StringUtils.containsIgnoreCase(request.getOperator(), "like")) { + whereValue = "'%" + value.get(0) + "%'"; + } else if (StringUtils.containsIgnoreCase(request.getOperator(), "between")) { + if (request.getDatasetTableField().getDeType() == 1) { + if (request.getDatasetTableField().getDeExtractType() == 2 + || request.getDatasetTableField().getDeExtractType() == 3 + || request.getDatasetTableField().getDeExtractType() == 4) { + whereValue = String.format(MysqlConstants.WHERE_BETWEEN, value.get(0), value.get(1)); + } else { + SimpleDateFormat simpleDateFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss"); + String startTime = simpleDateFormat.format(new Date(Long.parseLong(value.get(0)))); + String endTime = simpleDateFormat.format(new Date(Long.parseLong(value.get(1)))); + whereValue = String.format(MysqlConstants.WHERE_BETWEEN, startTime, endTime); + } + } else { + whereValue = String.format(MysqlConstants.WHERE_BETWEEN, value.get(0), value.get(1)); + } + } else { + whereValue = String.format(MysqlConstants.WHERE_VALUE_VALUE, value.get(0)); + } + list.add(SQLObj.builder() + .whereField(whereName) + .whereTermAndValue(whereTerm + whereValue) + .build()); + } + List strList = new ArrayList<>(); + list.forEach(ele -> strList.add(ele.getWhereField() + " " + ele.getWhereTermAndValue())); + return CollectionUtils.isNotEmpty(list) ? "(" + String.join(" AND ", strList) + ")" : null; + } + + private String transDateFormat(String dateStyle, String datePattern) { + String split = "-"; + if (StringUtils.equalsIgnoreCase(datePattern, "date_sub")) { + split = "-"; + } else if (StringUtils.equalsIgnoreCase(datePattern, "date_split")) { + split = "/"; + } else { + split = "-"; + } + + if (StringUtils.isEmpty(dateStyle)) { + return "%Y-%m-%d %H:%i:%S"; + } + + switch (dateStyle) { + case "y": + return "%Y"; + case "y_Q": + return "CONCAT(%s,'" + split + "',%s)"; + case "y_M": + return "%Y" + split + "%m"; + case "y_W": + return "%Y" + split + "%u"; + case "y_M_d": + return "%Y" + split + "%m" + split + "%d"; + case "H_m_s": + return "%H:%i:%S"; + case "y_M_d_H_m": + return "%Y" + split + "%m" + split + "%d" + " %H:%i"; + case "y_M_d_H_m_s": + return "%Y" + split + "%m" + split + "%d" + " %H:%i:%S"; + default: + return "%Y-%m-%d %H:%i:%S"; + } + } + + private SQLObj getXFields(ChartViewFieldDTO x, String originField, String fieldAlias) { + String fieldName = ""; + if (x.getDeExtractType() == 1) { + if (x.getDeType() == 2 || x.getDeType() == 3) { + fieldName = String.format(MysqlConstants.UNIX_TIMESTAMP, originField) + "*1000"; + } else if (x.getDeType() == 1) { + String format = transDateFormat(x.getDateStyle(), x.getDatePattern()); + if (StringUtils.equalsIgnoreCase(x.getDateStyle(), "y_Q")) { + fieldName = String.format(format, + String.format(MysqlConstants.DATE_FORMAT, originField, "%Y"), + String.format(MysqlConstants.QUARTER, originField)); + } else { + fieldName = String.format(MysqlConstants.DATE_FORMAT, originField, format); + } + } else { + fieldName = originField; + } + } else { + if (x.getDeType() == 1) { + String format = transDateFormat(x.getDateStyle(), x.getDatePattern()); + if (x.getDeExtractType() == 0) { + if (StringUtils.equalsIgnoreCase(x.getDateStyle(), "y_Q")) { + fieldName = String.format(format, + String.format(MysqlConstants.DATE_FORMAT, String.format(MysqlConstants.STR_TO_DATE, originField, MysqlConstants.DEFAULT_DATE_FORMAT), "%Y"), + String.format(MysqlConstants.QUARTER, String.format(MysqlConstants.STR_TO_DATE, originField, MysqlConstants.DEFAULT_DATE_FORMAT))); + } else { + fieldName = String.format(MysqlConstants.DATE_FORMAT, originField, format); + } + } else { + String cast = String.format(MysqlConstants.CAST, originField, MysqlConstants.DEFAULT_INT_FORMAT) + "/1000"; + String from_unixtime = String.format(MysqlConstants.FROM_UNIXTIME, cast, MysqlConstants.DEFAULT_DATE_FORMAT); + if (StringUtils.equalsIgnoreCase(x.getDateStyle(), "y_Q")) { + fieldName = String.format(format, + String.format(MysqlConstants.DATE_FORMAT, from_unixtime, "%Y"), + String.format(MysqlConstants.QUARTER, from_unixtime)); + } else { + fieldName = String.format(MysqlConstants.DATE_FORMAT, from_unixtime, format); + } + } + } else if (x.getDeType() == 0 && x.getDeExtractType() == 0) { + fieldName = String.format(MysqlConstants.CAST, originField, MysqlConstants.CHAR); + } else { + if (x.getDeType() == DeTypeConstants.DE_INT) { + fieldName = String.format(MysqlConstants.CAST, originField, MysqlConstants.DEFAULT_INT_FORMAT); + } else if (x.getDeType() == DeTypeConstants.DE_FLOAT) { + fieldName = String.format(MysqlConstants.CAST, originField, MysqlConstants.DEFAULT_FLOAT_FORMAT); + } else { + fieldName = originField; + } + } + } + return SQLObj.builder() + .fieldName(fieldName) + .fieldAlias(fieldAlias) + .build(); + } + + private List getXWheres(ChartViewFieldDTO x, String originField, String fieldAlias) { + List list = new ArrayList<>(); + if (CollectionUtils.isNotEmpty(x.getFilter()) && x.getFilter().size() > 0) { + x.getFilter().forEach(f -> { + String whereName = ""; + String whereTerm = transMysqlFilterTerm(f.getTerm()); + String whereValue = ""; + if (x.getDeType() == 1 && x.getDeExtractType() != 1) { + String cast = String.format(MysqlConstants.CAST, originField, MysqlConstants.DEFAULT_INT_FORMAT) + "/1000"; + whereName = String.format(MysqlConstants.FROM_UNIXTIME, cast, MysqlConstants.DEFAULT_DATE_FORMAT); + } else { + whereName = originField; + } + if (StringUtils.equalsIgnoreCase(f.getTerm(), "null")) { + whereValue = ""; + } else if (StringUtils.equalsIgnoreCase(f.getTerm(), "not_null")) { + whereValue = ""; + } else if (StringUtils.equalsIgnoreCase(f.getTerm(), "empty")) { + whereValue = "''"; + } else if (StringUtils.equalsIgnoreCase(f.getTerm(), "not_empty")) { + whereValue = "''"; + } else if (StringUtils.containsIgnoreCase(f.getTerm(), "in")) { + whereValue = "('" + StringUtils.join(f.getValue(), "','") + "')"; + } else if (StringUtils.containsIgnoreCase(f.getTerm(), "like")) { + whereValue = "'%" + f.getValue() + "%'"; + } else { + whereValue = String.format(MysqlConstants.WHERE_VALUE_VALUE, f.getValue()); + } + list.add(SQLObj.builder() + .whereField(whereName) + .whereAlias(fieldAlias) + .whereTermAndValue(whereTerm + whereValue) + .build()); + }); + } + return list; + } + + private SQLObj getYFields(ChartViewFieldDTO y, String originField, String fieldAlias) { + String fieldName = ""; + if (StringUtils.equalsIgnoreCase(y.getDataeaseName(), "*")) { + fieldName = MysqlConstants.AGG_COUNT; + } else if (SQLConstants.DIMENSION_TYPE.contains(y.getDeType())) { + if (StringUtils.equalsIgnoreCase(y.getSummary(), "count_distinct")) { + fieldName = String.format(MysqlConstants.AGG_FIELD, "COUNT", "DISTINCT " + originField); + } else { + fieldName = String.format(MysqlConstants.AGG_FIELD, y.getSummary(), originField); + } + } else { + if (StringUtils.equalsIgnoreCase(y.getSummary(), "avg") || StringUtils.containsIgnoreCase(y.getSummary(), "pop")) { + String cast = String.format(MysqlConstants.CAST, originField, y.getDeType() == 2 ? MysqlConstants.DEFAULT_INT_FORMAT : MysqlConstants.DEFAULT_FLOAT_FORMAT); + String agg = String.format(MysqlConstants.AGG_FIELD, y.getSummary(), cast); + String cast1 = String.format(MysqlConstants.CAST, agg, MysqlConstants.DEFAULT_FLOAT_FORMAT); + fieldName = String.format(MysqlConstants.ROUND, cast1, "8"); + } else { + String cast = String.format(MysqlConstants.CAST, originField, y.getDeType() == 2 ? MysqlConstants.DEFAULT_INT_FORMAT : MysqlConstants.DEFAULT_FLOAT_FORMAT); + if (StringUtils.equalsIgnoreCase(y.getSummary(), "count_distinct")) { + fieldName = String.format(MysqlConstants.AGG_FIELD, "COUNT", "DISTINCT " + cast); + } else { + fieldName = String.format(MysqlConstants.AGG_FIELD, y.getSummary(), cast); + } + } + } + return SQLObj.builder() + .fieldName(fieldName) + .fieldAlias(fieldAlias) + .build(); + } + + private String getYWheres(ChartViewFieldDTO y, String originField, String fieldAlias) { + List list = new ArrayList<>(); + if (CollectionUtils.isNotEmpty(y.getFilter()) && y.getFilter().size() > 0) { + y.getFilter().forEach(f -> { + String whereTerm = transMysqlFilterTerm(f.getTerm()); + String whereValue = ""; + // 原始类型不是时间,在de中被转成时间的字段做处理 + if (StringUtils.equalsIgnoreCase(f.getTerm(), "null")) { + whereValue = ""; + } else if (StringUtils.equalsIgnoreCase(f.getTerm(), "not_null")) { + whereValue = ""; + } else if (StringUtils.equalsIgnoreCase(f.getTerm(), "empty")) { + whereValue = "''"; + } else if (StringUtils.equalsIgnoreCase(f.getTerm(), "not_empty")) { + whereValue = "''"; + } else if (StringUtils.containsIgnoreCase(f.getTerm(), "in")) { + whereValue = "('" + StringUtils.join(f.getValue(), "','") + "')"; + } else if (StringUtils.containsIgnoreCase(f.getTerm(), "like")) { + whereValue = "'%" + f.getValue() + "%'"; + } else { + whereValue = String.format(MysqlConstants.WHERE_VALUE_VALUE, f.getValue()); + } + list.add(SQLObj.builder() + .whereField(fieldAlias) + .whereAlias(fieldAlias) + .whereTermAndValue(whereTerm + whereValue) + .build()); + }); + } + List strList = new ArrayList<>(); + list.forEach(ele -> strList.add(ele.getWhereField() + " " + ele.getWhereTermAndValue())); + return CollectionUtils.isNotEmpty(list) ? "(" + String.join(" " + getLogic(y.getLogic()) + " ", strList) + ")" : null; + } + + private String calcFieldRegex(String originField, SQLObj tableObj) { + originField = originField.replaceAll("[\\t\\n\\r]]", ""); + // 正则提取[xxx] + String regex = "\\[(.*?)]"; + Pattern pattern = Pattern.compile(regex); + Matcher matcher = pattern.matcher(originField); + Set ids = new HashSet<>(); + while (matcher.find()) { + String id = matcher.group(1); + ids.add(id); + } + if (CollectionUtils.isEmpty(ids)) { + return originField; + } + DatasetTableFieldExample datasetTableFieldExample = new DatasetTableFieldExample(); + datasetTableFieldExample.createCriteria().andIdIn(new ArrayList<>(ids)); + List calcFields = datasetTableFieldMapper.selectByExample(datasetTableFieldExample); + for (DatasetTableField ele : calcFields) { + originField = originField.replaceAll("\\[" + ele.getId() + "]", + String.format(MysqlConstants.KEYWORD_FIX, tableObj.getTableAlias(), ele.getDataeaseName())); + } + return originField; + } + + private String sqlLimit(String sql, ChartViewWithBLOBs view) { + if (StringUtils.equalsIgnoreCase(view.getResultMode(), "custom")) { + return sql + " LIMIT 0," + view.getResultCount(); + } else { + return sql; + } + } + + public List dateformat() { + return JSONArray.parseArray("[\n" + + "{\"dateformat\": \"%Y-%m-%d\"},\n" + + "{\"dateformat\": \"%Y/%m/%d\"},\n" + + "{\"dateformat\": \"%Y%m%d\"},\n" + + "{\"dateformat\": \"%Y-%m-%d %H:%i:%S\"},\n" + + "{\"dateformat\": \"%Y/%m/%d %H:%i:%S\"},\n" + + "{\"dateformat\": \"%Y%m%d %H:%i:%S\"}\n" + + "]", Dateformat.class); + } +} diff --git a/backend/src/main/java/io/dataease/provider/query/mysql/MysqlQueryProvider.java b/backend/src/main/java/io/dataease/provider/query/mysql/MysqlQueryProvider.java index 9db871adb5..141f722112 100644 --- a/backend/src/main/java/io/dataease/provider/query/mysql/MysqlQueryProvider.java +++ b/backend/src/main/java/io/dataease/provider/query/mysql/MysqlQueryProvider.java @@ -1,1398 +1,1397 @@ -package io.dataease.provider.query.mysql; - -import com.alibaba.fastjson.JSONArray; -import io.dataease.plugins.common.base.domain.ChartViewWithBLOBs; -import io.dataease.plugins.common.base.domain.DatasetTableField; -import io.dataease.plugins.common.base.domain.DatasetTableFieldExample; -import io.dataease.plugins.common.base.domain.Datasource; -import io.dataease.plugins.common.base.mapper.DatasetTableFieldMapper; -import io.dataease.plugins.common.constants.DeTypeConstants; -import io.dataease.plugins.common.constants.datasource.MySQLConstants; -import io.dataease.plugins.common.constants.datasource.SQLConstants; -import io.dataease.plugins.common.constants.engine.MysqlConstants; -import io.dataease.plugins.common.dto.chart.ChartCustomFilterItemDTO; -import io.dataease.plugins.common.dto.chart.ChartFieldCustomFilterDTO; -import io.dataease.plugins.common.dto.chart.ChartViewFieldDTO; -import io.dataease.plugins.common.dto.datasource.DeSortField; -import io.dataease.plugins.common.dto.sqlObj.SQLObj; -import io.dataease.plugins.common.request.chart.ChartExtFilterRequest; -import io.dataease.plugins.common.request.permission.DataSetRowPermissionsTreeDTO; -import io.dataease.plugins.common.request.permission.DatasetRowPermissionsTreeItem; -import io.dataease.plugins.datasource.entity.Dateformat; -import io.dataease.plugins.datasource.entity.PageInfo; -import io.dataease.plugins.datasource.query.QueryProvider; -import io.dataease.plugins.datasource.query.Utils; -import org.apache.commons.collections4.CollectionUtils; -import org.apache.commons.lang3.ObjectUtils; -import org.apache.commons.lang3.StringUtils; -import org.springframework.stereotype.Service; -import org.stringtemplate.v4.ST; -import org.stringtemplate.v4.STGroup; -import org.stringtemplate.v4.STGroupFile; - -import javax.annotation.Resource; -import java.text.MessageFormat; -import java.text.SimpleDateFormat; -import java.util.*; -import java.util.regex.Matcher; -import java.util.regex.Pattern; -import java.util.stream.Collectors; - -import static io.dataease.plugins.common.constants.datasource.SQLConstants.TABLE_ALIAS_PREFIX; - - -/** - * @Author gin - * @Date 2021/5/17 2:43 下午 - */ -@Service("mysqlQueryProvider") -public class MysqlQueryProvider extends QueryProvider { - @Resource - private DatasetTableFieldMapper datasetTableFieldMapper; - - @Override - public Integer transFieldType(String field) { - switch (field) { - case "CHAR": - case "VARCHAR": - case "TEXT": - case "TINYTEXT": - case "MEDIUMTEXT": - case "LONGTEXT": - case "ENUM": - return 0;// 文本 - case "DATE": - case "TIME": - case "YEAR": - case "DATETIME": - case "TIMESTAMP": - return 1;// 时间 - case "INT": - case "SMALLINT": - case "MEDIUMINT": - case "INTEGER": - case "BIGINT": - case "LONG": //增加了LONG类型 - return 2;// 整型 - case "FLOAT": - case "DOUBLE": - case "DECIMAL": - return 3;// 浮点 - case "BIT": - case "TINYINT": - return 4;// 布尔 - default: - return 0; - } - } - - @Override - public String createSQLPreview(String sql, String orderBy) { - return "SELECT * FROM (" + sqlFix(sql) + ") AS tmp " + " LIMIT 0,1000"; - } - - @Override - public String createQuerySQL(String table, List fields, boolean isGroup, Datasource ds, List fieldCustomFilter, List rowPermissionsTree) { - return createQuerySQL(table, fields, isGroup, ds, fieldCustomFilter, rowPermissionsTree, null); - } - - @Override - public String createQuerySQLAsTmp(String sql, List fields, boolean isGroup, List fieldCustomFilter, List rowPermissionsTree) { - return createQuerySQL("(" + sqlFix(sql) + ")", fields, isGroup, null, fieldCustomFilter, rowPermissionsTree, null); - } - - private SQLObj buildSortField(DeSortField f, SQLObj tableObj, int index) { - String originField; - if (ObjectUtils.isNotEmpty(f.getExtField()) && f.getExtField() == 2) { - // 解析origin name中有关联的字段生成sql表达式 - originField = calcFieldRegex(f.getOriginName(), tableObj); - } else if (ObjectUtils.isNotEmpty(f.getExtField()) && f.getExtField() == 1) { - originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), f.getOriginName()); - } else { - originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), f.getOriginName()); - } - String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_X_PREFIX, index); - String fieldName = ""; - // 处理横轴字段 - if (f.getDeExtractType() == 1) { - if (f.getDeType() == 2 || f.getDeType() == 3) { - fieldName = String.format(MySQLConstants.UNIX_TIMESTAMP, originField) + "*1000"; - } else { - if (f.getType().equalsIgnoreCase("YEAR")) { - fieldName = String.format(MySQLConstants.DATE_FORMAT, "CONCAT(" + originField + ",'-01-01')", MySQLConstants.DEFAULT_DATE_FORMAT); - } else if (f.getType().equalsIgnoreCase("TIME")) { - fieldName = String.format(MySQLConstants.DATE_FORMAT, "CONCAT('1970-01-01', " + originField + ")", MySQLConstants.DEFAULT_DATE_FORMAT); - } else { - fieldName = String.format(MySQLConstants.DATE_FORMAT, originField, MySQLConstants.DEFAULT_DATE_FORMAT); - } - } - } else if (f.getDeExtractType() == 0) { - if (f.getDeType() == 2) { - fieldName = String.format(MySQLConstants.CAST, originField, MySQLConstants.DEFAULT_INT_FORMAT); - } else if (f.getDeType() == 3) { - fieldName = String.format(MySQLConstants.CAST, originField, MySQLConstants.DEFAULT_FLOAT_FORMAT); - } else if (f.getDeType() == 1) { - fieldName = StringUtils.isEmpty(f.getDateFormat()) ? String.format(MySQLConstants.STR_TO_DATE, originField, MysqlConstants.DEFAULT_DATE_FORMAT) : - String.format(MySQLConstants.DATE_FORMAT, String.format(MySQLConstants.STR_TO_DATE, originField, f.getDateFormat()), MySQLConstants.DEFAULT_DATE_FORMAT); - } else { - fieldName = originField; - } - } else { - if (f.getDeType() == 1) { - String cast = String.format(MySQLConstants.CAST, originField, MySQLConstants.DEFAULT_INT_FORMAT) + "/1000"; - fieldName = String.format(MySQLConstants.FROM_UNIXTIME, cast, MySQLConstants.DEFAULT_DATE_FORMAT); - } else if (f.getDeType() == 2) { - fieldName = String.format(MySQLConstants.CAST, originField, MySQLConstants.DEFAULT_INT_FORMAT); - } else { - fieldName = originField; - } - } - SQLObj result = SQLObj.builder().orderField(originField).orderAlias(originField).orderDirection(f.getOrderDirection()).build(); - return result; - - } - - @Override - public String createQuerySQL(String table, List fields, boolean isGroup, Datasource ds, List fieldCustomFilter, List rowPermissionsTree, List sortFields) { - SQLObj tableObj = SQLObj.builder() - .tableName((table.startsWith("(") && table.endsWith(")")) ? table : String.format(MySQLConstants.KEYWORD_TABLE, table)) - .tableAlias(String.format(TABLE_ALIAS_PREFIX, 0)) - .build(); - List xFields = new ArrayList<>(); - if (CollectionUtils.isNotEmpty(fields)) { - for (int i = 0; i < fields.size(); i++) { - DatasetTableField f = fields.get(i); - String originField; - if (ObjectUtils.isNotEmpty(f.getExtField()) && f.getExtField() == 2) { - // 解析origin name中有关联的字段生成sql表达式 - originField = calcFieldRegex(f.getOriginName(), tableObj); - } else if (ObjectUtils.isNotEmpty(f.getExtField()) && f.getExtField() == 1) { - originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), f.getOriginName()); - } else { - originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), f.getOriginName()); - } - String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_X_PREFIX, i); - String fieldName = ""; - // 处理横轴字段 - if (f.getDeExtractType() == 1) { - if (f.getDeType() == 2 || f.getDeType() == 3) { - fieldName = String.format(MySQLConstants.UNIX_TIMESTAMP, originField) + "*1000"; - } else { - if (f.getType().equalsIgnoreCase("YEAR")) { - fieldName = String.format(MySQLConstants.DATE_FORMAT, "CONCAT(" + originField + ",'-01-01')", MySQLConstants.DEFAULT_DATE_FORMAT); - } else if (f.getType().equalsIgnoreCase("TIME")) { - fieldName = String.format(MySQLConstants.DATE_FORMAT, "CONCAT('1970-01-01', " + originField + ")", MySQLConstants.DEFAULT_DATE_FORMAT); - } else { - fieldName = String.format(MySQLConstants.DATE_FORMAT, originField, MySQLConstants.DEFAULT_DATE_FORMAT); - } - } - } else if (f.getDeExtractType() == 0) { - if (f.getDeType() == 2) { - fieldName = String.format(MySQLConstants.CAST, originField, MySQLConstants.DEFAULT_INT_FORMAT); - } else if (f.getDeType() == 3) { - fieldName = String.format(MySQLConstants.CAST, originField, MySQLConstants.DEFAULT_FLOAT_FORMAT); - } else if (f.getDeType() == 1) { - fieldName = StringUtils.isEmpty(f.getDateFormat()) ? String.format(MySQLConstants.STR_TO_DATE, originField, MysqlConstants.DEFAULT_DATE_FORMAT) : - String.format(MySQLConstants.DATE_FORMAT, String.format(MySQLConstants.STR_TO_DATE, originField, f.getDateFormat()), MySQLConstants.DEFAULT_DATE_FORMAT); - } else { - fieldName = originField; - } - } else { - if (f.getDeType() == 1) { - String cast = String.format(MySQLConstants.CAST, originField, MySQLConstants.DEFAULT_INT_FORMAT) + "/1000"; - fieldName = String.format(MySQLConstants.FROM_UNIXTIME, cast, MySQLConstants.DEFAULT_DATE_FORMAT); - } else if (f.getDeType() == 2) { - fieldName = String.format(MySQLConstants.CAST, originField, MySQLConstants.DEFAULT_INT_FORMAT); - } else { - fieldName = originField; - } - } - xFields.add(SQLObj.builder() - .fieldName(fieldName) - .fieldAlias(fieldAlias) - .build()); - } - } - - - STGroup stg = new STGroupFile(SQLConstants.SQL_TEMPLATE); - ST st_sql = stg.getInstanceOf("previewSql"); - st_sql.add("isGroup", isGroup); - if (CollectionUtils.isNotEmpty(xFields)) st_sql.add("groups", xFields); - if (ObjectUtils.isNotEmpty(tableObj)) st_sql.add("table", tableObj); - - String customWheres = transCustomFilterList(tableObj, fieldCustomFilter); - String whereTrees = transFilterTrees(tableObj, rowPermissionsTree); - List wheres = new ArrayList<>(); - if (customWheres != null) wheres.add(customWheres); - if (whereTrees != null) wheres.add(whereTrees); - if (CollectionUtils.isNotEmpty(wheres)) st_sql.add("filters", wheres); - - List xOrders = new ArrayList<>(); - if (CollectionUtils.isNotEmpty(sortFields)) { - int step = fields.size(); - for (int i = step; i < (step + sortFields.size()); i++) { - DeSortField deSortField = sortFields.get(i - step); - SQLObj order = buildSortField(deSortField, tableObj, i); - xOrders.add(order); - } - } - if (ObjectUtils.isNotEmpty(xOrders)) { - st_sql.add("orders", xOrders); - } - - return st_sql.render(); - } - - @Override - public String createQuerySQLAsTmp(String sql, List fields, boolean isGroup, List fieldCustomFilter, List rowPermissionsTree, List sortFields) { - return createQuerySQL("(" + sqlFix(sql) + ")", fields, isGroup, null, fieldCustomFilter, rowPermissionsTree, sortFields); - } - - @Override - public String createQueryTableWithPage(String table, List fields, Integer page, Integer pageSize, Integer realSize, boolean isGroup, Datasource ds, List fieldCustomFilter, List rowPermissionsTree) { - return createQuerySQL(table, fields, isGroup, null, fieldCustomFilter, rowPermissionsTree) + " LIMIT " + (page - 1) * pageSize + "," + realSize; - } - - @Override - public String createQueryTableWithLimit(String table, List fields, Integer limit, boolean isGroup, Datasource ds, List fieldCustomFilter, List rowPermissionsTree) { - return createQuerySQL(table, fields, isGroup, null, fieldCustomFilter, rowPermissionsTree) + " LIMIT 0," + limit; - } - - @Override - public String createQuerySqlWithLimit(String sql, List fields, Integer limit, boolean isGroup, List fieldCustomFilter, List rowPermissionsTree) { - return createQuerySQLAsTmp(sql, fields, isGroup, fieldCustomFilter, rowPermissionsTree) + " LIMIT 0," + limit; - } - - @Override - public String createQuerySQLWithPage(String sql, List fields, Integer page, Integer pageSize, Integer realSize, boolean isGroup, List fieldCustomFilter, List rowPermissionsTree) { - return createQuerySQLAsTmp(sql, fields, isGroup, fieldCustomFilter, rowPermissionsTree) + " LIMIT " + (page - 1) * pageSize + "," + realSize; - } - - @Override - public String getSQL(String table, List xAxis, List yAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, Datasource ds, ChartViewWithBLOBs view) { - SQLObj tableObj = SQLObj.builder() - .tableName((table.startsWith("(") && table.endsWith(")")) ? table : String.format(MySQLConstants.KEYWORD_TABLE, table)) - .tableAlias(String.format(TABLE_ALIAS_PREFIX, 0)) - .build(); - List xFields = new ArrayList<>(); - List xOrders = new ArrayList<>(); - if (CollectionUtils.isNotEmpty(xAxis)) { - for (int i = 0; i < xAxis.size(); i++) { - ChartViewFieldDTO x = xAxis.get(i); - String originField; - if (ObjectUtils.isNotEmpty(x.getExtField()) && x.getExtField() == 2) { - // 解析origin name中有关联的字段生成sql表达式 - originField = calcFieldRegex(x.getOriginName(), tableObj); - } else if (ObjectUtils.isNotEmpty(x.getExtField()) && x.getExtField() == 1) { - originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), x.getOriginName()); - } else { - originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), x.getOriginName()); - } - String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_X_PREFIX, i); - // 处理横轴字段 - xFields.add(getXFields(x, originField, fieldAlias)); - // 处理横轴排序 - if (StringUtils.isNotEmpty(x.getSort()) && Utils.joinSort(x.getSort())) { - xOrders.add(SQLObj.builder() - .orderField(originField) - .orderAlias(fieldAlias) - .orderDirection(x.getSort()) - .build()); - } - } - } - List yFields = new ArrayList<>(); - List yWheres = new ArrayList<>(); - List yOrders = new ArrayList<>(); - if (CollectionUtils.isNotEmpty(yAxis)) { - for (int i = 0; i < yAxis.size(); i++) { - ChartViewFieldDTO y = yAxis.get(i); - String originField; - if (ObjectUtils.isNotEmpty(y.getExtField()) && y.getExtField() == 2) { - // 解析origin name中有关联的字段生成sql表达式 - originField = calcFieldRegex(y.getOriginName(), tableObj); - } else if (ObjectUtils.isNotEmpty(y.getExtField()) && y.getExtField() == 1) { - originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), y.getOriginName()); - } else { - originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), y.getOriginName()); - } - String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_Y_PREFIX, i); - // 处理纵轴字段 - yFields.add(getYFields(y, originField, fieldAlias)); - // 处理纵轴过滤 - yWheres.add(getYWheres(y, originField, fieldAlias)); - // 处理纵轴排序 - if (StringUtils.isNotEmpty(y.getSort()) && Utils.joinSort(y.getSort())) { - yOrders.add(SQLObj.builder() - .orderField(originField) - .orderAlias(fieldAlias) - .orderDirection(y.getSort()) - .build()); - } - } - } - // 处理视图中字段过滤 - String customWheres = transCustomFilterList(tableObj, fieldCustomFilter); - // 处理仪表板字段过滤 - String extWheres = transExtFilterList(tableObj, extFilterRequestList); - // row permissions tree - String whereTrees = transFilterTrees(tableObj, rowPermissionsTree); - // 构建sql所有参数 - List fields = new ArrayList<>(); - fields.addAll(xFields); - fields.addAll(yFields); - List wheres = new ArrayList<>(); - if (customWheres != null) wheres.add(customWheres); - if (extWheres != null) wheres.add(extWheres); - if (whereTrees != null) wheres.add(whereTrees); - List groups = new ArrayList<>(); - groups.addAll(xFields); - // 外层再次套sql - List orders = new ArrayList<>(); - orders.addAll(xOrders); - orders.addAll(yOrders); - List aggWheres = new ArrayList<>(); - aggWheres.addAll(yWheres.stream().filter(ObjectUtils::isNotEmpty).collect(Collectors.toList())); - - STGroup stg = new STGroupFile(SQLConstants.SQL_TEMPLATE); - ST st_sql = stg.getInstanceOf("querySql"); - if (CollectionUtils.isNotEmpty(xFields)) st_sql.add("groups", xFields); - if (CollectionUtils.isNotEmpty(yFields)) st_sql.add("aggregators", yFields); - if (CollectionUtils.isNotEmpty(wheres)) st_sql.add("filters", wheres); - if (ObjectUtils.isNotEmpty(tableObj)) st_sql.add("table", tableObj); - String sql = st_sql.render(); - - ST st = stg.getInstanceOf("querySql"); - SQLObj tableSQL = SQLObj.builder() - .tableName(String.format(MySQLConstants.BRACKETS, sql)) - .tableAlias(String.format(TABLE_ALIAS_PREFIX, 1)) - .build(); - if (CollectionUtils.isNotEmpty(aggWheres)) st.add("filters", aggWheres); - if (CollectionUtils.isNotEmpty(orders)) st.add("orders", orders); - if (ObjectUtils.isNotEmpty(tableSQL)) st.add("table", tableSQL); - return sqlLimit(st.render(), view); - } - - @Override - public String getSQLTableInfo(String table, List xAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, Datasource ds, ChartViewWithBLOBs view) { - return sqlLimit(originalTableInfo(table, xAxis, fieldCustomFilter, rowPermissionsTree, extFilterRequestList, ds, view), view); - } - - @Override - public String getSQLWithPage(boolean isTable, String table, List xAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, Datasource ds, ChartViewWithBLOBs view, PageInfo pageInfo) { - String limit = ((pageInfo.getGoPage() != null && pageInfo.getPageSize() != null) ? " LIMIT " + (pageInfo.getGoPage() - 1) * pageInfo.getPageSize() + "," + pageInfo.getPageSize() : ""); - if (isTable) { - return originalTableInfo(table, xAxis, fieldCustomFilter, rowPermissionsTree, extFilterRequestList, ds, view) + limit; - } else { - return originalTableInfo("(" + sqlFix(table) + ")", xAxis, fieldCustomFilter, rowPermissionsTree, extFilterRequestList, ds, view) + limit; - } - } - - private String originalTableInfo(String table, List xAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, Datasource ds, ChartViewWithBLOBs view) { - SQLObj tableObj = SQLObj.builder() - .tableName((table.startsWith("(") && table.endsWith(")")) ? table : String.format(MySQLConstants.KEYWORD_TABLE, table)) - .tableAlias(String.format(TABLE_ALIAS_PREFIX, 0)) - .build(); - List xFields = new ArrayList<>(); - List xOrders = new ArrayList<>(); - if (CollectionUtils.isNotEmpty(xAxis)) { - for (int i = 0; i < xAxis.size(); i++) { - ChartViewFieldDTO x = xAxis.get(i); - String originField; - if (ObjectUtils.isNotEmpty(x.getExtField()) && x.getExtField() == 2) { - // 解析origin name中有关联的字段生成sql表达式 - originField = calcFieldRegex(x.getOriginName(), tableObj); - } else if (ObjectUtils.isNotEmpty(x.getExtField()) && x.getExtField() == 1) { - originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), x.getOriginName()); - } else { - if (x.getDeType() == 2 || x.getDeType() == 3) { - originField = String.format(MySQLConstants.CAST, String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), x.getOriginName()), MySQLConstants.DEFAULT_FLOAT_FORMAT); - } else { - originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), x.getOriginName()); - } - } - String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_X_PREFIX, i); - // 处理横轴字段 - xFields.add(getXFields(x, originField, fieldAlias)); - // 处理横轴排序 - if (StringUtils.isNotEmpty(x.getSort()) && Utils.joinSort(x.getSort())) { - xOrders.add(SQLObj.builder() - .orderField(originField) - .orderAlias(fieldAlias) - .orderDirection(x.getSort()) - .build()); - } - } - } - // 处理视图中字段过滤 - String customWheres = transCustomFilterList(tableObj, fieldCustomFilter); - // 处理仪表板字段过滤 - String extWheres = transExtFilterList(tableObj, extFilterRequestList); - // row permissions tree - String whereTrees = transFilterTrees(tableObj, rowPermissionsTree); - // 构建sql所有参数 - List fields = new ArrayList<>(); - fields.addAll(xFields); - List wheres = new ArrayList<>(); - if (customWheres != null) wheres.add(customWheres); - if (extWheres != null) wheres.add(extWheres); - if (whereTrees != null) wheres.add(whereTrees); - List groups = new ArrayList<>(); - groups.addAll(xFields); - // 外层再次套sql - List orders = new ArrayList<>(); - orders.addAll(xOrders); - - STGroup stg = new STGroupFile(SQLConstants.SQL_TEMPLATE); - ST st_sql = stg.getInstanceOf("previewSql"); - st_sql.add("isGroup", false); - if (CollectionUtils.isNotEmpty(xFields)) st_sql.add("groups", xFields); - if (CollectionUtils.isNotEmpty(wheres)) st_sql.add("filters", wheres); - if (ObjectUtils.isNotEmpty(tableObj)) st_sql.add("table", tableObj); - String sql = st_sql.render(); - - ST st = stg.getInstanceOf("previewSql"); - st.add("isGroup", false); - SQLObj tableSQL = SQLObj.builder() - .tableName(String.format(MySQLConstants.BRACKETS, sql)) - .tableAlias(String.format(TABLE_ALIAS_PREFIX, 1)) - .build(); - if (CollectionUtils.isNotEmpty(orders)) st.add("orders", orders); - if (ObjectUtils.isNotEmpty(tableSQL)) st.add("table", tableSQL); - return st.render(); - } - - @Override - public String getSQLAsTmpTableInfo(String sql, List xAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, Datasource ds, ChartViewWithBLOBs view) { - return getSQLTableInfo("(" + sqlFix(sql) + ")", xAxis, fieldCustomFilter, rowPermissionsTree, extFilterRequestList, null, view); - } - - - @Override - public String getSQLAsTmp(String sql, List xAxis, List yAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, ChartViewWithBLOBs view) { - return getSQL("(" + sqlFix(sql) + ")", xAxis, yAxis, fieldCustomFilter, rowPermissionsTree, extFilterRequestList, null, view); - } - - @Override - public String getSQLStack(String table, List xAxis, List yAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, List extStack, Datasource ds, ChartViewWithBLOBs view) { - SQLObj tableObj = SQLObj.builder() - .tableName((table.startsWith("(") && table.endsWith(")")) ? table : String.format(MySQLConstants.KEYWORD_TABLE, table)) - .tableAlias(String.format(TABLE_ALIAS_PREFIX, 0)) - .build(); - List xFields = new ArrayList<>(); - List xOrders = new ArrayList<>(); - List xList = new ArrayList<>(); - xList.addAll(xAxis); - xList.addAll(extStack); - if (CollectionUtils.isNotEmpty(xList)) { - for (int i = 0; i < xList.size(); i++) { - ChartViewFieldDTO x = xList.get(i); - String originField; - if (ObjectUtils.isNotEmpty(x.getExtField()) && x.getExtField() == 2) { - // 解析origin name中有关联的字段生成sql表达式 - originField = calcFieldRegex(x.getOriginName(), tableObj); - } else if (ObjectUtils.isNotEmpty(x.getExtField()) && x.getExtField() == 1) { - originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), x.getOriginName()); - } else { - originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), x.getOriginName()); - } - String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_X_PREFIX, i); - // 处理横轴字段 - xFields.add(getXFields(x, originField, fieldAlias)); - // 处理横轴排序 - if (StringUtils.isNotEmpty(x.getSort()) && Utils.joinSort(x.getSort())) { - xOrders.add(SQLObj.builder() - .orderField(originField) - .orderAlias(fieldAlias) - .orderDirection(x.getSort()) - .build()); - } - } - } - List yFields = new ArrayList<>(); - List yWheres = new ArrayList<>(); - List yOrders = new ArrayList<>(); - if (CollectionUtils.isNotEmpty(yAxis)) { - for (int i = 0; i < yAxis.size(); i++) { - ChartViewFieldDTO y = yAxis.get(i); - String originField; - if (ObjectUtils.isNotEmpty(y.getExtField()) && y.getExtField() == 2) { - // 解析origin name中有关联的字段生成sql表达式 - originField = calcFieldRegex(y.getOriginName(), tableObj); - } else if (ObjectUtils.isNotEmpty(y.getExtField()) && y.getExtField() == 1) { - originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), y.getOriginName()); - } else { - originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), y.getOriginName()); - } - String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_Y_PREFIX, i); - // 处理纵轴字段 - yFields.add(getYFields(y, originField, fieldAlias)); - // 处理纵轴过滤 - yWheres.add(getYWheres(y, originField, fieldAlias)); - // 处理纵轴排序 - if (StringUtils.isNotEmpty(y.getSort()) && Utils.joinSort(y.getSort())) { - yOrders.add(SQLObj.builder() - .orderField(originField) - .orderAlias(fieldAlias) - .orderDirection(y.getSort()) - .build()); - } - } - } - // 处理视图中字段过滤 - String customWheres = transCustomFilterList(tableObj, fieldCustomFilter); - // 处理仪表板字段过滤 - String extWheres = transExtFilterList(tableObj, extFilterRequestList); - // row permissions tree - String whereTrees = transFilterTrees(tableObj, rowPermissionsTree); - // 构建sql所有参数 - List fields = new ArrayList<>(); - fields.addAll(xFields); - fields.addAll(yFields); - List wheres = new ArrayList<>(); - if (customWheres != null) wheres.add(customWheres); - if (extWheres != null) wheres.add(extWheres); - if (whereTrees != null) wheres.add(whereTrees); - List groups = new ArrayList<>(); - groups.addAll(xFields); - // 外层再次套sql - List orders = new ArrayList<>(); - orders.addAll(xOrders); - orders.addAll(yOrders); - List aggWheres = new ArrayList<>(); - aggWheres.addAll(yWheres.stream().filter(ObjectUtils::isNotEmpty).collect(Collectors.toList())); - - STGroup stg = new STGroupFile(SQLConstants.SQL_TEMPLATE); - ST st_sql = stg.getInstanceOf("querySql"); - if (CollectionUtils.isNotEmpty(xFields)) st_sql.add("groups", xFields); - if (CollectionUtils.isNotEmpty(yFields)) st_sql.add("aggregators", yFields); - if (CollectionUtils.isNotEmpty(wheres)) st_sql.add("filters", wheres); - if (ObjectUtils.isNotEmpty(tableObj)) st_sql.add("table", tableObj); - String sql = st_sql.render(); - - ST st = stg.getInstanceOf("querySql"); - SQLObj tableSQL = SQLObj.builder() - .tableName(String.format(MySQLConstants.BRACKETS, sql)) - .tableAlias(String.format(TABLE_ALIAS_PREFIX, 1)) - .build(); - if (CollectionUtils.isNotEmpty(aggWheres)) st.add("filters", aggWheres); - if (CollectionUtils.isNotEmpty(orders)) st.add("orders", orders); - if (ObjectUtils.isNotEmpty(tableSQL)) st.add("table", tableSQL); - return sqlLimit(st.render(), view); - } - - @Override - public String getSQLAsTmpStack(String table, List xAxis, List yAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, List extStack, ChartViewWithBLOBs view) { - return getSQLStack("(" + sqlFix(table) + ")", xAxis, yAxis, fieldCustomFilter, rowPermissionsTree, extFilterRequestList, extStack, null, view); - } - - @Override - public String getSQLScatter(String table, List xAxis, List yAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, List extBubble, Datasource ds, ChartViewWithBLOBs view) { - SQLObj tableObj = SQLObj.builder() - .tableName((table.startsWith("(") && table.endsWith(")")) ? table : String.format(MySQLConstants.KEYWORD_TABLE, table)) - .tableAlias(String.format(TABLE_ALIAS_PREFIX, 0)) - .build(); - List xFields = new ArrayList<>(); - List xOrders = new ArrayList<>(); - if (CollectionUtils.isNotEmpty(xAxis)) { - for (int i = 0; i < xAxis.size(); i++) { - ChartViewFieldDTO x = xAxis.get(i); - String originField; - if (ObjectUtils.isNotEmpty(x.getExtField()) && x.getExtField() == 2) { - // 解析origin name中有关联的字段生成sql表达式 - originField = calcFieldRegex(x.getOriginName(), tableObj); - } else if (ObjectUtils.isNotEmpty(x.getExtField()) && x.getExtField() == 1) { - originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), x.getOriginName()); - } else { - originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), x.getOriginName()); - } - String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_X_PREFIX, i); - // 处理横轴字段 - xFields.add(getXFields(x, originField, fieldAlias)); - // 处理横轴排序 - if (StringUtils.isNotEmpty(x.getSort()) && Utils.joinSort(x.getSort())) { - xOrders.add(SQLObj.builder() - .orderField(originField) - .orderAlias(fieldAlias) - .orderDirection(x.getSort()) - .build()); - } - } - } - List yFields = new ArrayList<>(); - List yWheres = new ArrayList<>(); - List yOrders = new ArrayList<>(); - List yList = new ArrayList<>(); - yList.addAll(yAxis); - yList.addAll(extBubble); - if (CollectionUtils.isNotEmpty(yList)) { - for (int i = 0; i < yList.size(); i++) { - ChartViewFieldDTO y = yList.get(i); - String originField; - if (ObjectUtils.isNotEmpty(y.getExtField()) && y.getExtField() == 2) { - // 解析origin name中有关联的字段生成sql表达式 - originField = calcFieldRegex(y.getOriginName(), tableObj); - } else if (ObjectUtils.isNotEmpty(y.getExtField()) && y.getExtField() == 1) { - originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), y.getOriginName()); - } else { - originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), y.getOriginName()); - } - String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_Y_PREFIX, i); - // 处理纵轴字段 - yFields.add(getYFields(y, originField, fieldAlias)); - // 处理纵轴过滤 - yWheres.add(getYWheres(y, originField, fieldAlias)); - // 处理纵轴排序 - if (StringUtils.isNotEmpty(y.getSort()) && Utils.joinSort(y.getSort())) { - yOrders.add(SQLObj.builder() - .orderField(originField) - .orderAlias(fieldAlias) - .orderDirection(y.getSort()) - .build()); - } - } - } - // 处理视图中字段过滤 - String customWheres = transCustomFilterList(tableObj, fieldCustomFilter); - // 处理仪表板字段过滤 - String extWheres = transExtFilterList(tableObj, extFilterRequestList); - // row permissions tree - String whereTrees = transFilterTrees(tableObj, rowPermissionsTree); - // 构建sql所有参数 - List fields = new ArrayList<>(); - fields.addAll(xFields); - fields.addAll(yFields); - List wheres = new ArrayList<>(); - if (customWheres != null) wheres.add(customWheres); - if (extWheres != null) wheres.add(extWheres); - if (whereTrees != null) wheres.add(whereTrees); - List groups = new ArrayList<>(); - groups.addAll(xFields); - // 外层再次套sql - List orders = new ArrayList<>(); - orders.addAll(xOrders); - orders.addAll(yOrders); - List aggWheres = new ArrayList<>(); - aggWheres.addAll(yWheres.stream().filter(ObjectUtils::isNotEmpty).collect(Collectors.toList())); - - STGroup stg = new STGroupFile(SQLConstants.SQL_TEMPLATE); - ST st_sql = stg.getInstanceOf("querySql"); - if (CollectionUtils.isNotEmpty(xFields)) st_sql.add("groups", xFields); - if (CollectionUtils.isNotEmpty(yFields)) st_sql.add("aggregators", yFields); - if (CollectionUtils.isNotEmpty(wheres)) st_sql.add("filters", wheres); - if (ObjectUtils.isNotEmpty(tableObj)) st_sql.add("table", tableObj); - String sql = st_sql.render(); - - ST st = stg.getInstanceOf("querySql"); - SQLObj tableSQL = SQLObj.builder() - .tableName(String.format(MySQLConstants.BRACKETS, sql)) - .tableAlias(String.format(TABLE_ALIAS_PREFIX, 1)) - .build(); - if (CollectionUtils.isNotEmpty(aggWheres)) st.add("filters", aggWheres); - if (CollectionUtils.isNotEmpty(orders)) st.add("orders", orders); - if (ObjectUtils.isNotEmpty(tableSQL)) st.add("table", tableSQL); - return sqlLimit(st.render(), view); - } - - @Override - public String getSQLAsTmpScatter(String table, List xAxis, List yAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, List extBubble, ChartViewWithBLOBs view) { - return getSQLScatter("(" + sqlFix(table) + ")", xAxis, yAxis, fieldCustomFilter, rowPermissionsTree, extFilterRequestList, extBubble, null, view); - } - - @Override - public String searchTable(String table) { - return "SELECT table_name FROM information_schema.TABLES WHERE table_name ='" + table + "'"; - } - - @Override - public String getSQLSummary(String table, List yAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, ChartViewWithBLOBs view, Datasource ds) { - // 字段汇总 排序等 - SQLObj tableObj = SQLObj.builder() - .tableName((table.startsWith("(") && table.endsWith(")")) ? table : String.format(MySQLConstants.KEYWORD_TABLE, table)) - .tableAlias(String.format(TABLE_ALIAS_PREFIX, 0)) - .build(); - List yFields = new ArrayList<>(); - List yWheres = new ArrayList<>(); - List yOrders = new ArrayList<>(); - if (CollectionUtils.isNotEmpty(yAxis)) { - for (int i = 0; i < yAxis.size(); i++) { - ChartViewFieldDTO y = yAxis.get(i); - String originField; - if (ObjectUtils.isNotEmpty(y.getExtField()) && y.getExtField() == 2) { - // 解析origin name中有关联的字段生成sql表达式 - originField = calcFieldRegex(y.getOriginName(), tableObj); - } else if (ObjectUtils.isNotEmpty(y.getExtField()) && y.getExtField() == 1) { - originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), y.getOriginName()); - } else { - originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), y.getOriginName()); - } - String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_Y_PREFIX, i); - // 处理纵轴字段 - yFields.add(getYFields(y, originField, fieldAlias)); - // 处理纵轴过滤 - yWheres.add(getYWheres(y, originField, fieldAlias)); - // 处理纵轴排序 - if (StringUtils.isNotEmpty(y.getSort()) && Utils.joinSort(y.getSort())) { - yOrders.add(SQLObj.builder() - .orderField(originField) - .orderAlias(fieldAlias) - .orderDirection(y.getSort()) - .build()); - } - } - } - // 处理视图中字段过滤 - String customWheres = transCustomFilterList(tableObj, fieldCustomFilter); - // 处理仪表板字段过滤 - String extWheres = transExtFilterList(tableObj, extFilterRequestList); - // row permissions tree - String whereTrees = transFilterTrees(tableObj, rowPermissionsTree); - // 构建sql所有参数 - List fields = new ArrayList<>(); - fields.addAll(yFields); - List wheres = new ArrayList<>(); - if (customWheres != null) wheres.add(customWheres); - if (extWheres != null) wheres.add(extWheres); - if (whereTrees != null) wheres.add(whereTrees); - List groups = new ArrayList<>(); - // 外层再次套sql - List orders = new ArrayList<>(); - orders.addAll(yOrders); - List aggWheres = new ArrayList<>(); - aggWheres.addAll(yWheres.stream().filter(ObjectUtils::isNotEmpty).collect(Collectors.toList())); - - STGroup stg = new STGroupFile(SQLConstants.SQL_TEMPLATE); - ST st_sql = stg.getInstanceOf("querySql"); - if (CollectionUtils.isNotEmpty(yFields)) st_sql.add("aggregators", yFields); - if (CollectionUtils.isNotEmpty(wheres)) st_sql.add("filters", wheres); - if (ObjectUtils.isNotEmpty(tableObj)) st_sql.add("table", tableObj); - String sql = st_sql.render(); - - ST st = stg.getInstanceOf("querySql"); - SQLObj tableSQL = SQLObj.builder() - .tableName(String.format(MySQLConstants.BRACKETS, sql)) - .tableAlias(String.format(TABLE_ALIAS_PREFIX, 1)) - .build(); - if (CollectionUtils.isNotEmpty(aggWheres)) st.add("filters", aggWheres); - if (CollectionUtils.isNotEmpty(orders)) st.add("orders", orders); - if (ObjectUtils.isNotEmpty(tableSQL)) st.add("table", tableSQL); - return sqlLimit(st.render(), view); - } - - @Override - public String getSQLSummaryAsTmp(String sql, List yAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, ChartViewWithBLOBs view) { - return getSQLSummary("(" + sqlFix(sql) + ")", yAxis, fieldCustomFilter, rowPermissionsTree, extFilterRequestList, view, null); - } - - @Override - public String wrapSql(String sql) { - sql = sql.trim(); - if (sql.lastIndexOf(";") == (sql.length() - 1)) { - sql = sql.substring(0, sql.length() - 1); - } - String tmpSql = "SELECT * FROM (" + sql + ") AS tmp " + " LIMIT 0"; - return tmpSql; - } - - @Override - public String createRawQuerySQL(String table, List fields, Datasource ds) { - String[] array = fields.stream().map(f -> { - StringBuilder stringBuilder = new StringBuilder(); - if (f.getDeExtractType() == 4) { // 处理 tinyint - stringBuilder.append("concat(`").append(f.getOriginName()).append("`,'') AS ").append(f.getDataeaseName()); - } else if (f.getDeExtractType() == 1 && f.getType().equalsIgnoreCase("YEAR")) { // 处理 YEAR - stringBuilder.append("").append(String.format(MySQLConstants.DATE_FORMAT, "CONCAT(" + f.getOriginName() + ",'-01-01')", MySQLConstants.DEFAULT_DATE_FORMAT)).append(" AS ").append(f.getDataeaseName()); - } else { - stringBuilder.append("`").append(f.getOriginName()).append("` AS ").append(f.getDataeaseName()); - } - return stringBuilder.toString(); - }).toArray(String[]::new); - table = table.trim().startsWith("(") ? table : String.format(MySQLConstants.KEYWORD_TABLE, table); - return MessageFormat.format("SELECT {0} FROM {1} LIMIT DE_OFFSET, DE_PAGE_SIZE ", StringUtils.join(array, ","), table); - } - - public String getTotalCount(boolean isTable, String sql, Datasource ds) { - if(isTable){ - return "SELECT COUNT(*) from " + String.format(MySQLConstants.KEYWORD_TABLE, sql); - }else { - return "SELECT COUNT(*) from ( " + sqlFix(sql) + " ) DE_COUNT_TEMP"; - } - } - - @Override - public String createRawQuerySQLAsTmp(String sql, List fields) { - return createRawQuerySQL("(" + sqlFix(sql) + ") AS DE_TEMP", fields, null); - } - - public String transTreeItem(SQLObj tableObj, DatasetRowPermissionsTreeItem item) { - String res = null; - DatasetTableField field = item.getField(); - if (ObjectUtils.isEmpty(field)) { - return null; - } - String whereName = ""; - String originName; - if (ObjectUtils.isNotEmpty(field.getExtField()) && field.getExtField() == 2) { - // 解析origin name中有关联的字段生成sql表达式 - originName = calcFieldRegex(field.getOriginName(), tableObj); - } else if (ObjectUtils.isNotEmpty(field.getExtField()) && field.getExtField() == 1) { - originName = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), field.getOriginName()); - } else { - originName = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), field.getOriginName()); - } - if (field.getDeType() == 1) { - if (field.getDeExtractType() == 0 || field.getDeExtractType() == 5) { - whereName = String.format(MySQLConstants.STR_TO_DATE, originName, StringUtils.isNotEmpty(field.getDateFormat()) ? field.getDateFormat() : MysqlConstants.DEFAULT_DATE_FORMAT); - } - if (field.getDeExtractType() == 2 || field.getDeExtractType() == 3 || field.getDeExtractType() == 4) { - String cast = String.format(MySQLConstants.CAST, originName, MySQLConstants.DEFAULT_INT_FORMAT) + "/1000"; - whereName = String.format(MySQLConstants.FROM_UNIXTIME, cast, MySQLConstants.DEFAULT_DATE_FORMAT); - } - if (field.getDeExtractType() == 1) { - whereName = originName; - } - } else if (field.getDeType() == 2 || field.getDeType() == 3) { - if (field.getDeExtractType() == 0 || field.getDeExtractType() == 5) { - whereName = String.format(MySQLConstants.CAST, originName, MySQLConstants.DEFAULT_FLOAT_FORMAT); - } - if (field.getDeExtractType() == 1) { - whereName = String.format(MySQLConstants.UNIX_TIMESTAMP, originName); - } - if (field.getDeExtractType() == 2 || field.getDeExtractType() == 3 || field.getDeExtractType() == 4) { - whereName = originName; - } - } else { - whereName = originName; - } - - if (StringUtils.equalsIgnoreCase(item.getFilterType(), "enum")) { - if (CollectionUtils.isNotEmpty(item.getEnumValue())) { - res = "(" + whereName + " IN ('" + String.join("','", item.getEnumValue()) + "'))"; - } - } else { - String value = item.getValue(); - String whereTerm = transMysqlFilterTerm(item.getTerm()); - String whereValue = ""; - - if (StringUtils.equalsIgnoreCase(item.getTerm(), "null")) { - whereValue = ""; - } else if (StringUtils.equalsIgnoreCase(item.getTerm(), "not_null")) { - whereValue = ""; - } else if (StringUtils.equalsIgnoreCase(item.getTerm(), "empty")) { - whereValue = "''"; - } else if (StringUtils.equalsIgnoreCase(item.getTerm(), "not_empty")) { - whereValue = "''"; - } else if (StringUtils.containsIgnoreCase(item.getTerm(), "in") || StringUtils.containsIgnoreCase(item.getTerm(), "not in")) { - whereValue = "('" + String.join("','", value.split(",")) + "')"; - } else if (StringUtils.containsIgnoreCase(item.getTerm(), "like")) { - whereValue = "'%" + value + "%'"; - } else { - whereValue = String.format(MySQLConstants.WHERE_VALUE_VALUE, value); - } - SQLObj build = SQLObj.builder() - .whereField(whereName) - .whereTermAndValue(whereTerm + whereValue) - .build(); - res = build.getWhereField() + " " + build.getWhereTermAndValue(); - } - return res; - } - - @Override - public String convertTableToSql(String tableName, Datasource ds) { - return createSQLPreview("SELECT * FROM " + String.format(MySQLConstants.KEYWORD_TABLE, tableName), null); - } - - public String transMysqlFilterTerm(String term) { - switch (term) { - case "eq": - return " = "; - case "not_eq": - return " <> "; - case "lt": - return " < "; - case "le": - return " <= "; - case "gt": - return " > "; - case "ge": - return " >= "; - case "in": - return " IN "; - case "not in": - return " NOT IN "; - case "like": - return " LIKE "; - case "not like": - return " NOT LIKE "; - case "null": - return " IS NULL "; - case "not_null": - return " IS NOT NULL "; - case "empty": - return " = "; - case "not_empty": - return " <> "; - case "between": - return " BETWEEN "; - default: - return ""; - } - } - - public String transCustomFilterList(SQLObj tableObj, List requestList) { - if (CollectionUtils.isEmpty(requestList)) { - return null; - } - List res = new ArrayList<>(); - for (ChartFieldCustomFilterDTO request : requestList) { - List list = new ArrayList<>(); - DatasetTableField field = request.getField(); - - if (ObjectUtils.isEmpty(field)) { - continue; - } - String whereName = ""; - String originName; - if (ObjectUtils.isNotEmpty(field.getExtField()) && field.getExtField() == 2) { - // 解析origin name中有关联的字段生成sql表达式 - originName = calcFieldRegex(field.getOriginName(), tableObj); - } else if (ObjectUtils.isNotEmpty(field.getExtField()) && field.getExtField() == 1) { - originName = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), field.getOriginName()); - } else { - originName = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), field.getOriginName()); - } - if (field.getDeType() == 1) { - if (field.getDeExtractType() == 0 || field.getDeExtractType() == 5) { - whereName = String.format(MySQLConstants.STR_TO_DATE, originName, StringUtils.isNotEmpty(field.getDateFormat()) ? field.getDateFormat() : MysqlConstants.DEFAULT_DATE_FORMAT); - } - if (field.getDeExtractType() == 2 || field.getDeExtractType() == 3 || field.getDeExtractType() == 4) { - String cast = String.format(MySQLConstants.CAST, originName, MySQLConstants.DEFAULT_INT_FORMAT) + "/1000"; - whereName = String.format(MySQLConstants.FROM_UNIXTIME, cast, MySQLConstants.DEFAULT_DATE_FORMAT); - } - if (field.getDeExtractType() == 1) { - whereName = originName; - } - } else if (field.getDeType() == 2 || field.getDeType() == 3) { - if (field.getDeExtractType() == 0 || field.getDeExtractType() == 5) { - whereName = String.format(MySQLConstants.CAST, originName, MySQLConstants.DEFAULT_FLOAT_FORMAT); - } - if (field.getDeExtractType() == 1) { - whereName = String.format(MySQLConstants.UNIX_TIMESTAMP, originName); - } - if (field.getDeExtractType() == 2 || field.getDeExtractType() == 3 || field.getDeExtractType() == 4) { - whereName = originName; - } - } else { - whereName = originName; - } - - if (StringUtils.equalsIgnoreCase(request.getFilterType(), "enum")) { - if (CollectionUtils.isNotEmpty(request.getEnumCheckField())) { - res.add("(" + whereName + " IN ('" + String.join("','", request.getEnumCheckField()) + "'))"); - } - } else { - List filter = request.getFilter(); - for (ChartCustomFilterItemDTO filterItemDTO : filter) { - String value = filterItemDTO.getValue(); - String whereTerm = transMysqlFilterTerm(filterItemDTO.getTerm()); - String whereValue = ""; - - if (StringUtils.equalsIgnoreCase(filterItemDTO.getTerm(), "null")) { - whereValue = ""; - } else if (StringUtils.equalsIgnoreCase(filterItemDTO.getTerm(), "not_null")) { - whereValue = ""; - } else if (StringUtils.equalsIgnoreCase(filterItemDTO.getTerm(), "empty")) { - whereValue = "''"; - } else if (StringUtils.equalsIgnoreCase(filterItemDTO.getTerm(), "not_empty")) { - whereValue = "''"; - } else if (StringUtils.containsIgnoreCase(filterItemDTO.getTerm(), "in") || StringUtils.containsIgnoreCase(filterItemDTO.getTerm(), "not in")) { - whereValue = "('" + String.join("','", value.split(",")) + "')"; - } else if (StringUtils.containsIgnoreCase(filterItemDTO.getTerm(), "like")) { - whereValue = "'%" + value + "%'"; - } else { - whereValue = String.format(MySQLConstants.WHERE_VALUE_VALUE, value); - } - list.add(SQLObj.builder() - .whereField(whereName) - .whereTermAndValue(whereTerm + whereValue) - .build()); - } - List strList = new ArrayList<>(); - list.forEach(ele -> strList.add(ele.getWhereField() + " " + ele.getWhereTermAndValue())); - if (CollectionUtils.isNotEmpty(list)) { - res.add("(" + String.join(" " + getLogic(request.getLogic()) + " ", strList) + ")"); - } - } - } - return CollectionUtils.isNotEmpty(res) ? "(" + String.join(" AND ", res) + ")" : null; - } - - public String transExtFilterList(SQLObj tableObj, List requestList) { - if (CollectionUtils.isEmpty(requestList)) { - return null; - } - List list = new ArrayList<>(); - for (ChartExtFilterRequest request : requestList) { - List value = request.getValue(); - - List whereNameList = new ArrayList<>(); - List fieldList = new ArrayList<>(); - if (request.getIsTree()) { - fieldList.addAll(request.getDatasetTableFieldList()); - } else { - fieldList.add(request.getDatasetTableField()); - } - - for (DatasetTableField field : fieldList) { - if (CollectionUtils.isEmpty(value) || ObjectUtils.isEmpty(field)) { - continue; - } - String whereName = ""; - - String originName; - if (ObjectUtils.isNotEmpty(field.getExtField()) && field.getExtField() == 2) { - // 解析origin name中有关联的字段生成sql表达式 - originName = calcFieldRegex(field.getOriginName(), tableObj); - } else if (ObjectUtils.isNotEmpty(field.getExtField()) && field.getExtField() == 1) { - originName = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), field.getOriginName()); - } else { - originName = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), field.getOriginName()); - } - - if (field.getDeType() == 1) { - String format = transDateFormat(request.getDateStyle(), request.getDatePattern()); - if (field.getDeExtractType() == 0 || field.getDeExtractType() == 5 || field.getDeExtractType() == 1) { - if (StringUtils.equalsIgnoreCase(request.getDateStyle(),"y_Q")){ - whereName = String.format(format, - String.format(MysqlConstants.DATE_FORMAT, originName, "%Y"), - String.format(MysqlConstants.QUARTER, String.format(MysqlConstants.DATE_FORMAT, originName, MysqlConstants.DEFAULT_DATE_FORMAT))); - } else { - whereName = String.format(MySQLConstants.DATE_FORMAT, originName, format); - } - } - if (field.getDeExtractType() == 2 || field.getDeExtractType() == 3 || field.getDeExtractType() == 4) { - String cast = String.format(MySQLConstants.CAST, originName, MySQLConstants.DEFAULT_INT_FORMAT) + "/1000"; - if (StringUtils.equalsIgnoreCase(request.getDateStyle(),"y_Q")){ - whereName = String.format(format, - String.format(MysqlConstants.DATE_FORMAT, cast, "%Y"), - String.format(MysqlConstants.QUARTER, String.format(MysqlConstants.DATE_FORMAT, field, MysqlConstants.DEFAULT_DATE_FORMAT))); - } else { - whereName = String.format(MySQLConstants.DATE_FORMAT, cast, format); - } - } - } else if (field.getDeType() == 2 || field.getDeType() == 3) { - if (field.getDeExtractType() == 0 || field.getDeExtractType() == 5) { - whereName = String.format(MySQLConstants.CAST, originName, MySQLConstants.DEFAULT_FLOAT_FORMAT); - } - if (field.getDeExtractType() == 1) { - whereName = String.format(MySQLConstants.UNIX_TIMESTAMP, originName); - } - if (field.getDeExtractType() == 2 || field.getDeExtractType() == 3 || field.getDeExtractType() == 4) { - whereName = originName; - } - } else { - whereName = originName; - } - whereNameList.add(whereName); - } - - String whereName = ""; - if (request.getIsTree()) { - whereName = "CONCAT(" + StringUtils.join(whereNameList, ",',',") + ")"; - } else { - whereName = whereNameList.get(0); - } - String whereTerm = transMysqlFilterTerm(request.getOperator()); - String whereValue = ""; - - if (StringUtils.containsIgnoreCase(request.getOperator(), "in")) { - whereValue = "('" + StringUtils.join(value, "','") + "')"; - } else if (StringUtils.containsIgnoreCase(request.getOperator(), "like")) { - whereValue = "'%" + value.get(0) + "%'"; - } else if (StringUtils.containsIgnoreCase(request.getOperator(), "between")) { - if (request.getDatasetTableField().getDeType() == 1) { - SimpleDateFormat simpleDateFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss.SSS"); - String startTime = simpleDateFormat.format(new Date(Long.parseLong(value.get(0)))); - String endTime = simpleDateFormat.format(new Date(Long.parseLong(value.get(1)))); - whereValue = String.format(MySQLConstants.WHERE_BETWEEN, startTime, endTime); - } else { - whereValue = String.format(MySQLConstants.WHERE_BETWEEN, value.get(0), value.get(1)); - } - } else { - whereValue = String.format(MySQLConstants.WHERE_VALUE_VALUE, value.get(0)); - } - list.add(SQLObj.builder() - .whereField(whereName) - .whereTermAndValue(whereTerm + whereValue) - .build()); - } - List strList = new ArrayList<>(); - list.forEach(ele -> strList.add(ele.getWhereField() + " " + ele.getWhereTermAndValue())); - return CollectionUtils.isNotEmpty(list) ? "(" + String.join(" AND ", strList) + ")" : null; - } - - private String sqlFix(String sql) { - sql = sql.trim(); - if (sql.lastIndexOf(";") == (sql.length() - 1)) { - sql = sql.substring(0, sql.length() - 1); - } - return sql; - } - - private String transDateFormat(String dateStyle, String datePattern) { - String split = "-"; - if (StringUtils.equalsIgnoreCase(datePattern, "date_sub")) { - split = "-"; - } else if (StringUtils.equalsIgnoreCase(datePattern, "date_split")) { - split = "/"; - } else { - split = "-"; - } - - if (StringUtils.isEmpty(dateStyle)) { - return "%Y-%m-%d %H:%i:%S"; - } - - switch (dateStyle) { - case "y": - return "%Y"; - case "y_Q": - return "CONCAT(%s,'" + split + "',%s)"; - case "y_M": - return "%Y" + split + "%m"; - case "y_W": - return "%Y" + split + "%u"; - case "y_M_d": - return "%Y" + split + "%m" + split + "%d"; - case "H_m_s": - return "%H:%i:%S"; - case "y_M_d_H_m": - return "%Y" + split + "%m" + split + "%d" + " %H:%i"; - case "y_M_d_H_m_s": - return "%Y" + split + "%m" + split + "%d" + " %H:%i:%S"; - default: - return "%Y-%m-%d %H:%i:%S"; - } - } - - private SQLObj getXFields(ChartViewFieldDTO x, String originField, String fieldAlias) { - String fieldName = ""; - if (x.getDeExtractType() == 1) { - if (x.getDeType() == 2 || x.getDeType() == 3) { - fieldName = String.format(MySQLConstants.UNIX_TIMESTAMP, originField) + "*1000"; - } else if (x.getDeType() == 1) { - String format = transDateFormat(x.getDateStyle(), x.getDatePattern()); - if (x.getType().equalsIgnoreCase("YEAR")) { - if (StringUtils.equalsIgnoreCase(x.getDateStyle(), "y_Q")) { - fieldName = String.format(format, - String.format(MySQLConstants.DATE_FORMAT, "CONCAT(" + originField + ",'-01-01')", "%Y"), - String.format(MySQLConstants.QUARTER, "CONCAT(" + originField + ",'-01-01')")); - } else { - fieldName = String.format(MySQLConstants.DATE_FORMAT, "CONCAT(" + originField + ",'-01-01')", format); - } - } else if (x.getType().equalsIgnoreCase("TIME")) { - fieldName = String.format(MySQLConstants.DATE_FORMAT, "CONCAT('1970-01-01', " + originField + ")", MySQLConstants.DEFAULT_DATE_FORMAT); - } else { - if (StringUtils.equalsIgnoreCase(x.getDateStyle(), "y_Q")) { - fieldName = String.format(format, - String.format(MySQLConstants.DATE_FORMAT, originField, "%Y"), - String.format(MySQLConstants.QUARTER, originField)); - } else { - fieldName = String.format(MySQLConstants.DATE_FORMAT, originField, format); - } - } - } else { - fieldName = originField; - } - } else { - if (x.getDeType() == 1) { - String format = transDateFormat(x.getDateStyle(), x.getDatePattern()); - if (x.getDeExtractType() == 0) { - if (StringUtils.equalsIgnoreCase(x.getDateStyle(), "y_Q")) { - fieldName = String.format(format, - String.format(MysqlConstants.DATE_FORMAT, String.format(MySQLConstants.STR_TO_DATE, originField, StringUtils.isNotEmpty(x.getDateFormat()) ? x.getDateFormat() : MysqlConstants.DEFAULT_DATE_FORMAT), "%Y"), - String.format(MysqlConstants.QUARTER, String.format(MySQLConstants.STR_TO_DATE, originField, StringUtils.isNotEmpty(x.getDateFormat()) ? x.getDateFormat() : MysqlConstants.DEFAULT_DATE_FORMAT))); - } else { - fieldName = String.format(MySQLConstants.DATE_FORMAT, String.format(MySQLConstants.STR_TO_DATE, originField, StringUtils.isNotEmpty(x.getDateFormat()) ? x.getDateFormat() : MysqlConstants.DEFAULT_DATE_FORMAT), format); - } - } else { - String cast = String.format(MySQLConstants.CAST, originField, MySQLConstants.DEFAULT_INT_FORMAT) + "/1000"; - String from_unixtime = String.format(MySQLConstants.FROM_UNIXTIME, cast, MySQLConstants.DEFAULT_DATE_FORMAT); - if (StringUtils.equalsIgnoreCase(x.getDateStyle(), "y_Q")) { - fieldName = String.format(format, - String.format(MySQLConstants.DATE_FORMAT, from_unixtime, "%Y"), - String.format(MySQLConstants.QUARTER, from_unixtime)); - } else { - fieldName = String.format(MySQLConstants.DATE_FORMAT, from_unixtime, format); - } - } - } else { - if (x.getDeType() == DeTypeConstants.DE_INT) { - fieldName = String.format(MySQLConstants.CAST, originField, MySQLConstants.DEFAULT_INT_FORMAT); - } else if (x.getDeType() == DeTypeConstants.DE_FLOAT) { - fieldName = String.format(MySQLConstants.CAST, originField, MySQLConstants.DEFAULT_FLOAT_FORMAT); - } else { - fieldName = originField; - } - } - } - return SQLObj.builder() - .fieldName(fieldName) - .fieldAlias(fieldAlias) - .build(); - } - - private List getXWheres(ChartViewFieldDTO x, String originField, String fieldAlias) { - List list = new ArrayList<>(); - if (CollectionUtils.isNotEmpty(x.getFilter()) && x.getFilter().size() > 0) { - x.getFilter().forEach(f -> { - String whereName = ""; - String whereTerm = transMysqlFilterTerm(f.getTerm()); - String whereValue = ""; - if (x.getDeType() == 1 && x.getDeExtractType() != 1) { - String cast = String.format(MySQLConstants.CAST, originField, MySQLConstants.DEFAULT_INT_FORMAT) + "/1000"; - whereName = String.format(MySQLConstants.FROM_UNIXTIME, cast, MySQLConstants.DEFAULT_DATE_FORMAT); - } else { - whereName = originField; - } - if (StringUtils.equalsIgnoreCase(f.getTerm(), "null")) { - whereValue = ""; - } else if (StringUtils.equalsIgnoreCase(f.getTerm(), "not_null")) { - whereValue = ""; - } else if (StringUtils.equalsIgnoreCase(f.getTerm(), "empty")) { - whereValue = "''"; - } else if (StringUtils.equalsIgnoreCase(f.getTerm(), "not_empty")) { - whereValue = "''"; - } else if (StringUtils.containsIgnoreCase(f.getTerm(), "in")) { - whereValue = "('" + StringUtils.join(f.getValue(), "','") + "')"; - } else if (StringUtils.containsIgnoreCase(f.getTerm(), "like")) { - whereValue = "'%" + f.getValue() + "%'"; - } else { - whereValue = String.format(MySQLConstants.WHERE_VALUE_VALUE, f.getValue()); - } - list.add(SQLObj.builder() - .whereField(whereName) - .whereAlias(fieldAlias) - .whereTermAndValue(whereTerm + whereValue) - .build()); - }); - } - return list; - } - - private SQLObj getYFields(ChartViewFieldDTO y, String originField, String fieldAlias) { - String fieldName = ""; - if (StringUtils.equalsIgnoreCase(y.getOriginName(), "*")) { - fieldName = MySQLConstants.AGG_COUNT; - } else if (SQLConstants.DIMENSION_TYPE.contains(y.getDeType())) { - if (StringUtils.equalsIgnoreCase(y.getSummary(), "count_distinct")) { - fieldName = String.format(MySQLConstants.AGG_FIELD, "COUNT", "DISTINCT " + originField); - } else if (StringUtils.equalsIgnoreCase(y.getSummary(), "group_concat")) { - fieldName = String.format(MySQLConstants.GROUP_CONCAT, originField); - } else { - fieldName = String.format(MySQLConstants.AGG_FIELD, y.getSummary(), originField); - } - } else { - if (StringUtils.equalsIgnoreCase(y.getSummary(), "avg") || StringUtils.containsIgnoreCase(y.getSummary(), "pop")) { - String cast = String.format(MySQLConstants.CAST, originField, y.getDeType() == 2 ? MySQLConstants.DEFAULT_INT_FORMAT : MySQLConstants.DEFAULT_FLOAT_FORMAT); - String agg = String.format(MySQLConstants.AGG_FIELD, y.getSummary(), cast); - fieldName = String.format(MySQLConstants.CAST, agg, MySQLConstants.DEFAULT_FLOAT_FORMAT); - } else { - String cast = String.format(MySQLConstants.CAST, originField, y.getDeType() == 2 ? MySQLConstants.DEFAULT_INT_FORMAT : MySQLConstants.DEFAULT_FLOAT_FORMAT); - if (StringUtils.equalsIgnoreCase(y.getSummary(), "count_distinct")) { - fieldName = String.format(MySQLConstants.AGG_FIELD, "COUNT", "DISTINCT " + cast); - } else { - fieldName = String.format(MySQLConstants.AGG_FIELD, y.getSummary(), cast); - } - } - } - return SQLObj.builder() - .fieldName(fieldName) - .fieldAlias(fieldAlias) - .build(); - } - - private String getYWheres(ChartViewFieldDTO y, String originField, String fieldAlias) { - List list = new ArrayList<>(); - if (CollectionUtils.isNotEmpty(y.getFilter()) && y.getFilter().size() > 0) { - y.getFilter().forEach(f -> { - String whereTerm = transMysqlFilterTerm(f.getTerm()); - String whereValue = ""; - // 原始类型不是时间,在de中被转成时间的字段做处理 - if (StringUtils.equalsIgnoreCase(f.getTerm(), "null")) { - whereValue = ""; - } else if (StringUtils.equalsIgnoreCase(f.getTerm(), "not_null")) { - whereValue = ""; - } else if (StringUtils.equalsIgnoreCase(f.getTerm(), "empty")) { - whereValue = "''"; - } else if (StringUtils.equalsIgnoreCase(f.getTerm(), "not_empty")) { - whereValue = "''"; - } else if (StringUtils.containsIgnoreCase(f.getTerm(), "in")) { - whereValue = "('" + StringUtils.join(f.getValue(), "','") + "')"; - } else if (StringUtils.containsIgnoreCase(f.getTerm(), "like")) { - whereValue = "'%" + f.getValue() + "%'"; - } else { - whereValue = String.format(MySQLConstants.WHERE_VALUE_VALUE, f.getValue()); - } - list.add(SQLObj.builder() - .whereField(fieldAlias) - .whereAlias(fieldAlias) - .whereTermAndValue(whereTerm + whereValue) - .build()); - }); - } - List strList = new ArrayList<>(); - list.forEach(ele -> strList.add(ele.getWhereField() + " " + ele.getWhereTermAndValue())); - return CollectionUtils.isNotEmpty(list) ? "(" + String.join(" " + getLogic(y.getLogic()) + " ", strList) + ")" : null; - } - - private String calcFieldRegex(String originField, SQLObj tableObj) { - originField = originField.replaceAll("[\\t\\n\\r]]", ""); - // 正则提取[xxx] - String regex = "\\[(.*?)]"; - Pattern pattern = Pattern.compile(regex); - Matcher matcher = pattern.matcher(originField); - Set ids = new HashSet<>(); - while (matcher.find()) { - String id = matcher.group(1); - ids.add(id); - } - if (CollectionUtils.isEmpty(ids)) { - return originField; - } - DatasetTableFieldExample datasetTableFieldExample = new DatasetTableFieldExample(); - datasetTableFieldExample.createCriteria().andIdIn(new ArrayList<>(ids)); - List calcFields = datasetTableFieldMapper.selectByExample(datasetTableFieldExample); - for (DatasetTableField ele : calcFields) { - originField = originField.replaceAll("\\[" + ele.getId() + "]", - String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), ele.getOriginName())); - } - return originField; - } - - private String sqlLimit(String sql, ChartViewWithBLOBs view) { - if (StringUtils.equalsIgnoreCase(view.getResultMode(), "custom")) { - return sql + " LIMIT 0," + view.getResultCount(); - } else { - return sql; - } - } - - public String sqlForPreview(String table, Datasource ds) { - return "SELECT * FROM " + String.format(MySQLConstants.KEYWORD_TABLE, table); - } - - public List dateformat() { - return JSONArray.parseArray("[\n" + - "{\"dateformat\": \"%Y-%m-%d\"},\n" + - "{\"dateformat\": \"%Y/%m/%d\"},\n" + - "{\"dateformat\": \"%Y%m%d\"},\n" + - "{\"dateformat\": \"%Y-%m-%d %H:%i:%S\"},\n" + - "{\"dateformat\": \"%Y/%m/%d %H:%i:%S\"},\n" + - "{\"dateformat\": \"%Y%m%d %H:%i:%S\"}\n" + - "]", Dateformat.class); - } - -} +package io.dataease.provider.query.mysql; + +import com.alibaba.fastjson.JSONArray; +import io.dataease.plugins.common.base.domain.ChartViewWithBLOBs; +import io.dataease.plugins.common.base.domain.DatasetTableField; +import io.dataease.plugins.common.base.domain.DatasetTableFieldExample; +import io.dataease.plugins.common.base.domain.Datasource; +import io.dataease.plugins.common.base.mapper.DatasetTableFieldMapper; +import io.dataease.plugins.common.constants.DeTypeConstants; +import io.dataease.plugins.common.constants.datasource.MySQLConstants; +import io.dataease.plugins.common.constants.datasource.SQLConstants; +import io.dataease.plugins.common.constants.engine.MysqlConstants; +import io.dataease.plugins.common.dto.chart.ChartCustomFilterItemDTO; +import io.dataease.plugins.common.dto.chart.ChartFieldCustomFilterDTO; +import io.dataease.plugins.common.dto.chart.ChartViewFieldDTO; +import io.dataease.plugins.common.dto.datasource.DeSortField; +import io.dataease.plugins.common.dto.sqlObj.SQLObj; +import io.dataease.plugins.common.request.chart.ChartExtFilterRequest; +import io.dataease.plugins.common.request.permission.DataSetRowPermissionsTreeDTO; +import io.dataease.plugins.common.request.permission.DatasetRowPermissionsTreeItem; +import io.dataease.plugins.datasource.entity.Dateformat; +import io.dataease.plugins.datasource.entity.PageInfo; +import io.dataease.plugins.datasource.query.QueryProvider; +import io.dataease.plugins.datasource.query.Utils; +import org.apache.commons.collections4.CollectionUtils; +import org.apache.commons.lang3.ObjectUtils; +import org.apache.commons.lang3.StringUtils; +import org.springframework.stereotype.Service; +import org.stringtemplate.v4.ST; +import org.stringtemplate.v4.STGroup; +import org.stringtemplate.v4.STGroupFile; + +import javax.annotation.Resource; +import java.text.MessageFormat; +import java.text.SimpleDateFormat; +import java.util.*; +import java.util.regex.Matcher; +import java.util.regex.Pattern; +import java.util.stream.Collectors; + +import static io.dataease.plugins.common.constants.datasource.SQLConstants.TABLE_ALIAS_PREFIX; + + +/** + * @Author gin + * @Date 2021/5/17 2:43 下午 + */ +@Service("mysqlQueryProvider") +public class MysqlQueryProvider extends QueryProvider { + @Resource + private DatasetTableFieldMapper datasetTableFieldMapper; + + @Override + public Integer transFieldType(String field) { + switch (field) { + case "CHAR": + case "VARCHAR": + case "TEXT": + case "TINYTEXT": + case "MEDIUMTEXT": + case "LONGTEXT": + case "ENUM": + return 0;// 文本 + case "DATE": + case "TIME": + case "YEAR": + case "DATETIME": + case "TIMESTAMP": + return 1;// 时间 + case "INT": + case "SMALLINT": + case "MEDIUMINT": + case "INTEGER": + case "BIGINT": + case "LONG": //增加了LONG类型 + return 2;// 整型 + case "FLOAT": + case "DOUBLE": + case "DECIMAL": + return 3;// 浮点 + case "BIT": + case "TINYINT": + return 4;// 布尔 + default: + return 0; + } + } + + @Override + public String createSQLPreview(String sql, String orderBy) { + return "SELECT * FROM (" + sqlFix(sql) + ") AS tmp " + " LIMIT 0,1000"; + } + + @Override + public String createQuerySQL(String table, List fields, boolean isGroup, Datasource ds, List fieldCustomFilter, List rowPermissionsTree) { + return createQuerySQL(table, fields, isGroup, ds, fieldCustomFilter, rowPermissionsTree, null); + } + + @Override + public String createQuerySQLAsTmp(String sql, List fields, boolean isGroup, List fieldCustomFilter, List rowPermissionsTree) { + return createQuerySQL("(" + sqlFix(sql) + ")", fields, isGroup, null, fieldCustomFilter, rowPermissionsTree, null); + } + + private SQLObj buildSortField(DeSortField f, SQLObj tableObj, int index) { + String originField; + if (ObjectUtils.isNotEmpty(f.getExtField()) && f.getExtField() == 2) { + // 解析origin name中有关联的字段生成sql表达式 + originField = calcFieldRegex(f.getOriginName(), tableObj); + } else if (ObjectUtils.isNotEmpty(f.getExtField()) && f.getExtField() == 1) { + originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), f.getOriginName()); + } else { + originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), f.getOriginName()); + } + String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_X_PREFIX, index); + String fieldName = ""; + // 处理横轴字段 + if (f.getDeExtractType() == 1) { + if (f.getDeType() == 2 || f.getDeType() == 3) { + fieldName = String.format(MySQLConstants.UNIX_TIMESTAMP, originField) + "*1000"; + } else { + if (f.getType().equalsIgnoreCase("YEAR")) { + fieldName = String.format(MySQLConstants.DATE_FORMAT, "CONCAT(" + originField + ",'-01-01')", MySQLConstants.DEFAULT_DATE_FORMAT); + } else if (f.getType().equalsIgnoreCase("TIME")) { + fieldName = String.format(MySQLConstants.DATE_FORMAT, "CONCAT('1970-01-01', " + originField + ")", MySQLConstants.DEFAULT_DATE_FORMAT); + } else { + fieldName = String.format(MySQLConstants.DATE_FORMAT, originField, MySQLConstants.DEFAULT_DATE_FORMAT); + } + } + } else if (f.getDeExtractType() == 0) { + if (f.getDeType() == 2) { + fieldName = String.format(MySQLConstants.CAST, originField, MySQLConstants.DEFAULT_INT_FORMAT); + } else if (f.getDeType() == 3) { + fieldName = String.format(MySQLConstants.CAST, originField, MySQLConstants.DEFAULT_FLOAT_FORMAT); + } else if (f.getDeType() == 1) { + fieldName = StringUtils.isEmpty(f.getDateFormat()) ? String.format(MySQLConstants.STR_TO_DATE, originField, MysqlConstants.DEFAULT_DATE_FORMAT) : + String.format(MySQLConstants.DATE_FORMAT, String.format(MySQLConstants.STR_TO_DATE, originField, f.getDateFormat()), MySQLConstants.DEFAULT_DATE_FORMAT); + } else { + fieldName = originField; + } + } else { + if (f.getDeType() == 1) { + String cast = String.format(MySQLConstants.CAST, originField, MySQLConstants.DEFAULT_INT_FORMAT) + "/1000"; + fieldName = String.format(MySQLConstants.FROM_UNIXTIME, cast, MySQLConstants.DEFAULT_DATE_FORMAT); + } else if (f.getDeType() == 2) { + fieldName = String.format(MySQLConstants.CAST, originField, MySQLConstants.DEFAULT_INT_FORMAT); + } else { + fieldName = originField; + } + } + SQLObj result = SQLObj.builder().orderField(originField).orderAlias(originField).orderDirection(f.getOrderDirection()).build(); + return result; + + } + + @Override + public String createQuerySQL(String table, List fields, boolean isGroup, Datasource ds, List fieldCustomFilter, List rowPermissionsTree, List sortFields) { + SQLObj tableObj = SQLObj.builder() + .tableName((table.startsWith("(") && table.endsWith(")")) ? table : String.format(MySQLConstants.KEYWORD_TABLE, table)) + .tableAlias(String.format(TABLE_ALIAS_PREFIX, 0)) + .build(); + List xFields = new ArrayList<>(); + if (CollectionUtils.isNotEmpty(fields)) { + for (int i = 0; i < fields.size(); i++) { + DatasetTableField f = fields.get(i); + String originField; + if (ObjectUtils.isNotEmpty(f.getExtField()) && f.getExtField() == 2) { + // 解析origin name中有关联的字段生成sql表达式 + originField = calcFieldRegex(f.getOriginName(), tableObj); + } else if (ObjectUtils.isNotEmpty(f.getExtField()) && f.getExtField() == 1) { + originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), f.getOriginName()); + } else { + originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), f.getOriginName()); + } + String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_X_PREFIX, i); + String fieldName = ""; + // 处理横轴字段 + if (f.getDeExtractType() == 1) { + if (f.getDeType() == 2 || f.getDeType() == 3) { + fieldName = String.format(MySQLConstants.UNIX_TIMESTAMP, originField) + "*1000"; + } else { + if (f.getType().equalsIgnoreCase("YEAR")) { + fieldName = String.format(MySQLConstants.DATE_FORMAT, "CONCAT(" + originField + ",'-01-01')", MySQLConstants.DEFAULT_DATE_FORMAT); + } else if (f.getType().equalsIgnoreCase("TIME")) { + fieldName = String.format(MySQLConstants.DATE_FORMAT, "CONCAT('1970-01-01', " + originField + ")", MySQLConstants.DEFAULT_DATE_FORMAT); + } else { + fieldName = String.format(MySQLConstants.DATE_FORMAT, originField, MySQLConstants.DEFAULT_DATE_FORMAT); + } + } + } else if (f.getDeExtractType() == 0) { + if (f.getDeType() == 2) { + fieldName = String.format(MySQLConstants.CAST, originField, MySQLConstants.DEFAULT_INT_FORMAT); + } else if (f.getDeType() == 3) { + fieldName = String.format(MySQLConstants.CAST, originField, MySQLConstants.DEFAULT_FLOAT_FORMAT); + } else if (f.getDeType() == 1) { + fieldName = StringUtils.isEmpty(f.getDateFormat()) ? String.format(MySQLConstants.STR_TO_DATE, originField, MysqlConstants.DEFAULT_DATE_FORMAT) : + String.format(MySQLConstants.DATE_FORMAT, String.format(MySQLConstants.STR_TO_DATE, originField, f.getDateFormat()), MySQLConstants.DEFAULT_DATE_FORMAT); + } else { + fieldName = originField; + } + } else { + if (f.getDeType() == 1) { + String cast = String.format(MySQLConstants.CAST, originField, MySQLConstants.DEFAULT_INT_FORMAT) + "/1000"; + fieldName = String.format(MySQLConstants.FROM_UNIXTIME, cast, MySQLConstants.DEFAULT_DATE_FORMAT); + } else if (f.getDeType() == 2) { + fieldName = String.format(MySQLConstants.CAST, originField, MySQLConstants.DEFAULT_INT_FORMAT); + } else { + fieldName = originField; + } + } + xFields.add(SQLObj.builder() + .fieldName(fieldName) + .fieldAlias(fieldAlias) + .build()); + } + } + + + STGroup stg = new STGroupFile(SQLConstants.SQL_TEMPLATE); + ST st_sql = stg.getInstanceOf("previewSql"); + st_sql.add("isGroup", isGroup); + if (CollectionUtils.isNotEmpty(xFields)) st_sql.add("groups", xFields); + if (ObjectUtils.isNotEmpty(tableObj)) st_sql.add("table", tableObj); + + String customWheres = transCustomFilterList(tableObj, fieldCustomFilter); + String whereTrees = transFilterTrees(tableObj, rowPermissionsTree); + List wheres = new ArrayList<>(); + if (customWheres != null) wheres.add(customWheres); + if (whereTrees != null) wheres.add(whereTrees); + if (CollectionUtils.isNotEmpty(wheres)) st_sql.add("filters", wheres); + + List xOrders = new ArrayList<>(); + if (CollectionUtils.isNotEmpty(sortFields)) { + int step = fields.size(); + for (int i = step; i < (step + sortFields.size()); i++) { + DeSortField deSortField = sortFields.get(i - step); + SQLObj order = buildSortField(deSortField, tableObj, i); + xOrders.add(order); + } + } + if (ObjectUtils.isNotEmpty(xOrders)) { + st_sql.add("orders", xOrders); + } + + return st_sql.render(); + } + + @Override + public String createQuerySQLAsTmp(String sql, List fields, boolean isGroup, List fieldCustomFilter, List rowPermissionsTree, List sortFields) { + return createQuerySQL("(" + sqlFix(sql) + ")", fields, isGroup, null, fieldCustomFilter, rowPermissionsTree, sortFields); + } + + @Override + public String createQueryTableWithPage(String table, List fields, Integer page, Integer pageSize, Integer realSize, boolean isGroup, Datasource ds, List fieldCustomFilter, List rowPermissionsTree) { + return createQuerySQL(table, fields, isGroup, null, fieldCustomFilter, rowPermissionsTree) + " LIMIT " + (page - 1) * pageSize + "," + realSize; + } + + @Override + public String createQueryTableWithLimit(String table, List fields, Integer limit, boolean isGroup, Datasource ds, List fieldCustomFilter, List rowPermissionsTree) { + return createQuerySQL(table, fields, isGroup, null, fieldCustomFilter, rowPermissionsTree) + " LIMIT 0," + limit; + } + + @Override + public String createQuerySqlWithLimit(String sql, List fields, Integer limit, boolean isGroup, List fieldCustomFilter, List rowPermissionsTree) { + return createQuerySQLAsTmp(sql, fields, isGroup, fieldCustomFilter, rowPermissionsTree) + " LIMIT 0," + limit; + } + + @Override + public String createQuerySQLWithPage(String sql, List fields, Integer page, Integer pageSize, Integer realSize, boolean isGroup, List fieldCustomFilter, List rowPermissionsTree) { + return createQuerySQLAsTmp(sql, fields, isGroup, fieldCustomFilter, rowPermissionsTree) + " LIMIT " + (page - 1) * pageSize + "," + realSize; + } + + @Override + public String getSQL(String table, List xAxis, List yAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, Datasource ds, ChartViewWithBLOBs view) { + SQLObj tableObj = SQLObj.builder() + .tableName((table.startsWith("(") && table.endsWith(")")) ? table : String.format(MySQLConstants.KEYWORD_TABLE, table)) + .tableAlias(String.format(TABLE_ALIAS_PREFIX, 0)) + .build(); + List xFields = new ArrayList<>(); + List xOrders = new ArrayList<>(); + if (CollectionUtils.isNotEmpty(xAxis)) { + for (int i = 0; i < xAxis.size(); i++) { + ChartViewFieldDTO x = xAxis.get(i); + String originField; + if (ObjectUtils.isNotEmpty(x.getExtField()) && x.getExtField() == 2) { + // 解析origin name中有关联的字段生成sql表达式 + originField = calcFieldRegex(x.getOriginName(), tableObj); + } else if (ObjectUtils.isNotEmpty(x.getExtField()) && x.getExtField() == 1) { + originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), x.getOriginName()); + } else { + originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), x.getOriginName()); + } + String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_X_PREFIX, i); + // 处理横轴字段 + xFields.add(getXFields(x, originField, fieldAlias)); + // 处理横轴排序 + if (StringUtils.isNotEmpty(x.getSort()) && Utils.joinSort(x.getSort())) { + xOrders.add(SQLObj.builder() + .orderField(originField) + .orderAlias(fieldAlias) + .orderDirection(x.getSort()) + .build()); + } + } + } + List yFields = new ArrayList<>(); + List yWheres = new ArrayList<>(); + List yOrders = new ArrayList<>(); + if (CollectionUtils.isNotEmpty(yAxis)) { + for (int i = 0; i < yAxis.size(); i++) { + ChartViewFieldDTO y = yAxis.get(i); + String originField; + if (ObjectUtils.isNotEmpty(y.getExtField()) && y.getExtField() == 2) { + // 解析origin name中有关联的字段生成sql表达式 + originField = calcFieldRegex(y.getOriginName(), tableObj); + } else if (ObjectUtils.isNotEmpty(y.getExtField()) && y.getExtField() == 1) { + originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), y.getOriginName()); + } else { + originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), y.getOriginName()); + } + String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_Y_PREFIX, i); + // 处理纵轴字段 + yFields.add(getYFields(y, originField, fieldAlias)); + // 处理纵轴过滤 + yWheres.add(getYWheres(y, originField, fieldAlias)); + // 处理纵轴排序 + if (StringUtils.isNotEmpty(y.getSort()) && Utils.joinSort(y.getSort())) { + yOrders.add(SQLObj.builder() + .orderField(originField) + .orderAlias(fieldAlias) + .orderDirection(y.getSort()) + .build()); + } + } + } + // 处理视图中字段过滤 + String customWheres = transCustomFilterList(tableObj, fieldCustomFilter); + // 处理仪表板字段过滤 + String extWheres = transExtFilterList(tableObj, extFilterRequestList); + // row permissions tree + String whereTrees = transFilterTrees(tableObj, rowPermissionsTree); + // 构建sql所有参数 + List fields = new ArrayList<>(); + fields.addAll(xFields); + fields.addAll(yFields); + List wheres = new ArrayList<>(); + if (customWheres != null) wheres.add(customWheres); + if (extWheres != null) wheres.add(extWheres); + if (whereTrees != null) wheres.add(whereTrees); + List groups = new ArrayList<>(); + groups.addAll(xFields); + // 外层再次套sql + List orders = new ArrayList<>(); + orders.addAll(xOrders); + orders.addAll(yOrders); + List aggWheres = new ArrayList<>(); + aggWheres.addAll(yWheres.stream().filter(ObjectUtils::isNotEmpty).collect(Collectors.toList())); + + STGroup stg = new STGroupFile(SQLConstants.SQL_TEMPLATE); + ST st_sql = stg.getInstanceOf("querySql"); + if (CollectionUtils.isNotEmpty(xFields)) st_sql.add("groups", xFields); + if (CollectionUtils.isNotEmpty(yFields)) st_sql.add("aggregators", yFields); + if (CollectionUtils.isNotEmpty(wheres)) st_sql.add("filters", wheres); + if (ObjectUtils.isNotEmpty(tableObj)) st_sql.add("table", tableObj); + String sql = st_sql.render(); + + ST st = stg.getInstanceOf("querySql"); + SQLObj tableSQL = SQLObj.builder() + .tableName(String.format(MySQLConstants.BRACKETS, sql)) + .tableAlias(String.format(TABLE_ALIAS_PREFIX, 1)) + .build(); + if (CollectionUtils.isNotEmpty(aggWheres)) st.add("filters", aggWheres); + if (CollectionUtils.isNotEmpty(orders)) st.add("orders", orders); + if (ObjectUtils.isNotEmpty(tableSQL)) st.add("table", tableSQL); + return sqlLimit(st.render(), view); + } + + @Override + public String getSQLTableInfo(String table, List xAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, Datasource ds, ChartViewWithBLOBs view) { + return sqlLimit(originalTableInfo(table, xAxis, fieldCustomFilter, rowPermissionsTree, extFilterRequestList, ds, view), view); + } + + @Override + public String getSQLWithPage(boolean isTable, String table, List xAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, Datasource ds, ChartViewWithBLOBs view, PageInfo pageInfo) { + String limit = ((pageInfo.getGoPage() != null && pageInfo.getPageSize() != null) ? " LIMIT " + (pageInfo.getGoPage() - 1) * pageInfo.getPageSize() + "," + pageInfo.getPageSize() : ""); + if (isTable) { + return originalTableInfo(table, xAxis, fieldCustomFilter, rowPermissionsTree, extFilterRequestList, ds, view) + limit; + } else { + return originalTableInfo("(" + sqlFix(table) + ")", xAxis, fieldCustomFilter, rowPermissionsTree, extFilterRequestList, ds, view) + limit; + } + } + + private String originalTableInfo(String table, List xAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, Datasource ds, ChartViewWithBLOBs view) { + SQLObj tableObj = SQLObj.builder() + .tableName((table.startsWith("(") && table.endsWith(")")) ? table : String.format(MySQLConstants.KEYWORD_TABLE, table)) + .tableAlias(String.format(TABLE_ALIAS_PREFIX, 0)) + .build(); + List xFields = new ArrayList<>(); + List xOrders = new ArrayList<>(); + if (CollectionUtils.isNotEmpty(xAxis)) { + for (int i = 0; i < xAxis.size(); i++) { + ChartViewFieldDTO x = xAxis.get(i); + String originField; + if (ObjectUtils.isNotEmpty(x.getExtField()) && x.getExtField() == 2) { + // 解析origin name中有关联的字段生成sql表达式 + originField = calcFieldRegex(x.getOriginName(), tableObj); + } else if (ObjectUtils.isNotEmpty(x.getExtField()) && x.getExtField() == 1) { + originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), x.getOriginName()); + } else { + if (x.getDeType() == 2 || x.getDeType() == 3) { + originField = String.format(MySQLConstants.CAST, String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), x.getOriginName()), MySQLConstants.DEFAULT_FLOAT_FORMAT); + } else { + originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), x.getOriginName()); + } + } + String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_X_PREFIX, i); + // 处理横轴字段 + xFields.add(getXFields(x, originField, fieldAlias)); + // 处理横轴排序 + if (StringUtils.isNotEmpty(x.getSort()) && Utils.joinSort(x.getSort())) { + xOrders.add(SQLObj.builder() + .orderField(originField) + .orderAlias(fieldAlias) + .orderDirection(x.getSort()) + .build()); + } + } + } + // 处理视图中字段过滤 + String customWheres = transCustomFilterList(tableObj, fieldCustomFilter); + // 处理仪表板字段过滤 + String extWheres = transExtFilterList(tableObj, extFilterRequestList); + // row permissions tree + String whereTrees = transFilterTrees(tableObj, rowPermissionsTree); + // 构建sql所有参数 + List fields = new ArrayList<>(); + fields.addAll(xFields); + List wheres = new ArrayList<>(); + if (customWheres != null) wheres.add(customWheres); + if (extWheres != null) wheres.add(extWheres); + if (whereTrees != null) wheres.add(whereTrees); + List groups = new ArrayList<>(); + groups.addAll(xFields); + // 外层再次套sql + List orders = new ArrayList<>(); + orders.addAll(xOrders); + + STGroup stg = new STGroupFile(SQLConstants.SQL_TEMPLATE); + ST st_sql = stg.getInstanceOf("previewSql"); + st_sql.add("isGroup", false); + if (CollectionUtils.isNotEmpty(xFields)) st_sql.add("groups", xFields); + if (CollectionUtils.isNotEmpty(wheres)) st_sql.add("filters", wheres); + if (ObjectUtils.isNotEmpty(tableObj)) st_sql.add("table", tableObj); + String sql = st_sql.render(); + + ST st = stg.getInstanceOf("previewSql"); + st.add("isGroup", false); + SQLObj tableSQL = SQLObj.builder() + .tableName(String.format(MySQLConstants.BRACKETS, sql)) + .tableAlias(String.format(TABLE_ALIAS_PREFIX, 1)) + .build(); + if (CollectionUtils.isNotEmpty(orders)) st.add("orders", orders); + if (ObjectUtils.isNotEmpty(tableSQL)) st.add("table", tableSQL); + return st.render(); + } + + @Override + public String getSQLAsTmpTableInfo(String sql, List xAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, Datasource ds, ChartViewWithBLOBs view) { + return getSQLTableInfo("(" + sqlFix(sql) + ")", xAxis, fieldCustomFilter, rowPermissionsTree, extFilterRequestList, null, view); + } + + + @Override + public String getSQLAsTmp(String sql, List xAxis, List yAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, ChartViewWithBLOBs view) { + return getSQL("(" + sqlFix(sql) + ")", xAxis, yAxis, fieldCustomFilter, rowPermissionsTree, extFilterRequestList, null, view); + } + + @Override + public String getSQLStack(String table, List xAxis, List yAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, List extStack, Datasource ds, ChartViewWithBLOBs view) { + SQLObj tableObj = SQLObj.builder() + .tableName((table.startsWith("(") && table.endsWith(")")) ? table : String.format(MySQLConstants.KEYWORD_TABLE, table)) + .tableAlias(String.format(TABLE_ALIAS_PREFIX, 0)) + .build(); + List xFields = new ArrayList<>(); + List xOrders = new ArrayList<>(); + List xList = new ArrayList<>(); + xList.addAll(xAxis); + xList.addAll(extStack); + if (CollectionUtils.isNotEmpty(xList)) { + for (int i = 0; i < xList.size(); i++) { + ChartViewFieldDTO x = xList.get(i); + String originField; + if (ObjectUtils.isNotEmpty(x.getExtField()) && x.getExtField() == 2) { + // 解析origin name中有关联的字段生成sql表达式 + originField = calcFieldRegex(x.getOriginName(), tableObj); + } else if (ObjectUtils.isNotEmpty(x.getExtField()) && x.getExtField() == 1) { + originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), x.getOriginName()); + } else { + originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), x.getOriginName()); + } + String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_X_PREFIX, i); + // 处理横轴字段 + xFields.add(getXFields(x, originField, fieldAlias)); + // 处理横轴排序 + if (StringUtils.isNotEmpty(x.getSort()) && Utils.joinSort(x.getSort())) { + xOrders.add(SQLObj.builder() + .orderField(originField) + .orderAlias(fieldAlias) + .orderDirection(x.getSort()) + .build()); + } + } + } + List yFields = new ArrayList<>(); + List yWheres = new ArrayList<>(); + List yOrders = new ArrayList<>(); + if (CollectionUtils.isNotEmpty(yAxis)) { + for (int i = 0; i < yAxis.size(); i++) { + ChartViewFieldDTO y = yAxis.get(i); + String originField; + if (ObjectUtils.isNotEmpty(y.getExtField()) && y.getExtField() == 2) { + // 解析origin name中有关联的字段生成sql表达式 + originField = calcFieldRegex(y.getOriginName(), tableObj); + } else if (ObjectUtils.isNotEmpty(y.getExtField()) && y.getExtField() == 1) { + originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), y.getOriginName()); + } else { + originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), y.getOriginName()); + } + String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_Y_PREFIX, i); + // 处理纵轴字段 + yFields.add(getYFields(y, originField, fieldAlias)); + // 处理纵轴过滤 + yWheres.add(getYWheres(y, originField, fieldAlias)); + // 处理纵轴排序 + if (StringUtils.isNotEmpty(y.getSort()) && Utils.joinSort(y.getSort())) { + yOrders.add(SQLObj.builder() + .orderField(originField) + .orderAlias(fieldAlias) + .orderDirection(y.getSort()) + .build()); + } + } + } + // 处理视图中字段过滤 + String customWheres = transCustomFilterList(tableObj, fieldCustomFilter); + // 处理仪表板字段过滤 + String extWheres = transExtFilterList(tableObj, extFilterRequestList); + // row permissions tree + String whereTrees = transFilterTrees(tableObj, rowPermissionsTree); + // 构建sql所有参数 + List fields = new ArrayList<>(); + fields.addAll(xFields); + fields.addAll(yFields); + List wheres = new ArrayList<>(); + if (customWheres != null) wheres.add(customWheres); + if (extWheres != null) wheres.add(extWheres); + if (whereTrees != null) wheres.add(whereTrees); + List groups = new ArrayList<>(); + groups.addAll(xFields); + // 外层再次套sql + List orders = new ArrayList<>(); + orders.addAll(xOrders); + orders.addAll(yOrders); + List aggWheres = new ArrayList<>(); + aggWheres.addAll(yWheres.stream().filter(ObjectUtils::isNotEmpty).collect(Collectors.toList())); + + STGroup stg = new STGroupFile(SQLConstants.SQL_TEMPLATE); + ST st_sql = stg.getInstanceOf("querySql"); + if (CollectionUtils.isNotEmpty(xFields)) st_sql.add("groups", xFields); + if (CollectionUtils.isNotEmpty(yFields)) st_sql.add("aggregators", yFields); + if (CollectionUtils.isNotEmpty(wheres)) st_sql.add("filters", wheres); + if (ObjectUtils.isNotEmpty(tableObj)) st_sql.add("table", tableObj); + String sql = st_sql.render(); + + ST st = stg.getInstanceOf("querySql"); + SQLObj tableSQL = SQLObj.builder() + .tableName(String.format(MySQLConstants.BRACKETS, sql)) + .tableAlias(String.format(TABLE_ALIAS_PREFIX, 1)) + .build(); + if (CollectionUtils.isNotEmpty(aggWheres)) st.add("filters", aggWheres); + if (CollectionUtils.isNotEmpty(orders)) st.add("orders", orders); + if (ObjectUtils.isNotEmpty(tableSQL)) st.add("table", tableSQL); + return sqlLimit(st.render(), view); + } + + @Override + public String getSQLAsTmpStack(String table, List xAxis, List yAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, List extStack, ChartViewWithBLOBs view) { + return getSQLStack("(" + sqlFix(table) + ")", xAxis, yAxis, fieldCustomFilter, rowPermissionsTree, extFilterRequestList, extStack, null, view); + } + + @Override + public String getSQLScatter(String table, List xAxis, List yAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, List extBubble, Datasource ds, ChartViewWithBLOBs view) { + SQLObj tableObj = SQLObj.builder() + .tableName((table.startsWith("(") && table.endsWith(")")) ? table : String.format(MySQLConstants.KEYWORD_TABLE, table)) + .tableAlias(String.format(TABLE_ALIAS_PREFIX, 0)) + .build(); + List xFields = new ArrayList<>(); + List xOrders = new ArrayList<>(); + if (CollectionUtils.isNotEmpty(xAxis)) { + for (int i = 0; i < xAxis.size(); i++) { + ChartViewFieldDTO x = xAxis.get(i); + String originField; + if (ObjectUtils.isNotEmpty(x.getExtField()) && x.getExtField() == 2) { + // 解析origin name中有关联的字段生成sql表达式 + originField = calcFieldRegex(x.getOriginName(), tableObj); + } else if (ObjectUtils.isNotEmpty(x.getExtField()) && x.getExtField() == 1) { + originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), x.getOriginName()); + } else { + originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), x.getOriginName()); + } + String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_X_PREFIX, i); + // 处理横轴字段 + xFields.add(getXFields(x, originField, fieldAlias)); + // 处理横轴排序 + if (StringUtils.isNotEmpty(x.getSort()) && Utils.joinSort(x.getSort())) { + xOrders.add(SQLObj.builder() + .orderField(originField) + .orderAlias(fieldAlias) + .orderDirection(x.getSort()) + .build()); + } + } + } + List yFields = new ArrayList<>(); + List yWheres = new ArrayList<>(); + List yOrders = new ArrayList<>(); + List yList = new ArrayList<>(); + yList.addAll(yAxis); + yList.addAll(extBubble); + if (CollectionUtils.isNotEmpty(yList)) { + for (int i = 0; i < yList.size(); i++) { + ChartViewFieldDTO y = yList.get(i); + String originField; + if (ObjectUtils.isNotEmpty(y.getExtField()) && y.getExtField() == 2) { + // 解析origin name中有关联的字段生成sql表达式 + originField = calcFieldRegex(y.getOriginName(), tableObj); + } else if (ObjectUtils.isNotEmpty(y.getExtField()) && y.getExtField() == 1) { + originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), y.getOriginName()); + } else { + originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), y.getOriginName()); + } + String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_Y_PREFIX, i); + // 处理纵轴字段 + yFields.add(getYFields(y, originField, fieldAlias)); + // 处理纵轴过滤 + yWheres.add(getYWheres(y, originField, fieldAlias)); + // 处理纵轴排序 + if (StringUtils.isNotEmpty(y.getSort()) && Utils.joinSort(y.getSort())) { + yOrders.add(SQLObj.builder() + .orderField(originField) + .orderAlias(fieldAlias) + .orderDirection(y.getSort()) + .build()); + } + } + } + // 处理视图中字段过滤 + String customWheres = transCustomFilterList(tableObj, fieldCustomFilter); + // 处理仪表板字段过滤 + String extWheres = transExtFilterList(tableObj, extFilterRequestList); + // row permissions tree + String whereTrees = transFilterTrees(tableObj, rowPermissionsTree); + // 构建sql所有参数 + List fields = new ArrayList<>(); + fields.addAll(xFields); + fields.addAll(yFields); + List wheres = new ArrayList<>(); + if (customWheres != null) wheres.add(customWheres); + if (extWheres != null) wheres.add(extWheres); + if (whereTrees != null) wheres.add(whereTrees); + List groups = new ArrayList<>(); + groups.addAll(xFields); + // 外层再次套sql + List orders = new ArrayList<>(); + orders.addAll(xOrders); + orders.addAll(yOrders); + List aggWheres = new ArrayList<>(); + aggWheres.addAll(yWheres.stream().filter(ObjectUtils::isNotEmpty).collect(Collectors.toList())); + + STGroup stg = new STGroupFile(SQLConstants.SQL_TEMPLATE); + ST st_sql = stg.getInstanceOf("querySql"); + if (CollectionUtils.isNotEmpty(xFields)) st_sql.add("groups", xFields); + if (CollectionUtils.isNotEmpty(yFields)) st_sql.add("aggregators", yFields); + if (CollectionUtils.isNotEmpty(wheres)) st_sql.add("filters", wheres); + if (ObjectUtils.isNotEmpty(tableObj)) st_sql.add("table", tableObj); + String sql = st_sql.render(); + + ST st = stg.getInstanceOf("querySql"); + SQLObj tableSQL = SQLObj.builder() + .tableName(String.format(MySQLConstants.BRACKETS, sql)) + .tableAlias(String.format(TABLE_ALIAS_PREFIX, 1)) + .build(); + if (CollectionUtils.isNotEmpty(aggWheres)) st.add("filters", aggWheres); + if (CollectionUtils.isNotEmpty(orders)) st.add("orders", orders); + if (ObjectUtils.isNotEmpty(tableSQL)) st.add("table", tableSQL); + return sqlLimit(st.render(), view); + } + + @Override + public String getSQLAsTmpScatter(String table, List xAxis, List yAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, List extBubble, ChartViewWithBLOBs view) { + return getSQLScatter("(" + sqlFix(table) + ")", xAxis, yAxis, fieldCustomFilter, rowPermissionsTree, extFilterRequestList, extBubble, null, view); + } + + @Override + public String searchTable(String table) { + return "SELECT table_name FROM information_schema.TABLES WHERE table_name ='" + table + "'"; + } + + @Override + public String getSQLSummary(String table, List yAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, ChartViewWithBLOBs view, Datasource ds) { + // 字段汇总 排序等 + SQLObj tableObj = SQLObj.builder() + .tableName((table.startsWith("(") && table.endsWith(")")) ? table : String.format(MySQLConstants.KEYWORD_TABLE, table)) + .tableAlias(String.format(TABLE_ALIAS_PREFIX, 0)) + .build(); + List yFields = new ArrayList<>(); + List yWheres = new ArrayList<>(); + List yOrders = new ArrayList<>(); + if (CollectionUtils.isNotEmpty(yAxis)) { + for (int i = 0; i < yAxis.size(); i++) { + ChartViewFieldDTO y = yAxis.get(i); + String originField; + if (ObjectUtils.isNotEmpty(y.getExtField()) && y.getExtField() == 2) { + // 解析origin name中有关联的字段生成sql表达式 + originField = calcFieldRegex(y.getOriginName(), tableObj); + } else if (ObjectUtils.isNotEmpty(y.getExtField()) && y.getExtField() == 1) { + originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), y.getOriginName()); + } else { + originField = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), y.getOriginName()); + } + String fieldAlias = String.format(SQLConstants.FIELD_ALIAS_Y_PREFIX, i); + // 处理纵轴字段 + yFields.add(getYFields(y, originField, fieldAlias)); + // 处理纵轴过滤 + yWheres.add(getYWheres(y, originField, fieldAlias)); + // 处理纵轴排序 + if (StringUtils.isNotEmpty(y.getSort()) && Utils.joinSort(y.getSort())) { + yOrders.add(SQLObj.builder() + .orderField(originField) + .orderAlias(fieldAlias) + .orderDirection(y.getSort()) + .build()); + } + } + } + // 处理视图中字段过滤 + String customWheres = transCustomFilterList(tableObj, fieldCustomFilter); + // 处理仪表板字段过滤 + String extWheres = transExtFilterList(tableObj, extFilterRequestList); + // row permissions tree + String whereTrees = transFilterTrees(tableObj, rowPermissionsTree); + // 构建sql所有参数 + List fields = new ArrayList<>(); + fields.addAll(yFields); + List wheres = new ArrayList<>(); + if (customWheres != null) wheres.add(customWheres); + if (extWheres != null) wheres.add(extWheres); + if (whereTrees != null) wheres.add(whereTrees); + List groups = new ArrayList<>(); + // 外层再次套sql + List orders = new ArrayList<>(); + orders.addAll(yOrders); + List aggWheres = new ArrayList<>(); + aggWheres.addAll(yWheres.stream().filter(ObjectUtils::isNotEmpty).collect(Collectors.toList())); + + STGroup stg = new STGroupFile(SQLConstants.SQL_TEMPLATE); + ST st_sql = stg.getInstanceOf("querySql"); + if (CollectionUtils.isNotEmpty(yFields)) st_sql.add("aggregators", yFields); + if (CollectionUtils.isNotEmpty(wheres)) st_sql.add("filters", wheres); + if (ObjectUtils.isNotEmpty(tableObj)) st_sql.add("table", tableObj); + String sql = st_sql.render(); + + ST st = stg.getInstanceOf("querySql"); + SQLObj tableSQL = SQLObj.builder() + .tableName(String.format(MySQLConstants.BRACKETS, sql)) + .tableAlias(String.format(TABLE_ALIAS_PREFIX, 1)) + .build(); + if (CollectionUtils.isNotEmpty(aggWheres)) st.add("filters", aggWheres); + if (CollectionUtils.isNotEmpty(orders)) st.add("orders", orders); + if (ObjectUtils.isNotEmpty(tableSQL)) st.add("table", tableSQL); + return sqlLimit(st.render(), view); + } + + @Override + public String getSQLSummaryAsTmp(String sql, List yAxis, List fieldCustomFilter, List rowPermissionsTree, List extFilterRequestList, ChartViewWithBLOBs view) { + return getSQLSummary("(" + sqlFix(sql) + ")", yAxis, fieldCustomFilter, rowPermissionsTree, extFilterRequestList, view, null); + } + + @Override + public String wrapSql(String sql) { + sql = sql.trim(); + if (sql.lastIndexOf(";") == (sql.length() - 1)) { + sql = sql.substring(0, sql.length() - 1); + } + String tmpSql = "SELECT * FROM (" + sql + ") AS tmp " + " LIMIT 0"; + return tmpSql; + } + + @Override + public String createRawQuerySQL(String table, List fields, Datasource ds) { + String[] array = fields.stream().map(f -> { + StringBuilder stringBuilder = new StringBuilder(); + if (f.getDeExtractType() == 4) { // 处理 tinyint + stringBuilder.append("concat(`").append(f.getOriginName()).append("`,'') AS ").append(f.getDataeaseName()); + } else if (f.getDeExtractType() == 1 && f.getType().equalsIgnoreCase("YEAR")) { // 处理 YEAR + stringBuilder.append("").append(String.format(MySQLConstants.DATE_FORMAT, "CONCAT(" + f.getOriginName() + ",'-01-01')", MySQLConstants.DEFAULT_DATE_FORMAT)).append(" AS ").append(f.getDataeaseName()); + } else { + stringBuilder.append("`").append(f.getOriginName()).append("` AS ").append(f.getDataeaseName()); + } + return stringBuilder.toString(); + }).toArray(String[]::new); + table = table.trim().startsWith("(") ? table : String.format(MySQLConstants.KEYWORD_TABLE, table); + return MessageFormat.format("SELECT {0} FROM {1} LIMIT DE_OFFSET, DE_PAGE_SIZE ", StringUtils.join(array, ","), table); + } + + public String getTotalCount(boolean isTable, String sql, Datasource ds) { + if (isTable) { + return "SELECT COUNT(*) from " + String.format(MySQLConstants.KEYWORD_TABLE, sql); + } else { + return "SELECT COUNT(*) from ( " + sqlFix(sql) + " ) DE_COUNT_TEMP"; + } + } + + @Override + public String createRawQuerySQLAsTmp(String sql, List fields) { + return createRawQuerySQL("(" + sqlFix(sql) + ") AS DE_TEMP", fields, null); + } + + public String transTreeItem(SQLObj tableObj, DatasetRowPermissionsTreeItem item) { + String res = null; + DatasetTableField field = item.getField(); + if (ObjectUtils.isEmpty(field)) { + return null; + } + String whereName = ""; + String originName; + if (ObjectUtils.isNotEmpty(field.getExtField()) && field.getExtField() == 2) { + // 解析origin name中有关联的字段生成sql表达式 + originName = calcFieldRegex(field.getOriginName(), tableObj); + } else if (ObjectUtils.isNotEmpty(field.getExtField()) && field.getExtField() == 1) { + originName = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), field.getOriginName()); + } else { + originName = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), field.getOriginName()); + } + if (field.getDeType() == 1) { + if (field.getDeExtractType() == 0 || field.getDeExtractType() == 5) { + whereName = String.format(MySQLConstants.STR_TO_DATE, originName, StringUtils.isNotEmpty(field.getDateFormat()) ? field.getDateFormat() : MysqlConstants.DEFAULT_DATE_FORMAT); + } + if (field.getDeExtractType() == 2 || field.getDeExtractType() == 3 || field.getDeExtractType() == 4) { + String cast = String.format(MySQLConstants.CAST, originName, MySQLConstants.DEFAULT_INT_FORMAT) + "/1000"; + whereName = String.format(MySQLConstants.FROM_UNIXTIME, cast, MySQLConstants.DEFAULT_DATE_FORMAT); + } + if (field.getDeExtractType() == 1) { + whereName = originName; + } + } else if (field.getDeType() == 2 || field.getDeType() == 3) { + if (field.getDeExtractType() == 0 || field.getDeExtractType() == 5) { + whereName = String.format(MySQLConstants.CAST, originName, MySQLConstants.DEFAULT_FLOAT_FORMAT); + } + if (field.getDeExtractType() == 1) { + whereName = String.format(MySQLConstants.UNIX_TIMESTAMP, originName); + } + if (field.getDeExtractType() == 2 || field.getDeExtractType() == 3 || field.getDeExtractType() == 4) { + whereName = originName; + } + } else { + whereName = originName; + } + + if (StringUtils.equalsIgnoreCase(item.getFilterType(), "enum")) { + if (CollectionUtils.isNotEmpty(item.getEnumValue())) { + res = "(" + whereName + " IN ('" + String.join("','", item.getEnumValue()) + "'))"; + } + } else { + String value = item.getValue(); + String whereTerm = transMysqlFilterTerm(item.getTerm()); + String whereValue = ""; + + if (StringUtils.equalsIgnoreCase(item.getTerm(), "null")) { + whereValue = ""; + } else if (StringUtils.equalsIgnoreCase(item.getTerm(), "not_null")) { + whereValue = ""; + } else if (StringUtils.equalsIgnoreCase(item.getTerm(), "empty")) { + whereValue = "''"; + } else if (StringUtils.equalsIgnoreCase(item.getTerm(), "not_empty")) { + whereValue = "''"; + } else if (StringUtils.containsIgnoreCase(item.getTerm(), "in") || StringUtils.containsIgnoreCase(item.getTerm(), "not in")) { + whereValue = "('" + String.join("','", value.split(",")) + "')"; + } else if (StringUtils.containsIgnoreCase(item.getTerm(), "like")) { + whereValue = "'%" + value + "%'"; + } else { + whereValue = String.format(MySQLConstants.WHERE_VALUE_VALUE, value); + } + SQLObj build = SQLObj.builder() + .whereField(whereName) + .whereTermAndValue(whereTerm + whereValue) + .build(); + res = build.getWhereField() + " " + build.getWhereTermAndValue(); + } + return res; + } + + @Override + public String convertTableToSql(String tableName, Datasource ds) { + return createSQLPreview("SELECT * FROM " + String.format(MySQLConstants.KEYWORD_TABLE, tableName), null); + } + + public String transMysqlFilterTerm(String term) { + switch (term) { + case "eq": + return " = "; + case "not_eq": + return " <> "; + case "lt": + return " < "; + case "le": + return " <= "; + case "gt": + return " > "; + case "ge": + return " >= "; + case "in": + return " IN "; + case "not in": + return " NOT IN "; + case "like": + return " LIKE "; + case "not like": + return " NOT LIKE "; + case "null": + return " IS NULL "; + case "not_null": + return " IS NOT NULL "; + case "empty": + return " = "; + case "not_empty": + return " <> "; + case "between": + return " BETWEEN "; + default: + return ""; + } + } + + public String transCustomFilterList(SQLObj tableObj, List requestList) { + if (CollectionUtils.isEmpty(requestList)) { + return null; + } + List res = new ArrayList<>(); + for (ChartFieldCustomFilterDTO request : requestList) { + List list = new ArrayList<>(); + DatasetTableField field = request.getField(); + + if (ObjectUtils.isEmpty(field)) { + continue; + } + String whereName = ""; + String originName; + if (ObjectUtils.isNotEmpty(field.getExtField()) && field.getExtField() == 2) { + // 解析origin name中有关联的字段生成sql表达式 + originName = calcFieldRegex(field.getOriginName(), tableObj); + } else if (ObjectUtils.isNotEmpty(field.getExtField()) && field.getExtField() == 1) { + originName = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), field.getOriginName()); + } else { + originName = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), field.getOriginName()); + } + if (field.getDeType() == 1) { + if (field.getDeExtractType() == 0 || field.getDeExtractType() == 5) { + whereName = String.format(MySQLConstants.STR_TO_DATE, originName, StringUtils.isNotEmpty(field.getDateFormat()) ? field.getDateFormat() : MysqlConstants.DEFAULT_DATE_FORMAT); + } + if (field.getDeExtractType() == 2 || field.getDeExtractType() == 3 || field.getDeExtractType() == 4) { + String cast = String.format(MySQLConstants.CAST, originName, MySQLConstants.DEFAULT_INT_FORMAT) + "/1000"; + whereName = String.format(MySQLConstants.FROM_UNIXTIME, cast, MySQLConstants.DEFAULT_DATE_FORMAT); + } + if (field.getDeExtractType() == 1) { + whereName = originName; + } + } else if (field.getDeType() == 2 || field.getDeType() == 3) { + if (field.getDeExtractType() == 0 || field.getDeExtractType() == 5) { + whereName = String.format(MySQLConstants.CAST, originName, MySQLConstants.DEFAULT_FLOAT_FORMAT); + } + if (field.getDeExtractType() == 1) { + whereName = String.format(MySQLConstants.UNIX_TIMESTAMP, originName); + } + if (field.getDeExtractType() == 2 || field.getDeExtractType() == 3 || field.getDeExtractType() == 4) { + whereName = originName; + } + } else { + whereName = originName; + } + + if (StringUtils.equalsIgnoreCase(request.getFilterType(), "enum")) { + if (CollectionUtils.isNotEmpty(request.getEnumCheckField())) { + res.add("(" + whereName + " IN ('" + String.join("','", request.getEnumCheckField()) + "'))"); + } + } else { + List filter = request.getFilter(); + for (ChartCustomFilterItemDTO filterItemDTO : filter) { + String value = filterItemDTO.getValue(); + String whereTerm = transMysqlFilterTerm(filterItemDTO.getTerm()); + String whereValue = ""; + + if (StringUtils.equalsIgnoreCase(filterItemDTO.getTerm(), "null")) { + whereValue = ""; + } else if (StringUtils.equalsIgnoreCase(filterItemDTO.getTerm(), "not_null")) { + whereValue = ""; + } else if (StringUtils.equalsIgnoreCase(filterItemDTO.getTerm(), "empty")) { + whereValue = "''"; + } else if (StringUtils.equalsIgnoreCase(filterItemDTO.getTerm(), "not_empty")) { + whereValue = "''"; + } else if (StringUtils.containsIgnoreCase(filterItemDTO.getTerm(), "in") || StringUtils.containsIgnoreCase(filterItemDTO.getTerm(), "not in")) { + whereValue = "('" + String.join("','", value.split(",")) + "')"; + } else if (StringUtils.containsIgnoreCase(filterItemDTO.getTerm(), "like")) { + whereValue = "'%" + value + "%'"; + } else { + whereValue = String.format(MySQLConstants.WHERE_VALUE_VALUE, value); + } + list.add(SQLObj.builder() + .whereField(whereName) + .whereTermAndValue(whereTerm + whereValue) + .build()); + } + List strList = new ArrayList<>(); + list.forEach(ele -> strList.add(ele.getWhereField() + " " + ele.getWhereTermAndValue())); + if (CollectionUtils.isNotEmpty(list)) { + res.add("(" + String.join(" " + getLogic(request.getLogic()) + " ", strList) + ")"); + } + } + } + return CollectionUtils.isNotEmpty(res) ? "(" + String.join(" AND ", res) + ")" : null; + } + + public String transExtFilterList(SQLObj tableObj, List requestList) { + if (CollectionUtils.isEmpty(requestList)) { + return null; + } + List list = new ArrayList<>(); + for (ChartExtFilterRequest request : requestList) { + List value = request.getValue(); + + List whereNameList = new ArrayList<>(); + List fieldList = new ArrayList<>(); + if (request.getIsTree()) { + fieldList.addAll(request.getDatasetTableFieldList()); + } else { + fieldList.add(request.getDatasetTableField()); + } + + for (DatasetTableField field : fieldList) { + if (CollectionUtils.isEmpty(value) || ObjectUtils.isEmpty(field)) { + continue; + } + String whereName = ""; + + String originName; + if (ObjectUtils.isNotEmpty(field.getExtField()) && field.getExtField() == 2) { + // 解析origin name中有关联的字段生成sql表达式 + originName = calcFieldRegex(field.getOriginName(), tableObj); + } else if (ObjectUtils.isNotEmpty(field.getExtField()) && field.getExtField() == 1) { + originName = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), field.getOriginName()); + } else { + originName = String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), field.getOriginName()); + } + + if (field.getDeType() == 1) { + String format = transDateFormat(request.getDateStyle(), request.getDatePattern()); + if (field.getDeExtractType() == 0 || field.getDeExtractType() == 5 || field.getDeExtractType() == 1) { + if (StringUtils.equalsIgnoreCase(request.getDateStyle(), "y_Q")) { + whereName = String.format(format, + String.format(MysqlConstants.DATE_FORMAT, originName, "%Y"), + String.format(MysqlConstants.QUARTER, String.format(MysqlConstants.DATE_FORMAT, originName, MysqlConstants.DEFAULT_DATE_FORMAT))); + } else { + whereName = String.format(MySQLConstants.DATE_FORMAT, originName, format); + } + } + if (field.getDeExtractType() == 2 || field.getDeExtractType() == 3 || field.getDeExtractType() == 4) { + whereName = originName; + } + } else if (field.getDeType() == 2 || field.getDeType() == 3) { + if (field.getDeExtractType() == 0 || field.getDeExtractType() == 5) { + whereName = String.format(MySQLConstants.CAST, originName, MySQLConstants.DEFAULT_FLOAT_FORMAT); + } + if (field.getDeExtractType() == 1) { + whereName = String.format(MySQLConstants.UNIX_TIMESTAMP, originName); + } + if (field.getDeExtractType() == 2 || field.getDeExtractType() == 3 || field.getDeExtractType() == 4) { + whereName = originName; + } + } else { + whereName = originName; + } + whereNameList.add(whereName); + } + + String whereName = ""; + if (request.getIsTree()) { + whereName = "CONCAT(" + StringUtils.join(whereNameList, ",',',") + ")"; + } else { + whereName = whereNameList.get(0); + } + String whereTerm = transMysqlFilterTerm(request.getOperator()); + String whereValue = ""; + + if (StringUtils.containsIgnoreCase(request.getOperator(), "in")) { + whereValue = "('" + StringUtils.join(value, "','") + "')"; + } else if (StringUtils.containsIgnoreCase(request.getOperator(), "like")) { + whereValue = "'%" + value.get(0) + "%'"; + } else if (StringUtils.containsIgnoreCase(request.getOperator(), "between")) { + if (request.getDatasetTableField().getDeType() == 1) { + if (request.getDatasetTableField().getDeExtractType() == 2 + || request.getDatasetTableField().getDeExtractType() == 3 + || request.getDatasetTableField().getDeExtractType() == 4) { + whereValue = String.format(MysqlConstants.WHERE_BETWEEN, value.get(0), value.get(1)); + } else { + SimpleDateFormat simpleDateFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss"); + String startTime = simpleDateFormat.format(new Date(Long.parseLong(value.get(0)))); + String endTime = simpleDateFormat.format(new Date(Long.parseLong(value.get(1)))); + whereValue = String.format(MySQLConstants.WHERE_BETWEEN, startTime, endTime); + } + } else { + whereValue = String.format(MySQLConstants.WHERE_BETWEEN, value.get(0), value.get(1)); + } + } else { + whereValue = String.format(MySQLConstants.WHERE_VALUE_VALUE, value.get(0)); + } + list.add(SQLObj.builder() + .whereField(whereName) + .whereTermAndValue(whereTerm + whereValue) + .build()); + } + List strList = new ArrayList<>(); + list.forEach(ele -> strList.add(ele.getWhereField() + " " + ele.getWhereTermAndValue())); + return CollectionUtils.isNotEmpty(list) ? "(" + String.join(" AND ", strList) + ")" : null; + } + + private String sqlFix(String sql) { + sql = sql.trim(); + if (sql.lastIndexOf(";") == (sql.length() - 1)) { + sql = sql.substring(0, sql.length() - 1); + } + return sql; + } + + private String transDateFormat(String dateStyle, String datePattern) { + String split = "-"; + if (StringUtils.equalsIgnoreCase(datePattern, "date_sub")) { + split = "-"; + } else if (StringUtils.equalsIgnoreCase(datePattern, "date_split")) { + split = "/"; + } else { + split = "-"; + } + + if (StringUtils.isEmpty(dateStyle)) { + return "%Y-%m-%d %H:%i:%S"; + } + + switch (dateStyle) { + case "y": + return "%Y"; + case "y_Q": + return "CONCAT(%s,'" + split + "',%s)"; + case "y_M": + return "%Y" + split + "%m"; + case "y_W": + return "%Y" + split + "%u"; + case "y_M_d": + return "%Y" + split + "%m" + split + "%d"; + case "H_m_s": + return "%H:%i:%S"; + case "y_M_d_H_m": + return "%Y" + split + "%m" + split + "%d" + " %H:%i"; + case "y_M_d_H_m_s": + return "%Y" + split + "%m" + split + "%d" + " %H:%i:%S"; + default: + return "%Y-%m-%d %H:%i:%S"; + } + } + + private SQLObj getXFields(ChartViewFieldDTO x, String originField, String fieldAlias) { + String fieldName = ""; + if (x.getDeExtractType() == 1) { + if (x.getDeType() == 2 || x.getDeType() == 3) { + fieldName = String.format(MySQLConstants.UNIX_TIMESTAMP, originField) + "*1000"; + } else if (x.getDeType() == 1) { + String format = transDateFormat(x.getDateStyle(), x.getDatePattern()); + if (x.getType().equalsIgnoreCase("YEAR")) { + if (StringUtils.equalsIgnoreCase(x.getDateStyle(), "y_Q")) { + fieldName = String.format(format, + String.format(MySQLConstants.DATE_FORMAT, "CONCAT(" + originField + ",'-01-01')", "%Y"), + String.format(MySQLConstants.QUARTER, "CONCAT(" + originField + ",'-01-01')")); + } else { + fieldName = String.format(MySQLConstants.DATE_FORMAT, "CONCAT(" + originField + ",'-01-01')", format); + } + } else if (x.getType().equalsIgnoreCase("TIME")) { + fieldName = String.format(MySQLConstants.DATE_FORMAT, "CONCAT('1970-01-01', " + originField + ")", MySQLConstants.DEFAULT_DATE_FORMAT); + } else { + if (StringUtils.equalsIgnoreCase(x.getDateStyle(), "y_Q")) { + fieldName = String.format(format, + String.format(MySQLConstants.DATE_FORMAT, originField, "%Y"), + String.format(MySQLConstants.QUARTER, originField)); + } else { + fieldName = String.format(MySQLConstants.DATE_FORMAT, originField, format); + } + } + } else { + fieldName = originField; + } + } else { + if (x.getDeType() == 1) { + String format = transDateFormat(x.getDateStyle(), x.getDatePattern()); + if (x.getDeExtractType() == 0) { + if (StringUtils.equalsIgnoreCase(x.getDateStyle(), "y_Q")) { + fieldName = String.format(format, + String.format(MysqlConstants.DATE_FORMAT, String.format(MySQLConstants.STR_TO_DATE, originField, StringUtils.isNotEmpty(x.getDateFormat()) ? x.getDateFormat() : MysqlConstants.DEFAULT_DATE_FORMAT), "%Y"), + String.format(MysqlConstants.QUARTER, String.format(MySQLConstants.STR_TO_DATE, originField, StringUtils.isNotEmpty(x.getDateFormat()) ? x.getDateFormat() : MysqlConstants.DEFAULT_DATE_FORMAT))); + } else { + fieldName = String.format(MySQLConstants.DATE_FORMAT, String.format(MySQLConstants.STR_TO_DATE, originField, StringUtils.isNotEmpty(x.getDateFormat()) ? x.getDateFormat() : MysqlConstants.DEFAULT_DATE_FORMAT), format); + } + } else { + String cast = String.format(MySQLConstants.CAST, originField, MySQLConstants.DEFAULT_INT_FORMAT) + "/1000"; + String from_unixtime = String.format(MySQLConstants.FROM_UNIXTIME, cast, MySQLConstants.DEFAULT_DATE_FORMAT); + if (StringUtils.equalsIgnoreCase(x.getDateStyle(), "y_Q")) { + fieldName = String.format(format, + String.format(MySQLConstants.DATE_FORMAT, from_unixtime, "%Y"), + String.format(MySQLConstants.QUARTER, from_unixtime)); + } else { + fieldName = String.format(MySQLConstants.DATE_FORMAT, from_unixtime, format); + } + } + } else { + if (x.getDeType() == DeTypeConstants.DE_INT) { + fieldName = String.format(MySQLConstants.CAST, originField, MySQLConstants.DEFAULT_INT_FORMAT); + } else if (x.getDeType() == DeTypeConstants.DE_FLOAT) { + fieldName = String.format(MySQLConstants.CAST, originField, MySQLConstants.DEFAULT_FLOAT_FORMAT); + } else { + fieldName = originField; + } + } + } + return SQLObj.builder() + .fieldName(fieldName) + .fieldAlias(fieldAlias) + .build(); + } + + private List getXWheres(ChartViewFieldDTO x, String originField, String fieldAlias) { + List list = new ArrayList<>(); + if (CollectionUtils.isNotEmpty(x.getFilter()) && x.getFilter().size() > 0) { + x.getFilter().forEach(f -> { + String whereName = ""; + String whereTerm = transMysqlFilterTerm(f.getTerm()); + String whereValue = ""; + if (x.getDeType() == 1 && x.getDeExtractType() != 1) { + String cast = String.format(MySQLConstants.CAST, originField, MySQLConstants.DEFAULT_INT_FORMAT) + "/1000"; + whereName = String.format(MySQLConstants.FROM_UNIXTIME, cast, MySQLConstants.DEFAULT_DATE_FORMAT); + } else { + whereName = originField; + } + if (StringUtils.equalsIgnoreCase(f.getTerm(), "null")) { + whereValue = ""; + } else if (StringUtils.equalsIgnoreCase(f.getTerm(), "not_null")) { + whereValue = ""; + } else if (StringUtils.equalsIgnoreCase(f.getTerm(), "empty")) { + whereValue = "''"; + } else if (StringUtils.equalsIgnoreCase(f.getTerm(), "not_empty")) { + whereValue = "''"; + } else if (StringUtils.containsIgnoreCase(f.getTerm(), "in")) { + whereValue = "('" + StringUtils.join(f.getValue(), "','") + "')"; + } else if (StringUtils.containsIgnoreCase(f.getTerm(), "like")) { + whereValue = "'%" + f.getValue() + "%'"; + } else { + whereValue = String.format(MySQLConstants.WHERE_VALUE_VALUE, f.getValue()); + } + list.add(SQLObj.builder() + .whereField(whereName) + .whereAlias(fieldAlias) + .whereTermAndValue(whereTerm + whereValue) + .build()); + }); + } + return list; + } + + private SQLObj getYFields(ChartViewFieldDTO y, String originField, String fieldAlias) { + String fieldName = ""; + if (StringUtils.equalsIgnoreCase(y.getOriginName(), "*")) { + fieldName = MySQLConstants.AGG_COUNT; + } else if (SQLConstants.DIMENSION_TYPE.contains(y.getDeType())) { + if (StringUtils.equalsIgnoreCase(y.getSummary(), "count_distinct")) { + fieldName = String.format(MySQLConstants.AGG_FIELD, "COUNT", "DISTINCT " + originField); + } else if (StringUtils.equalsIgnoreCase(y.getSummary(), "group_concat")) { + fieldName = String.format(MySQLConstants.GROUP_CONCAT, originField); + } else { + fieldName = String.format(MySQLConstants.AGG_FIELD, y.getSummary(), originField); + } + } else { + if (StringUtils.equalsIgnoreCase(y.getSummary(), "avg") || StringUtils.containsIgnoreCase(y.getSummary(), "pop")) { + String cast = String.format(MySQLConstants.CAST, originField, y.getDeType() == 2 ? MySQLConstants.DEFAULT_INT_FORMAT : MySQLConstants.DEFAULT_FLOAT_FORMAT); + String agg = String.format(MySQLConstants.AGG_FIELD, y.getSummary(), cast); + fieldName = String.format(MySQLConstants.CAST, agg, MySQLConstants.DEFAULT_FLOAT_FORMAT); + } else { + String cast = String.format(MySQLConstants.CAST, originField, y.getDeType() == 2 ? MySQLConstants.DEFAULT_INT_FORMAT : MySQLConstants.DEFAULT_FLOAT_FORMAT); + if (StringUtils.equalsIgnoreCase(y.getSummary(), "count_distinct")) { + fieldName = String.format(MySQLConstants.AGG_FIELD, "COUNT", "DISTINCT " + cast); + } else { + fieldName = String.format(MySQLConstants.AGG_FIELD, y.getSummary(), cast); + } + } + } + return SQLObj.builder() + .fieldName(fieldName) + .fieldAlias(fieldAlias) + .build(); + } + + private String getYWheres(ChartViewFieldDTO y, String originField, String fieldAlias) { + List list = new ArrayList<>(); + if (CollectionUtils.isNotEmpty(y.getFilter()) && y.getFilter().size() > 0) { + y.getFilter().forEach(f -> { + String whereTerm = transMysqlFilterTerm(f.getTerm()); + String whereValue = ""; + // 原始类型不是时间,在de中被转成时间的字段做处理 + if (StringUtils.equalsIgnoreCase(f.getTerm(), "null")) { + whereValue = ""; + } else if (StringUtils.equalsIgnoreCase(f.getTerm(), "not_null")) { + whereValue = ""; + } else if (StringUtils.equalsIgnoreCase(f.getTerm(), "empty")) { + whereValue = "''"; + } else if (StringUtils.equalsIgnoreCase(f.getTerm(), "not_empty")) { + whereValue = "''"; + } else if (StringUtils.containsIgnoreCase(f.getTerm(), "in")) { + whereValue = "('" + StringUtils.join(f.getValue(), "','") + "')"; + } else if (StringUtils.containsIgnoreCase(f.getTerm(), "like")) { + whereValue = "'%" + f.getValue() + "%'"; + } else { + whereValue = String.format(MySQLConstants.WHERE_VALUE_VALUE, f.getValue()); + } + list.add(SQLObj.builder() + .whereField(fieldAlias) + .whereAlias(fieldAlias) + .whereTermAndValue(whereTerm + whereValue) + .build()); + }); + } + List strList = new ArrayList<>(); + list.forEach(ele -> strList.add(ele.getWhereField() + " " + ele.getWhereTermAndValue())); + return CollectionUtils.isNotEmpty(list) ? "(" + String.join(" " + getLogic(y.getLogic()) + " ", strList) + ")" : null; + } + + private String calcFieldRegex(String originField, SQLObj tableObj) { + originField = originField.replaceAll("[\\t\\n\\r]]", ""); + // 正则提取[xxx] + String regex = "\\[(.*?)]"; + Pattern pattern = Pattern.compile(regex); + Matcher matcher = pattern.matcher(originField); + Set ids = new HashSet<>(); + while (matcher.find()) { + String id = matcher.group(1); + ids.add(id); + } + if (CollectionUtils.isEmpty(ids)) { + return originField; + } + DatasetTableFieldExample datasetTableFieldExample = new DatasetTableFieldExample(); + datasetTableFieldExample.createCriteria().andIdIn(new ArrayList<>(ids)); + List calcFields = datasetTableFieldMapper.selectByExample(datasetTableFieldExample); + for (DatasetTableField ele : calcFields) { + originField = originField.replaceAll("\\[" + ele.getId() + "]", + String.format(MySQLConstants.KEYWORD_FIX, tableObj.getTableAlias(), ele.getOriginName())); + } + return originField; + } + + private String sqlLimit(String sql, ChartViewWithBLOBs view) { + if (StringUtils.equalsIgnoreCase(view.getResultMode(), "custom")) { + return sql + " LIMIT 0," + view.getResultCount(); + } else { + return sql; + } + } + + public String sqlForPreview(String table, Datasource ds) { + return "SELECT * FROM " + String.format(MySQLConstants.KEYWORD_TABLE, table); + } + + public List dateformat() { + return JSONArray.parseArray("[\n" + + "{\"dateformat\": \"%Y-%m-%d\"},\n" + + "{\"dateformat\": \"%Y/%m/%d\"},\n" + + "{\"dateformat\": \"%Y%m%d\"},\n" + + "{\"dateformat\": \"%Y-%m-%d %H:%i:%S\"},\n" + + "{\"dateformat\": \"%Y/%m/%d %H:%i:%S\"},\n" + + "{\"dateformat\": \"%Y%m%d %H:%i:%S\"}\n" + + "]", Dateformat.class); + } + +} diff --git a/backend/src/main/java/io/dataease/service/dataset/DataSetTableService.java b/backend/src/main/java/io/dataease/service/dataset/DataSetTableService.java index e54774e2e6..312538f866 100644 --- a/backend/src/main/java/io/dataease/service/dataset/DataSetTableService.java +++ b/backend/src/main/java/io/dataease/service/dataset/DataSetTableService.java @@ -147,7 +147,7 @@ public class DataSetTableService { public static final String regex = "\\$\\{(.*?)\\}"; private static final String SubstitutedParams = "DATAEASE_PATAMS_BI"; private static final String SubstitutedSql = " 'BI' = 'BI' "; - private static final String SubstitutedSqlVirtualData = " 1 < 2 "; + private static final String SubstitutedSqlVirtualData = " 1 > 2 "; @Value("${upload.file.path}") private String path; @@ -1272,7 +1272,7 @@ public class DataSetTableService { DatasourceRequest datasourceRequest = new DatasourceRequest(); datasourceRequest.setDatasource(ds); - sql = realData ? handleVariableDefaultValue(sql, dataSetTableRequest.getSqlVariableDetails(), ds.getType(), true) : removeVariables(sql, ds.getType()).replaceAll(SubstitutedSql, SubstitutedSqlVirtualData); + sql = realData ? handleVariableDefaultValue(sql, dataSetTableRequest.getSqlVariableDetails(), ds.getType(), true) : removeVariables(sql, ds.getType()).replaceAll(SubstitutedSql.trim(), SubstitutedSqlVirtualData); if (StringUtils.isEmpty(sql)) { DataEaseException.throwException(Translator.get("i18n_sql_not_empty")); } @@ -1942,7 +1942,7 @@ public class DataSetTableService { QueryProvider qp = ProviderFactory.getQueryProvider(ds.getType()); DataTableInfoDTO dataTableInfo = new Gson().fromJson(datasetTable.getInfo(), DataTableInfoDTO.class); String sql = dataTableInfo.isBase64Encryption() ? new String(java.util.Base64.getDecoder().decode(dataTableInfo.getSql())) : dataTableInfo.getSql(); - sql = removeVariables(sql, ds.getType()).replaceAll(SubstitutedSql, SubstitutedSqlVirtualData); + sql = removeVariables(sql, ds.getType()).replaceAll(SubstitutedSql.trim(), SubstitutedSqlVirtualData); String sqlAsTable = qp.createSQLPreview(sql, null); datasourceRequest.setQuery(sqlAsTable); fields = datasourceProvider.fetchResultField(datasourceRequest); diff --git a/backend/src/main/java/io/dataease/service/panel/PanelGroupService.java b/backend/src/main/java/io/dataease/service/panel/PanelGroupService.java index 4d54ff13cd..7f22ac1a7a 100644 --- a/backend/src/main/java/io/dataease/service/panel/PanelGroupService.java +++ b/backend/src/main/java/io/dataease/service/panel/PanelGroupService.java @@ -1161,6 +1161,8 @@ public class PanelGroupService { componentFilterInfo.setGoPage(1l); componentFilterInfo.setPageSize(1000000l); componentFilterInfo.setExcelExportFlag(true); + componentFilterInfo.setProxy(request.getProxy()); + componentFilterInfo.setUser(request.getUserId()); ChartViewDTO chartViewInfo = chartViewService.getData(request.getViewId(), componentFilterInfo); List tableRow = (List) chartViewInfo.getData().get("tableRow"); List result = new ArrayList<>(); diff --git a/backend/src/main/resources/db/migration/V53__1.18.6.sql b/backend/src/main/resources/db/migration/V53__1.18.6.sql new file mode 100644 index 0000000000..4af9e12007 --- /dev/null +++ b/backend/src/main/resources/db/migration/V53__1.18.6.sql @@ -0,0 +1,4 @@ +UPDATE `my_plugin` +SET `version` = '1.18.6' +where `plugin_id` > 0 + and `version` = '1.18.5'; diff --git a/frontend/package.json b/frontend/package.json index 9e1a52ee7c..640c9086b1 100644 --- a/frontend/package.json +++ b/frontend/package.json @@ -1,6 +1,6 @@ { "name": "dataease", - "version": "1.18.5", + "version": "1.18.6", "description": "dataease front", "private": true, "scripts": { diff --git a/frontend/src/components/canvas/utils/utils.js b/frontend/src/components/canvas/utils/utils.js index 11b0a94811..5fadb1707a 100644 --- a/frontend/src/components/canvas/utils/utils.js +++ b/frontend/src/components/canvas/utils/utils.js @@ -373,7 +373,12 @@ export function insertBatchTreeNode(nodeInfoArray, tree) { } } -export function updateCacheTree(opt, treeName, nodeInfo, tree) { +export function updateCacheTree(opt, treeName, nodeInfoFull, tree) { + const nodeInfo = { + ...nodeInfoFull, + panelData: null, + panelStyle: null + } if (opt === 'new' || opt === 'copy') { insertTreeNode(nodeInfo, tree) } else if (opt === 'move') { diff --git a/frontend/src/lang/en.js b/frontend/src/lang/en.js index ce2af3c82d..3f232302af 100644 --- a/frontend/src/lang/en.js +++ b/frontend/src/lang/en.js @@ -607,7 +607,8 @@ export default { oidc: 'OIDC Setting', theme: 'Theme Setting', cas: 'CAS Setting', - map: 'MAP Setting' + map: 'MAP Setting', + select_left: 'Please select a region on the left' }, license: { i18n_no_license_record: 'No License Record', diff --git a/frontend/src/lang/tw.js b/frontend/src/lang/tw.js index 8ea17b41ac..94e4cae86a 100644 --- a/frontend/src/lang/tw.js +++ b/frontend/src/lang/tw.js @@ -607,7 +607,8 @@ export default { oidc: 'OIDC設置', theme: '主題設置', cas: 'CAS設置', - map: '地圖設置' + map: '地圖設置', + select_left: '請在左側選擇區域' }, license: { i18n_no_license_record: '沒有 License 記錄', diff --git a/frontend/src/lang/zh.js b/frontend/src/lang/zh.js index 6cc8e19a87..b94532ecfe 100644 --- a/frontend/src/lang/zh.js +++ b/frontend/src/lang/zh.js @@ -608,7 +608,8 @@ export default { oidc: 'OIDC设置', theme: '主题设置', cas: 'CAS设置', - map: '地图设置' + map: '地图设置', + select_left: '请在左侧选择区域' }, license: { i18n_no_license_record: '没有 License 记录', diff --git a/frontend/src/views/system/sysParam/MapSetting/MapSettingRight.vue b/frontend/src/views/system/sysParam/MapSetting/MapSettingRight.vue index 7957adf60b..c41ef1b080 100644 --- a/frontend/src/views/system/sysParam/MapSetting/MapSettingRight.vue +++ b/frontend/src/views/system/sysParam/MapSetting/MapSettingRight.vue @@ -138,7 +138,7 @@ diff --git a/mobile/package.json b/mobile/package.json index 7817f9bb01..3417ce608e 100644 --- a/mobile/package.json +++ b/mobile/package.json @@ -1,6 +1,6 @@ { "name": "dataease-mobile", - "version": "1.18.5", + "version": "1.18.6", "private": true, "scripts": { "serve": "npm run dev:h5", diff --git a/pom.xml b/pom.xml index bb2355da07..1fa739fcc5 100644 --- a/pom.xml +++ b/pom.xml @@ -16,7 +16,7 @@ - 1.18.5 + 1.18.6 dataease