Ejemplo n.º 1
0
 /**
  * 构建维度表
  *
  * @param cube 立方体
  * @return 维度表定义
  */
 private List<DimTableMetaDefine> buildDimTables(MiniCube cube) {
   Collection<Dimension> dimensions = cube.getDimensions().values();
   if (dimensions == null || dimensions.size() == 0) {
     return new ArrayList<DimTableMetaDefine>();
   }
   Map<String, DimTableMetaDefine> dimTableCache = new HashMap<String, DimTableMetaDefine>();
   List<DimTableMetaDefine> rs = new ArrayList<DimTableMetaDefine>();
   String factTableName = cube.getSource();
   for (Dimension dimension : dimensions) {
     if (dimension.getLevels().size() > 1) { // 组合维度 不处理
       continue;
     }
     String dimTableName = dimension.getTableName();
     if (dimTableName == null || dimTableName.equals(factTableName)) {
       continue;
     }
     // 同一个维度表中的列,只需要加入维度表中就可以了
     if (dimTableCache.containsKey(dimension.getTableName())) {
       DimTableMetaDefine dimTable = dimTableCache.get(dimension.getTableName());
       ColumnMetaDefine column = buildColumn(this.getLevel(dimension));
       dimTable.addColumn(column);
     } else { // 构建新的维度表,并加入当前列
       DimTableMetaDefine dimTable = getDimTableDefineWithLevelType(cube.getSource(), dimension);
       ColumnMetaDefine column = buildColumn(this.getLevel(dimension));
       dimTable.addColumn(column);
       dimTableCache.put(dimension.getTableName(), dimTable);
     }
   }
   rs.addAll(dimTableCache.values());
   return rs;
 }
Ejemplo n.º 2
0
 /**
  * trans cube
  *
  * @param cube
  * @return new Cube
  */
 public static Cube transformCube(Cube cube) {
   MiniCube newCube = (MiniCube) DeepcopyUtils.deepCopy(cube);
   final Map<String, Measure> measures = Maps.newConcurrentMap();
   cube.getMeasures()
       .values()
       .forEach(
           m -> {
             measures.put(m.getName(), m);
           });
   newCube.setMeasures(measures);
   final Map<String, Dimension> dimensions = Maps.newLinkedHashMap();
   cube.getDimensions()
       .values()
       .forEach(
           dim -> {
             MiniCubeDimension tmp = (MiniCubeDimension) DeepcopyUtils.deepCopy(dim);
             LinkedHashMap<String, Level> tmpLevel = Maps.newLinkedHashMap();
             dim.getLevels()
                 .values()
                 .forEach(
                     level -> {
                       level.setDimension(dim);
                       tmpLevel.put(level.getName(), level);
                     });
             tmp.setLevels(tmpLevel);
             dimensions.put(tmp.getName(), tmp);
           });
   newCube.setDimensions(dimensions);
   return newCube;
 }
Ejemplo n.º 3
0
 /**
  * 构建星型模型
  *
  * @param cube 立方体定义
  * @return star mode 定义
  */
 public StarModel buildModel(MiniCube cube) {
   StarModel model = new StarModel();
   model.setCubeId(cube.getId());
   logger.info("current cube is : [{}]", cube);
   logger.info("current cube's schema is : [{}]", cube.getSchema());
   // 确认schema不为空
   if (cube.getSchema() != null) {
     model.setDsId(cube.getSchema().getDatasource());
     model.setSchemaId(cube.getSchema().getId());
   }
   model.setFactTable(buildFactTable(cube));
   model.setDimTables(buildDimTables(cube));
   return model;
 }
Ejemplo n.º 4
0
 /**
  * 构建事实表
  *
  * @param cube cube定义
  * @return 事实表定义
  */
 private FactTableMetaDefine buildFactTable(MiniCube cube) {
   FactTableMetaDefine factTable = new FactTableMetaDefine();
   factTable.setCubeId(cube.getId());
   factTable.setMutilple(cube.isMutilple());
   if (factTable.isMutilple()) {
     // 分库分表导致多张表组成事实表
     factTable.setRegExp(cube.getSource());
     if (cube.getSource() != null) {
       List<String> regexTables = Lists.newArrayList();
       Collections.addAll(regexTables, cube.getSource().split(","));
       factTable.setRegExpTables(regexTables);
       if (regexTables != null && regexTables.size() > 0) {
         factTable.setName(regexTables.get(0));
       }
     }
     factTable.setDivideTableStrategyVo(cube.getDivideTableStrategyVo());
   } else {
     // 事实表名称
     factTable.setName(cube.getSource());
   }
   if (cube.getMeasures() == null || cube.getMeasures().isEmpty()) {
     logger.debug("measure is empty");
   } else {
     Collection<Measure> measures = cube.getMeasures().values();
     if (measures == null) {
       logger.debug("can't get measuers");
       return factTable;
     }
     measures.forEach(
         m -> {
           ColumnMetaDefine column = new ColumnMetaDefine();
           column.setCaption(m.getCaption());
           column.setName(m.getDefine());
           factTable.addColumn(column);
         });
     // 添加维度引用的列
     cube.getDimensions()
         .values()
         .forEach(
             dim -> {
               ColumnMetaDefine column = new ColumnMetaDefine();
               // modify by jiangyichao at 2014-10-09 修改维度caption
               column.setCaption(dim.getFacttableCaption());
               column.setName(dim.getFacttableColumn());
               factTable.addColumn(column);
             });
   }
   return factTable;
 }
Ejemplo n.º 5
0
  /**
   * 获取扩展区域包含的立方体定义
   *
   * @param reportModel 报表模型
   * @param area 扩展区域
   * @return 立方体定义
   * @throws QueryModelBuildException
   */
  public static Cube getCubeWithExtendArea(ReportDesignModel reportModel, ExtendArea area)
      throws QueryModelBuildException {
    Cube oriCube = getCubeFromReportModel(reportModel, area);
    // 对于可选指标,默认将事实表包含的所有列作为查询条件
    if ("true".equals(area.getOtherSetting().get(Constants.CAN_CHANGED_MEASURE))) {
      Cube rs = transformCube(oriCube);
      modifyMeasures(rs.getMeasures(), rs);
      return rs;
    }
    Map<String, List<Dimension>> filterDims = collectFilterDim(reportModel);
    MiniCube cube = new MiniCube(area.getCubeId());
    String areaId = area.getId();
    LogicModel logicModel = area.getLogicModel();
    if (area.getType() == ExtendAreaType.SELECTION_AREA
        || area.getType() == ExtendAreaType.LITEOLAP_CHART
        || area.getType() == ExtendAreaType.LITEOLAP_TABLE) {
      LiteOlapExtendArea liteOlapArea =
          (LiteOlapExtendArea) reportModel.getExtendById(area.getReferenceAreaId());
      logicModel = liteOlapArea.getLogicModel();
      areaId = area.getReferenceAreaId();
    }
    if (logicModel == null) {
      throw new QueryModelBuildException("logic model is empty");
    }
    Item[] items = logicModel.getItems(area.getType() != ExtendAreaType.TABLE);
    Map<String, Dimension> dimensions = new HashMap<String, Dimension>();
    Map<String, Measure> measures = new HashMap<String, Measure>();

    for (Item item : items) {
      OlapElement olapElement = oriCube.getDimensions().get(item.getOlapElementId());
      if (olapElement == null) { // 维度不存在或者可能是指标信息
        olapElement = oriCube.getMeasures().get(item.getOlapElementId());
        if (olapElement != null) {
          Measure measure = (Measure) olapElement;
          measures.put(measure.getName(), measure);
        }
      } else {
        MiniCubeDimension dim = (MiniCubeDimension) DeepcopyUtils.deepCopy(olapElement);
        dim.setLevels(Maps.newLinkedHashMap());
        ;
        ((Dimension) olapElement)
            .getLevels()
            .values()
            .forEach(
                level -> {
                  level.setDimension(dim);
                  dim.getLevels().put(level.getName(), level);
                });
        dimensions.put(dim.getName(), dim);
      }
    }
    if (area.getType() == ExtendAreaType.LITEOLAP) {
      /** TODO 把liteOlap中候选的维度和指标加入到items里面 */
      Map<String, Item> candDims = ((LiteOlapExtendArea) area).getCandDims();
      Schema schema = reportModel.getSchema();
      String cubeId = area.getCubeId();
      for (String elementId : candDims.keySet()) {
        OlapElement element =
            ReportDesignModelUtils.getDimOrIndDefineWithId(schema, cubeId, elementId);
        MiniCubeDimension dim = (MiniCubeDimension) DeepcopyUtils.deepCopy(element);
        dim.setLevels(Maps.newLinkedHashMap());
        ((Dimension) element)
            .getLevels()
            .values()
            .forEach(
                level -> {
                  level.setDimension(dim);
                  dim.getLevels().put(level.getName(), level);
                });
        dimensions.put(element.getName(), (Dimension) element);
      }
      Map<String, Item> candInds = ((LiteOlapExtendArea) area).getCandInds();
      for (String elementId : candInds.keySet()) {
        OlapElement element =
            ReportDesignModelUtils.getDimOrIndDefineWithId(schema, cubeId, elementId);
        if (element instanceof CallbackMeasure) {
          CallbackMeasure m = DeepcopyUtils.deepCopy((CallbackMeasure) element);
          String url = ((CallbackMeasure) element).getCallbackUrl();
          m.setCallbackUrl(HttpUrlUtils.getBaseUrl(url));
          m.setCallbackParams(HttpUrlUtils.getParams(url));
          measures.put(m.getName(), m);
        } else {
          measures.put(element.getName(), (Measure) element);
        }
      }
    }
    if (filterDims != null) {
      List<Dimension> dims = filterDims.get(area.getCubeId());
      if (dims != null) {
        for (Dimension dim : dims) {
          if (dim != null) {
            dimensions.put(dim.getName(), dim);
          }
        }
      }

      // TODO 处理不同cube共用同一查询条件情况
      filterDims.forEach(
          (key, dimArray) -> {
            if (key != null && !key.equals(area.getCubeId())) {
              dimArray
                  .stream()
                  .filter(
                      dim -> {
                        return dim instanceof TimeDimension;
                      })
                  .forEach(
                      dim -> {
                        for (Dimension tmp : oriCube.getDimensions().values()) {
                          if (dim.getName().equals(tmp.getName())) {
                            MiniCubeDimension tmpDim =
                                (MiniCubeDimension) DeepcopyUtils.deepCopy(dim);
                            tmpDim.setLevels((LinkedHashMap<String, Level>) tmp.getLevels());
                            tmpDim.setFacttableColumn(tmp.getFacttableColumn());
                            tmpDim.setFacttableCaption(tmp.getFacttableCaption());
                            dimensions.put(tmpDim.getName(), tmpDim);
                          }
                        }
                      });
            }
          });
    }
    cube.setDimensions(dimensions);
    modifyMeasures(measures, oriCube);
    cube.setMeasures(measures);
    cube.setSource(((MiniCube) oriCube).getSource());
    cube.setPrimaryKey(((MiniCube) oriCube).getPrimaryKey());
    cube.setId(oriCube.getId() + "_" + areaId);
    return cube;
  }
Ejemplo n.º 6
0
  /**
   * 将查询动作转化成问题模型
   *
   * @param dsDefine
   * @param queryAction 查询动作
   * @return 问题模型
   * @throws QueryModelBuildException 构建失败异常
   */
  public static QuestionModel convert2QuestionModel(
      DataSourceDefine dsDefine,
      ReportDesignModel reportModel,
      QueryAction queryAction,
      Map<String, Object> requestParams,
      PageInfo pageInfo,
      String securityKey)
      throws QueryModelBuildException {
    if (queryAction == null) {
      throw new QueryModelBuildException("query action is null");
    }
    ConfigQuestionModel questionModel = new ConfigQuestionModel();
    String areaId = queryAction.getExtendAreaId();
    if (StringUtils.isEmpty(areaId)) {
      throw new QueryModelBuildException("area id is empty");
    }
    ExtendArea area = reportModel.getExtendById(areaId);
    if (area == null) {
      throw new QueryModelBuildException("can not get area with id : " + areaId);
    }
    Cube cube = getCubeFromReportModel(reportModel, area);
    if (cube == null) {
      throw new QueryModelBuildException("can not get cube define in area : " + areaId);
    }
    if (area.getType() == ExtendAreaType.PLANE_TABLE) {
      cube = transformCube(cube);
      MiniCube miniCube = (MiniCube) cube;
      DivideTableStrategyVo divideVo = miniCube.getDivideTableStrategyVo();
      DivideTableContext divideContext = new DivideTableContext();
      DivideTableService divideTableService = null;
      if (divideVo != null) {
        switch (divideVo.getCondition()) {
          case "yyyyMMdd":
            divideTableService = new DayDivideTableStrategyServiceImpl();
            break;
          case "yyyyMM":
            divideTableService = new MonthDivideTableStrategyServiceImpl();
            break;
          case "yyyy":
            divideTableService = new YearDivideTableStrategyServiceImpl();
            break;
          default:
            throw new UnsupportedOperationException("暂时不支持该分表策略");
        }
        divideContext.setDivideTableService(divideTableService);
        if (divideContext.getAllFactTableName(divideVo, requestParams) != null) {
          miniCube.setSource(divideContext.getAllFactTableName(divideVo, requestParams));
        }
        MiniCubeSchema schema = (MiniCubeSchema) reportModel.getSchema();
        schema.getCubes().put(miniCube.getId(), miniCube);
        reportModel.setSchema(schema);
      }
      miniCube.setProductLine(dsDefine.getProductLine());
      questionModel.setCube(miniCube);
    } else {
      cube = getCubeWithExtendArea(reportModel, area);
      ((MiniCube) cube).setProductLine(dsDefine.getProductLine());
      questionModel.setCube(cube);
    }
    // 设置轴信息
    questionModel.setAxisMetas(buildAxisMeta(reportModel.getSchema(), area, queryAction));

    questionModel.setCubeId(area.getCubeId());
    // TODO 动态更新cube 针对查询过程中动态添加的属性 需要仔细考虑此处逻辑
    Set<Item> tmp = Sets.newHashSet();
    tmp.addAll(queryAction.getSlices().keySet());
    tmp.addAll(queryAction.getRows().keySet());
    try {
      DataSourceInfo dataSource =
          DataSourceConnectionServiceFactory.getDataSourceConnectionServiceInstance(
                  dsDefine.getDataSourceType().name())
              .parseToDataSourceInfo(dsDefine, securityKey);
      questionModel.setDataSourceInfo(dataSource);
    } catch (Exception e) {
      throw new RuntimeException(e);
    }
    OrderDesc orderDesc = queryAction.getOrderDesc();
    if (orderDesc != null) {
      SortType sortType = SortType.valueOf(orderDesc.getOrderType());
      String uniqueName = "";
      if (DataModelUtils.isMeasure(orderDesc.getName(), cube)) {
        uniqueName = uniqueName + "[Measure].";
      } else {
        uniqueName = uniqueName + "[Dimension].";
      }
      uniqueName = uniqueName + "[" + orderDesc.getName() + "]";
      SortRecord sortRecord = new SortRecord(sortType, uniqueName, orderDesc.getRecordSize());
      questionModel.setSortRecord(sortRecord);
    }
    // TODO 此处没有考虑指标、维度交叉情况,如后续有指标维度交叉情况,此处需要调整
    questionModel.getQueryConditionLimit().setWarningAtOverFlow(false);
    if (queryAction.isNeedOthers()) {
      // TODO 需要开发通用工具包 将常量定义到通用工具包中
      questionModel.getRequestParams().put("NEED_OTHERS", "1");
    }
    // 设置请求参数信息
    if (requestParams != null) {
      for (String key : requestParams.keySet()) {
        Object value = requestParams.get(key);
        if (value != null && value instanceof String) {
          questionModel.getRequestParams().put(key, (String) value);
        }
      }
      // 设计器中, 设置分页信息
      if (requestParams.get(Constants.IN_EDITOR) != null
          && Boolean.valueOf(requestParams.get(Constants.IN_EDITOR).toString())) {
        questionModel.setPageInfo(pageInfo);
      }
    }
    if (area.getType() == ExtendAreaType.PLANE_TABLE) {
      questionModel.setQuerySource("SQL");
      // 对于平面表不使用汇总方式
      questionModel.setNeedSummary(false);
      // 设置分页信息
      questionModel.setPageInfo(pageInfo);
      // 针对平面表构建查询条件
      Map<String, MetaCondition> conditionsForPlaneTable =
          QueryConditionUtils.buildQueryConditionsForPlaneTable(reportModel, area, queryAction);
      questionModel.setQueryConditions(conditionsForPlaneTable);
    } else {
      questionModel.setQuerySource("TESSERACT");
      // 针对其他情况构建查询条件
      Map<String, MetaCondition> conditionsForPivotTable =
          QueryConditionUtils.buildQueryConditionsForPivotTable(reportModel, area, queryAction);
      questionModel.setQueryConditions(conditionsForPivotTable);
      if (queryAction.getDrillDimValues() == null
          || !queryAction.getDrillDimValues().isEmpty()
          || queryAction.isChartQuery()) {
        questionModel.setNeedSummary(false);
      } else {
        ExtendAreaType areaType =
            reportModel.getExtendById(queryAction.getExtendAreaId()).getType();
        if (areaType != ExtendAreaType.TABLE) {
          questionModel.setNeedSummary(false);
        } else {
          questionModel.setNeedSummary(needSummary(questionModel));
        }
      }

      if (questionModel.isNeedSummary()
          && "false".equals(area.getOtherSetting().get("needSummary"))) {
        questionModel.setNeedSummary(false);
      }
    }
    questionModel.setUseIndex(true);

    putSliceConditionIntoParams(queryAction, questionModel);
    questionModel.setFilterBlank(queryAction.isFilterBlank());
    return questionModel;
  }