自定义报表维度

This commit is contained in:
钱涛 2023-11-06 18:46:49 +08:00
parent 83f38d1d74
commit 36a77a8e0f
7 changed files with 263 additions and 26 deletions

View File

@ -19,6 +19,10 @@
<result column="tenant_key" property="tenantKey"/>
<result column="unit_type" property="unitType"/>
<result column="update_time" property="updateTime"/>
<result column="last_rule" property="lastRule"/>
<result column="old_rule" property="oldRule"/>
<result column="frequent_rule" property="frequentRule"/>
<result column="tile_rule" property="tileRule"/>
</resultMap>
<!-- 表字段 -->
@ -42,6 +46,10 @@
, t.tenant_key
, t.unit_type
, t.update_time
, t.last_rule
, t.old_rule
, t.frequent_rule
, t.tile_rule
</sql>
<!-- 查询全部 -->
@ -184,6 +192,18 @@
<if test="updateTime != null">
update_time,
</if>
<if test="lastRule != null">
last_rule,
</if>
<if test="oldRule != null">
old_rule,
</if>
<if test="frequentRule != null">
frequent_rule,
</if>
<if test="tileRule != null">
tile_rule,
</if>
</trim>
<trim prefix="VALUES (" suffix=")" suffixOverrides=",">
<if test="avgRule != null">
@ -237,6 +257,18 @@
<if test="updateTime != null">
#{updateTime},
</if>
<if test="lastRule != null">
#{lastRule},
</if>
<if test="oldRule != null">
#{oldRule},
</if>
<if test="frequentRule != null">
#{frequentRule},
</if>
<if test="tileRule != null">
#{tileRule},
</if>
</trim>
</insert>
@ -260,6 +292,10 @@
tenant_key=#{tenantKey},
unit_type=#{unitType},
update_time=#{updateTime},
last_rule=#{lastRule},
old_rule=#{oldRule},
frequent_rule=#{frequentRule},
tile_rule=#{tileRule},
</set>
WHERE id = #{id} AND delete_type = 0
</update>
@ -317,6 +353,18 @@
<if test="updateTime != null">
update_time=#{updateTime},
</if>
<if test="lastRule != null">
last_rule=#{lastRule},
</if>
<if test="oldRule != null">
old_rule=#{oldRule},
</if>
<if test="frequentRule != null">
frequent_rule=#{frequentRule},
</if>
<if test="tileRule != null">
tile_rule=#{tileRule},
</if>
</set>
WHERE id = #{id} AND delete_type = 0
</update>

View File

@ -13,6 +13,7 @@ import com.engine.salary.report.entity.param.SalaryStatisticsReportDataQueryPara
import com.engine.salary.report.entity.po.SalaryStatisticsDimensionPO;
import com.engine.salary.report.entity.po.SalaryStatisticsItemPO;
import com.engine.salary.report.entity.po.SalaryStatisticsReportPO;
import com.engine.salary.report.enums.SalaryStatisticsItemStringRuleEnum;
import com.engine.salary.report.enums.UnitTypeEnum;
import com.engine.salary.report.util.ReportDataUtil;
import com.engine.salary.report.util.ReportTimeUtil;
@ -20,6 +21,7 @@ import com.engine.salary.util.SalaryDateUtil;
import com.engine.salary.util.SalaryEntityUtil;
import com.engine.salary.util.SalaryI18nUtil;
import com.engine.salary.util.page.PageInfo;
import com.google.common.base.Joiner;
import com.google.common.collect.Maps;
import com.google.common.collect.Sets;
import org.apache.commons.collections4.CollectionUtils;
@ -45,7 +47,6 @@ public class SalaryStatisticsReportBO {
public static final String MAX = "max";
public static final String MIN = "min";
public static final String MEDIAN = "median";
public static final String LATEST = "last";
public static final String ZERO = "0";
public static final String ONE = "1";
@ -174,7 +175,13 @@ public class SalaryStatisticsReportBO {
// 6.中位数规则数据处理
calculate4Median(result, item, nowDetail, lastDetail, sameDetail);
// 7.最近值
calculate4Latest(result, item, nowDetail, lastDetail, sameDetail);
calculate4Last(result, item, nowDetail, lastDetail, sameDetail);
// 8.最久值
calculate4Old(result, item, nowDetail, lastDetail, sameDetail);
// 9.最频繁
calculate4Frequent(result, item, nowDetail, lastDetail, sameDetail);
// 10.平铺
calculate4Tile(result, item, nowDetail, lastDetail, sameDetail);
});
return result;
}
@ -491,14 +498,14 @@ public class SalaryStatisticsReportBO {
* @param lastDetail
* @param sameDetail
*/
private static void calculate4Latest(Map<String, String> result, SalaryStatisticsItemPO item, List<Map<String, String>> nowDetail, List<Map<String, String>> lastDetail, List<Map<String, String>> sameDetail) {
SalaryStatisticsItemRuleDTO medianRule = JSON.parseObject(item.getMedianRule(), SalaryStatisticsItemRuleDTO.class);
if (medianRule == null || medianRule.getTotalValue() != 1) {
private static void calculate4Last(Map<String, String> result, SalaryStatisticsItemPO item, List<Map<String, String>> nowDetail, List<Map<String, String>> lastDetail, List<Map<String, String>> sameDetail) {
SalaryStatisticsItemRuleDTO lastRule = JSON.parseObject(item.getLastRule(), SalaryStatisticsItemRuleDTO.class);
if (lastRule == null || lastRule.getTotalValue() != 1) {
return;
}
String lastValue = "";
// 本期
if (medianRule.getTotalValue() == 1) {
if (lastRule.getTotalValue() == 1) {
List<String> decimalList = Lists.newArrayList();
if (StringUtils.isNotEmpty(item.getItemValue())) {
String[] itemValues = item.getItemValue().split(COMMA);
@ -512,7 +519,109 @@ public class SalaryStatisticsReportBO {
}
// 本期最近值
lastValue = last(decimalList);
nowAndRatio(result, item, medianRule, LATEST, lastValue);
nowAndRatio(result, item, lastRule, SalaryStatisticsItemStringRuleEnum.LAST.getValue(), lastValue);
}
}
/**
* 最旧的值
*
* @param result
* @param item
* @param nowDetail
* @param lastDetail
* @param sameDetail
*/
private static void calculate4Old(Map<String, String> result, SalaryStatisticsItemPO item, List<Map<String, String>> nowDetail, List<Map<String, String>> lastDetail, List<Map<String, String>> sameDetail) {
SalaryStatisticsItemRuleDTO oldRule = JSON.parseObject(item.getOldRule(), SalaryStatisticsItemRuleDTO.class);
if (oldRule == null || oldRule.getTotalValue() != 1) {
return;
}
String value = "";
// 本期
if (oldRule.getTotalValue() == 1) {
List<String> decimalList = Lists.newArrayList();
if (StringUtils.isNotEmpty(item.getItemValue())) {
String[] itemValues = item.getItemValue().split(COMMA);
for (String itemId : itemValues) {
for (Map<String, String> x : nowDetail) {
if (MapUtils.isNotEmpty(x) && StringUtils.isNotBlank(x.get(itemId))) {
decimalList.add(x.get(itemId));
}
}
}
}
// 本期最近值
value = old(decimalList);
nowAndRatio(result, item, oldRule, SalaryStatisticsItemStringRuleEnum.OLD.getValue(), value);
}
}
/**
* 最频繁
*
* @param result
* @param item
* @param nowDetail
* @param lastDetail
* @param sameDetail
*/
private static void calculate4Frequent(Map<String, String> result, SalaryStatisticsItemPO item, List<Map<String, String>> nowDetail, List<Map<String, String>> lastDetail, List<Map<String, String>> sameDetail) {
SalaryStatisticsItemRuleDTO frequentRule = JSON.parseObject(item.getOldRule(), SalaryStatisticsItemRuleDTO.class);
if (frequentRule == null || frequentRule.getTotalValue() != 1) {
return;
}
String value = "";
// 本期
if (frequentRule.getTotalValue() == 1) {
List<String> decimalList = Lists.newArrayList();
if (StringUtils.isNotEmpty(item.getItemValue())) {
String[] itemValues = item.getItemValue().split(COMMA);
for (String itemId : itemValues) {
for (Map<String, String> x : nowDetail) {
if (MapUtils.isNotEmpty(x) && StringUtils.isNotBlank(x.get(itemId))) {
decimalList.add(x.get(itemId));
}
}
}
}
// 本期最近值
value = frequent(decimalList);
nowAndRatio(result, item, frequentRule, SalaryStatisticsItemStringRuleEnum.FREQUENT.getValue(), value);
}
}
/**
* 平铺
*
* @param result
* @param item
* @param nowDetail
* @param lastDetail
* @param sameDetail
*/
private static void calculate4Tile(Map<String, String> result, SalaryStatisticsItemPO item, List<Map<String, String>> nowDetail, List<Map<String, String>> lastDetail, List<Map<String, String>> sameDetail) {
SalaryStatisticsItemRuleDTO tileRule = JSON.parseObject(item.getOldRule(), SalaryStatisticsItemRuleDTO.class);
if (tileRule == null || tileRule.getTotalValue() != 1) {
return;
}
String value = "";
// 本期
if (tileRule.getTotalValue() == 1) {
List<String> decimalList = Lists.newArrayList();
if (StringUtils.isNotEmpty(item.getItemValue())) {
String[] itemValues = item.getItemValue().split(COMMA);
for (String itemId : itemValues) {
for (Map<String, String> x : nowDetail) {
if (MapUtils.isNotEmpty(x) && StringUtils.isNotBlank(x.get(itemId))) {
decimalList.add(x.get(itemId));
}
}
}
}
// 本期最近值
value = tile(decimalList);
nowAndRatio(result, item, tileRule, SalaryStatisticsItemStringRuleEnum.TILE.getValue(), value);
}
}
@ -549,10 +658,6 @@ public class SalaryStatisticsReportBO {
String keyPrefix = item.getId().toString() + UD + ruleKey;
// 本期合计
result.put(keyPrefix + K_NOW, sumDecimal);
// // 占比和本期合计一样的值便于计算
// if (rule.getRatioValue() == 1) {
// result.put(keyPrefix + K_RATIO, result.get(keyPrefix + K_NOW));
// }
}
/**
@ -655,6 +760,7 @@ public class SalaryStatisticsReportBO {
/**
* 最新的值
*
* @param list
* @return
*/
@ -665,6 +771,51 @@ public class SalaryStatisticsReportBO {
return list.get(0);
}
/**
* 最旧的值
*
* @param list
* @return
*/
public static String old(List<String> list) {
if (CollectionUtils.isEmpty(list)) {
return "";
}
return list.get(list.size() - 1);
}
/**
* 最频繁
*
* @param list
* @return
*/
public static String frequent(List<String> list) {
if (CollectionUtils.isEmpty(list)) {
return "";
}
return list.stream()
.collect(Collectors.groupingBy(Function.identity(), Collectors.counting()))
.entrySet()
.stream()
.max(Map.Entry.comparingByValue())
.map(Map.Entry::getKey)
.orElse("");
}
/**
* 平铺
*
* @param list
* @return
*/
public static String tile(List<String> list) {
if (CollectionUtils.isEmpty(list)) {
return "";
}
return Joiner.on(",").join((Iterable<?>) list);
}
public static List<Map<String, String>> po2map(List<SalaryAcctEmployeePO> list, Map<Long, Map<String, String>> salaryAcctResultValueMap) {
if (CollectionUtils.isEmpty(list)) {
return new ArrayList<>();
@ -1021,6 +1172,26 @@ public class SalaryStatisticsReportBO {
children.add(new WeaTableColumnGroup(COL_WIDTH, SalaryI18nUtil.getI18nLabel(174376, "中位数同比差值"), k + UD + MEDIAN + P_Y2Y_D_VALUE));
children.add(new WeaTableColumnGroup(COL_WIDTH, SalaryI18nUtil.getI18nLabel(174377, "中位数同比增幅"), k + UD + MEDIAN + P_Y2Y_INCREASE));
}
// 7.最新值children
SalaryStatisticsItemRuleDTO lastRule = JSON.parseObject(itemPO.getLastRule(), SalaryStatisticsItemRuleDTO.class);
if (lastRule != null && 1 == lastRule.getTotalValue()) {
children.add(new WeaTableColumnGroup(COL_WIDTH, SalaryI18nUtil.getI18nLabel(174246, "最新值"), k + UD + SalaryStatisticsItemStringRuleEnum.LAST.getValue() + P_NOW));
}
// 8.最旧值children
SalaryStatisticsItemRuleDTO oldRule = JSON.parseObject(itemPO.getOldRule(), SalaryStatisticsItemRuleDTO.class);
if (oldRule != null && 1 == oldRule.getTotalValue()) {
children.add(new WeaTableColumnGroup(COL_WIDTH, SalaryI18nUtil.getI18nLabel(174246, "最旧值"), k + UD + SalaryStatisticsItemStringRuleEnum.OLD.getValue() + P_NOW));
}
// 9.最频繁children
SalaryStatisticsItemRuleDTO frequentRule = JSON.parseObject(itemPO.getFrequentRule(), SalaryStatisticsItemRuleDTO.class);
if (frequentRule != null && 1 == frequentRule.getTotalValue()) {
children.add(new WeaTableColumnGroup(COL_WIDTH, SalaryI18nUtil.getI18nLabel(174246, "频繁出现"), k + UD + SalaryStatisticsItemStringRuleEnum.FREQUENT.getValue() + P_NOW));
}
// 10.平铺children
SalaryStatisticsItemRuleDTO tileRule = JSON.parseObject(itemPO.getTileRule(), SalaryStatisticsItemRuleDTO.class);
if (tileRule != null && 1 == tileRule.getTotalValue()) {
children.add(new WeaTableColumnGroup(COL_WIDTH, SalaryI18nUtil.getI18nLabel(174246, "平铺"), k + UD + SalaryStatisticsItemStringRuleEnum.TILE.getValue() + P_NOW));
}
weaTableColumn.setChildren(children);
result.add(weaTableColumn);
});

View File

@ -14,30 +14,29 @@ import java.math.BigDecimal;
@Builder
@NoArgsConstructor
@AllArgsConstructor
//"薪酬统计报表自定义统计项目规则")
public class SalaryStatisticsItemRuleDTO {
//是否有合计列")
//是否有合计列若是文本代表是否显示
private Integer totalValue;
//是否有占比列")
//是否有占比列
private Integer ratioValue;
//是否有环比列")
//是否有环比列
private Integer m2mValue;
//合计环比上限")
//合计环比上限
private BigDecimal m2mUpperLimit;
//合计环比下限")
//合计环比下限
private BigDecimal m2mLowerLimit;
//是否有同比列")
//是否有同比列
private Integer y2yValue;
//合计同比上限")
//合计同比上限
private BigDecimal y2yUpperLimit;
//合计同比下限")
//合计同比下限
private BigDecimal y2yLowerLimit;
}

View File

@ -50,9 +50,20 @@ public class SalaryStatisticsItemSaveParam {
//中位数规则
private SalaryStatisticsItemRuleDTO medianRule;
//最近值
private SalaryStatisticsItemRuleDTO lastRule;
//最旧值
private SalaryStatisticsItemRuleDTO oldRule;
//频繁出现
private SalaryStatisticsItemRuleDTO frequentRule;
//平铺
private SalaryStatisticsItemRuleDTO tileRule;
//统计单位
private Integer unitType;
}

View File

@ -130,7 +130,7 @@ public class SalaryStatisticsItemPO implements Serializable {
/**
* 最近值
* <p>
* "able":"1", 是否使用
* "totalValue":"1", 是否使用
*/
private String lastRule;
@ -138,7 +138,7 @@ public class SalaryStatisticsItemPO implements Serializable {
* 最早值
* <p>
* {
* "able":"1", 是否使用
* "totalValue":"1", 是否使用
* }
*/
private String oldRule;
@ -147,7 +147,7 @@ public class SalaryStatisticsItemPO implements Serializable {
* 出现最多
* <p>
* {
* "able":"1", 是否使用
* "totalValue":"1", 是否使用
* }
*/
private String frequentRule;
@ -156,7 +156,7 @@ public class SalaryStatisticsItemPO implements Serializable {
* 平铺
* <p>
* {
* "able":"1", 是否使用
* "totalValue":"1", 是否使用
* }
*/
private String tileRule;

View File

@ -9,7 +9,7 @@ public enum SalaryStatisticsItemStringRuleEnum implements BaseEnum<String> {
LAST("last", "最近值", 83993),
OLD("old", "最早值", 83994),
FREQUENT("frequent", "出现最多", 83994),
FREQUENT("frequent", "最频繁", 83994),
TILE("tile", "平铺", 83994),
;

View File

@ -116,6 +116,10 @@ public class SalaryStatisticsItemServiceImpl extends Service implements SalarySt
.maxRule(SalaryEntityUtil.toJSONString(saveParam.getMaxRule()))
.minRule(SalaryEntityUtil.toJSONString(saveParam.getMinRule()))
.medianRule(SalaryEntityUtil.toJSONString(saveParam.getMedianRule()))
.lastRule(SalaryEntityUtil.toJSONString(saveParam.getMedianRule()))
.oldRule(SalaryEntityUtil.toJSONString(saveParam.getMedianRule()))
.frequentRule(SalaryEntityUtil.toJSONString(saveParam.getMedianRule()))
.tileRule(SalaryEntityUtil.toJSONString(saveParam.getMedianRule()))
.indexValue(max + 1)
.statReportId(saveParam.getStatReportId())
.unitType(saveParam.getUnitType() == null ? UnitTypeEnum.YUAN.getValue() : saveParam.getUnitType())
@ -149,6 +153,10 @@ public class SalaryStatisticsItemServiceImpl extends Service implements SalarySt
itemPO.setMaxRule(SalaryEntityUtil.toJSONString(saveParam.getMaxRule()));
itemPO.setMinRule(SalaryEntityUtil.toJSONString(saveParam.getMinRule()));
itemPO.setMedianRule(SalaryEntityUtil.toJSONString(saveParam.getMedianRule()));
itemPO.setLastRule(SalaryEntityUtil.toJSONString(saveParam.getLastRule()));
itemPO.setOldRule(SalaryEntityUtil.toJSONString(saveParam.getOldRule()));
itemPO.setFrequentRule(SalaryEntityUtil.toJSONString(saveParam.getFrequentRule()));
itemPO.setTileRule(SalaryEntityUtil.toJSONString(saveParam.getTileRule()));
}
getSalaryStatisticsItemMapper().updateIgnoreNull(itemPO);