GetWaterPowerReadingService.java 12 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224
  1. package com.kingdee.eas.custom.dormitorysystem.service;
  2. import com.kingdee.bos.BOSException;
  3. import com.kingdee.bos.Context;
  4. import com.kingdee.bos.bsf.service.app.IHRMsfService;
  5. import com.kingdee.bos.dao.ormapping.ObjectUuidPK;
  6. import com.kingdee.bos.metadata.data.SortType;
  7. import com.kingdee.bos.metadata.entity.EntityViewInfo;
  8. import com.kingdee.bos.metadata.entity.FilterInfo;
  9. import com.kingdee.bos.metadata.entity.FilterItemInfo;
  10. import com.kingdee.bos.metadata.entity.SelectorItemCollection;
  11. import com.kingdee.bos.metadata.entity.SelectorItemInfo;
  12. import com.kingdee.bos.metadata.entity.SorterItemCollection;
  13. import com.kingdee.bos.metadata.entity.SorterItemInfo;
  14. import com.kingdee.bos.metadata.query.util.CompareType;
  15. import com.kingdee.eas.common.EASBizException;
  16. import com.kingdee.eas.custom.dormitorysystem.waterpower.IWaterPowerMeterReading;
  17. import com.kingdee.eas.custom.dormitorysystem.waterpower.WaterPowerMeterReadingCollection;
  18. import com.kingdee.eas.custom.dormitorysystem.waterpower.WaterPowerMeterReadingFactory;
  19. import com.kingdee.eas.custom.dormitorysystem.waterpower.WaterPowerMeterReadingInfo;
  20. import com.kingdee.shr.base.syssetting.exception.SHRWebException;
  21. import com.kingdee.util.NumericExceptionSubItem;
  22. import org.apache.commons.lang3.StringUtils;
  23. import org.jetbrains.annotations.NotNull;
  24. import org.slf4j.Logger;
  25. import org.slf4j.LoggerFactory;
  26. import java.time.LocalDate;
  27. import java.time.format.DateTimeFormatter;
  28. import java.time.temporal.TemporalAdjusters;
  29. import java.util.ArrayList;
  30. import java.util.List;
  31. import java.util.Map;
  32. /**
  33. * 水电表读数查询服务
  34. * coyle
  35. */
  36. public class GetWaterPowerReadingService implements IHRMsfService {
  37. private static final Logger logger = LoggerFactory.getLogger(GetWaterPowerReadingService.class);
  38. // 仅保留使用的日期格式化器
  39. private static final DateTimeFormatter DATE_FORMATTER = DateTimeFormatter.ofPattern("yyyy-MM-dd");
  40. @Override
  41. public Object process(Context ctx, Map<String, Object> param) throws EASBizException, BOSException {
  42. // 1. 基础参数校验,防止空指针
  43. if (param == null) {
  44. logger.warn("查询水电表读数时,入参param为null,返回空集合");
  45. return new WaterPowerMeterReadingCollection();
  46. }
  47. if (ctx == null) {
  48. logger.error("查询水电表读数时,上下文Context为null");
  49. throw new BOSException("上下文Context不能为空");
  50. }
  51. FilterInfo filterInfo = new FilterInfo();
  52. Object fidObj = param.get("fid");
  53. if (fidObj != null && !StringUtils.isEmpty(fidObj.toString())) {
  54. String fid = fidObj.toString().trim();
  55. fid = getString(fid);
  56. buildWaterPowerInfo(ctx, fid);
  57. }else{
  58. // 标记各过滤条件是否存在,用于动态构建maskString
  59. boolean hasDateFilter = false;
  60. boolean hasRoomFilter = false;
  61. boolean hasDataTypeFilter = false;
  62. // 存储过滤条件的逻辑片段,最后拼接成maskString
  63. List<String> filterLogicSegments = new ArrayList<>();
  64. // 2. 处理日期参数(原years参数,语义为查询月份/日期)
  65. Object dateParamObj = param.get("years");
  66. if (dateParamObj != null && !StringUtils.isEmpty(dateParamObj.toString())) {
  67. String dateParam = dateParamObj.toString().trim();
  68. dateParam = getString(dateParam);
  69. try {
  70. LocalDate startDate;
  71. LocalDate endDate;
  72. // 处理 yyyy-MM 格式(如2025-08)
  73. if (dateParam.matches("\\d{4}-\\d{2}")) {
  74. LocalDate monthDate = LocalDate.parse(dateParam + "-01", DATE_FORMATTER);
  75. startDate = monthDate.with(TemporalAdjusters.firstDayOfMonth());
  76. endDate = monthDate.with(TemporalAdjusters.firstDayOfNextMonth());
  77. }
  78. // 处理 yyyy-MM-dd 格式(如2025-08-15)
  79. else if (dateParam.matches("\\d{4}-\\d{2}-\\d{2}")) {
  80. LocalDate inputDate = LocalDate.parse(dateParam, DATE_FORMATTER);
  81. startDate = inputDate.with(TemporalAdjusters.firstDayOfMonth());
  82. endDate = inputDate.with(TemporalAdjusters.firstDayOfNextMonth());
  83. } else {
  84. logger.warn("日期参数格式不合法,值为:{},支持格式:yyyy-MM 或 yyyy-MM-dd", dateParam);
  85. return buildWaterPowerCollection(ctx, filterInfo);
  86. }
  87. // 添加日期过滤项(索引0:>=startTime,索引1:<endTime)
  88. String startTime = startDate.format(DATE_FORMATTER);
  89. String endTime = endDate.format(DATE_FORMATTER);
  90. filterInfo.getFilterItems().add(new FilterItemInfo("years", startTime, CompareType.GREATER_EQUALS));
  91. filterInfo.getFilterItems().add(new FilterItemInfo("years", endTime, CompareType.LESS));
  92. hasDateFilter = true;
  93. // 日期条件逻辑:#0 and #1
  94. filterLogicSegments.add("#0 and #1");
  95. logger.info("添加日期过滤条件:years >= {} 且 years < {}", startTime, endTime);
  96. } catch (Exception e) {
  97. logger.error("处理日期参数时发生异常,参数值:{}", dateParam, e);
  98. // 直接抛出框架规范的EASBizException,避免嵌套异常和RuntimeException
  99. throw new EASBizException(new NumericExceptionSubItem("00001","日期参数解析失败:" + e.getMessage()));
  100. }
  101. }
  102. // 3. 处理房间号参数(模糊查询number/name)
  103. Object roomNumberObj = param.get("roomNumber");
  104. if (roomNumberObj != null && !StringUtils.isEmpty(roomNumberObj.toString())) {
  105. String roomNumber = roomNumberObj.toString().trim();
  106. roomNumber = getString(roomNumber);
  107. String likePattern = "%" + roomNumber + "%";
  108. // 计算房间号过滤项的起始索引(根据前面的日期项数量)
  109. int roomFilterStartIndex = hasDateFilter ? 2 : 0;
  110. // 添加房间号过滤项
  111. filterInfo.getFilterItems().add(new FilterItemInfo("dormitory.number", likePattern, CompareType.LIKE));
  112. filterInfo.getFilterItems().add(new FilterItemInfo("dormitory.name", likePattern, CompareType.LIKE));
  113. hasRoomFilter = true;
  114. // 房间号条件逻辑:(#n or #n+1)
  115. String roomLogic = String.format("(#%d or #%d)", roomFilterStartIndex, roomFilterStartIndex + 1);
  116. filterLogicSegments.add(roomLogic);
  117. logger.info("添加房间号模糊过滤条件:dormitory.number LIKE {} 或 dormitory.name LIKE {}", likePattern, likePattern);
  118. logger.info("房间号过滤逻辑片段:{}", roomLogic);
  119. }
  120. // 4. 处理数据类型参数(筛选无水费/无电费记录)
  121. Object dataTypeObj = param.get("dataType");
  122. if (dataTypeObj != null && !StringUtils.isEmpty(dataTypeObj.toString())) {
  123. String dataType = dataTypeObj.toString().trim();
  124. // 计算数据类型过滤项的起始索引(日期2项 + 房间号2项 = 4;无前置则0/2)
  125. int dataTypeIndex = filterInfo.getFilterItems().size();
  126. String dataTypeLogic = "";
  127. if(StringUtils.equals(dataType, ShowType.UNPAPER.getValue())){
  128. // 无水费:totalWaterTons为空
  129. filterInfo.getFilterItems().add(new FilterItemInfo("totalWaterTons", null, CompareType.EMPTY));
  130. dataTypeLogic = String.format("#%d", dataTypeIndex);
  131. logger.info("添加数据类型过滤条件:无水费记录(totalWaterTons 为空)");
  132. }else if(StringUtils.equals(dataType, ShowType.UNELECTRICITY.getValue())){
  133. // 无电费:totalElecDegrees为空
  134. filterInfo.getFilterItems().add(new FilterItemInfo("totalElecDegrees", null, CompareType.EMPTY));
  135. dataTypeLogic = String.format("#%d", dataTypeIndex);
  136. logger.info("添加数据类型过滤条件:无电费记录(totalElecDegrees 为空)");
  137. }
  138. if (StringUtils.isNotBlank(dataTypeLogic)) {
  139. hasDataTypeFilter = true;
  140. filterLogicSegments.add(dataTypeLogic);
  141. }
  142. }
  143. // 5. 动态构建最终的maskString(所有条件用AND连接)
  144. if (!filterLogicSegments.isEmpty()) {
  145. String finalMaskString = String.join(" and ", filterLogicSegments);
  146. filterInfo.setMaskString(finalMaskString);
  147. logger.info("最终过滤条件组合逻辑(maskString):{}", finalMaskString);
  148. } else {
  149. logger.info("无任何过滤条件,查询全部水电表读数记录");
  150. }
  151. }
  152. // 6. 构建查询结果并返回
  153. return buildWaterPowerCollection(ctx, filterInfo);
  154. }
  155. @NotNull
  156. private static String getString(String fid) {
  157. if(fid.startsWith("'") && fid.endsWith("'")){
  158. fid = fid.substring(1, fid.length() - 1);
  159. }else if(fid.startsWith("\"") && fid.endsWith("\"")){
  160. fid = fid.substring(1, fid.length() - 1);
  161. }
  162. return fid;
  163. }
  164. /**
  165. * 构建排序条件并查询水电表读数集合
  166. * 抽离通用逻辑,提高代码复用性
  167. */
  168. private WaterPowerMeterReadingCollection buildWaterPowerCollection(Context ctx, FilterInfo filterInfo) throws BOSException {
  169. // 构建排序条件
  170. SorterItemCollection sorterItemCollection = new SorterItemCollection();
  171. SorterItemInfo yearsSorter = new SorterItemInfo("years");
  172. yearsSorter.setSortType(SortType.DESCEND);
  173. sorterItemCollection.add(yearsSorter);
  174. sorterItemCollection.add(new SorterItemInfo("dormitory.number")); // 按房间号升序
  175. SelectorItemCollection selectCol = new SelectorItemCollection();
  176. selectCol.add(new SelectorItemInfo("*"));
  177. selectCol.add(new SelectorItemInfo("dormitory.displayName"));
  178. selectCol.add(new SelectorItemInfo("dormitory.name"));
  179. // 构建视图并查询
  180. EntityViewInfo entityViewInfo = new EntityViewInfo();
  181. entityViewInfo.setFilter(filterInfo);
  182. entityViewInfo.setSorter(sorterItemCollection);
  183. entityViewInfo.setSelector(selectCol);
  184. IWaterPowerMeterReading wpIns = WaterPowerMeterReadingFactory.getLocalInstance(ctx);
  185. WaterPowerMeterReadingCollection wpCol = wpIns.getWaterPowerMeterReadingCollection(entityViewInfo);
  186. logger.info("水电表读数查询完成,共查询到 {} 条记录", wpCol.size());
  187. return wpCol;
  188. }
  189. /**
  190. * 构建排序条件并查询水电表读数集合
  191. * 抽离通用逻辑,提高代码复用性
  192. */
  193. private WaterPowerMeterReadingInfo buildWaterPowerInfo(Context ctx, String fid) throws BOSException, EASBizException {
  194. IWaterPowerMeterReading wpIns = WaterPowerMeterReadingFactory.getLocalInstance(ctx);
  195. WaterPowerMeterReadingInfo wpCol = wpIns.getWaterPowerMeterReadingInfo(new ObjectUuidPK(fid));
  196. logger.info("水电表读数查询完成,共查询到 {} 条记录", wpCol.size());
  197. return wpCol;
  198. }
  199. }