AllocationServiceImpl.java 56 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008
  1. package com.kcim.service.impl;
  2. import cn.hutool.core.collection.CollUtil;
  3. import cn.hutool.core.date.DateTime;
  4. import cn.hutool.core.date.DateUtil;
  5. import cn.hutool.core.util.StrUtil;
  6. import cn.hutool.poi.excel.ExcelWriter;
  7. import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
  8. import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
  9. import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
  10. import com.kcim.common.constants.NumberConstant;
  11. import com.kcim.common.exception.CostException;
  12. import com.kcim.common.util.BeanUtil;
  13. import com.kcim.common.util.JacksonUtil;
  14. import com.kcim.common.util.PageUtils;
  15. import com.kcim.common.util.UserContext;
  16. import com.kcim.dao.mapper.AllocationMapper;
  17. import com.kcim.dao.model.*;
  18. import com.kcim.dao.model.dto.StartDTO;
  19. import com.kcim.dao.repository.ResponsibilityRepository;
  20. import com.kcim.service.*;
  21. import com.kcim.vo.*;
  22. import lombok.extern.slf4j.Slf4j;
  23. import org.apache.poi.ss.usermodel.Sheet;
  24. import org.springframework.stereotype.Service;
  25. import org.springframework.transaction.annotation.Propagation;
  26. import org.springframework.transaction.annotation.Transactional;
  27. import org.springframework.util.CollectionUtils;
  28. import java.math.BigDecimal;
  29. import java.math.RoundingMode;
  30. import java.util.*;
  31. import java.util.concurrent.atomic.AtomicReference;
  32. import java.util.stream.Collectors;
  33. @Slf4j
  34. @Service("allocationService")
  35. public class AllocationServiceImpl extends ServiceImpl<AllocationMapper, Allocation> implements AllocationService {
  36. // @Value("${file.serverPath}")
  37. // private String fileTempPath;
  38. //
  39. // @Value("${file.serverUrl}")
  40. // private String FILE_PATH;
  41. private final CostCostingGroupService costCostingGroupService;
  42. private final CostShareLevelService shareLevelService;
  43. private final ResponsibilityService responsibilityService;
  44. private final CostAccountShareService accountShareService;
  45. private final ShareParamValueService shareParamValueService;
  46. private final CostShareParamService shareParamService;
  47. private final AllocationQueryService allocationQueryService;
  48. private final ResponsibilityRepository responsibilityRepository;
  49. private final CenterService centerService;
  50. public AllocationServiceImpl(CostCostingGroupService costCostingGroupService,
  51. CostShareLevelService shareLevelService,
  52. ResponsibilityService responsibilityService,
  53. CostAccountShareService accountShareService,
  54. ShareParamValueService shareParamValueService, CostShareParamService shareParamService, AllocationQueryService allocationQueryService, AllocationQueryService allocationQueryService1, ResponsibilityRepository responsibilityRepository, CenterService centerService) {
  55. this.costCostingGroupService = costCostingGroupService;
  56. this.shareLevelService = shareLevelService;
  57. this.responsibilityService = responsibilityService;
  58. this.accountShareService = accountShareService;
  59. this.shareParamValueService = shareParamValueService;
  60. this.shareParamService = shareParamService;
  61. this.allocationQueryService = allocationQueryService1;
  62. this.responsibilityRepository = responsibilityRepository;
  63. this.centerService = centerService;
  64. }
  65. /**
  66. * 分摊成本数据
  67. *
  68. * @param startDTO {@link StartDTO}
  69. * @param hospId 医院id
  70. */
  71. @Override
  72. @Transactional(rollbackFor = Throwable.class, propagation = Propagation.REQUIRED)
  73. public void startAllocation(StartDTO startDTO, Long hospId) {
  74. long timeMillis = System.currentTimeMillis();
  75. // 得到这个月的所有导入的成本数据
  76. List<CostCostingGroup> costingGroups = costCostingGroupService.getByYearAndDate(startDTO.getYear(), startDTO.getMonth(), hospId);
  77. // 没有重新导入
  78. if (costingGroups.isEmpty()) {
  79. throw new CostException("本月分摊数据未导入");
  80. }
  81. // 导入数据按责任中心归类
  82. Map<String, List<CostCostingGroup>> responsibilityCodeMap = costingGroups.stream().collect(Collectors.groupingBy(CostCostingGroup::getResponsibilityCode));
  83. // 得到这个月导入的成本分摊参数值列表
  84. List<ShareParamValue> shareParamValues = shareParamValueService.getListByYearAndMonth(startDTO.getYear(), startDTO.getMonth(), hospId);
  85. if (shareParamValues.isEmpty()) {
  86. throw new CostException("本月成本分摊参数值未导入");
  87. }
  88. Map<String, List<ShareParamValue>> paramValueRespCodeMap = shareParamValues.stream().collect(Collectors.groupingBy(ShareParamValue::getResponsibilityCode));
  89. // 删除该年月已经分摊过的数据
  90. removeData(startDTO, hospId);
  91. // 得到这个医院所有的分摊层级列表排序
  92. List<CostShareLevelVO> shareLevelVOs = shareLevelService.getAll(hospId);
  93. if (CollUtil.isEmpty(shareLevelVOs)) {
  94. throw new CostException("请先设置医院分摊层级");
  95. }
  96. //优化循环调用 责任中心 分摊层级对应
  97. //成本分摊字典
  98. List<CostShareParamVO> costShareParamList = shareParamService.getAll(hospId);
  99. if (CollUtil.isEmpty(costShareParamList)) {
  100. throw new CostException("请先设置分摊参数字典");
  101. }
  102. Map<String,String> ShareParamNameMap = costShareParamList.stream().collect(Collectors.toMap(CostShareParamVO::getShareParamCode, CostShareParamVO::getShareParamName, (a, b) -> b));
  103. //责任中心
  104. List<Responsibility> responsibilityList = responsibilityRepository.getList(hospId);
  105. if (CollUtil.isEmpty(responsibilityList)) {
  106. throw new CostException("请先设置责任中心");
  107. }
  108. //按shareId分组
  109. Map<Long, List<Responsibility>> responsibilityShareIdMap = responsibilityList.stream().collect(Collectors.groupingBy(Responsibility::getShareId));
  110. Map<String,String> responsibilityNameMap = responsibilityList.stream().collect(Collectors.toMap(Responsibility::getResponsibilityCode, Responsibility::getResponsibilityName, (a, b) -> b));
  111. Map<String,Long> responsibilityShareIdDictMap = responsibilityList.stream().collect(Collectors.toMap(Responsibility::getResponsibilityCode, Responsibility::getShareId, (a, b) -> b));
  112. //分摊参数对应
  113. List<CostAccountShare> accountShareList = accountShareService.getAll();
  114. if (CollUtil.isEmpty(accountShareList)) {
  115. throw new CostException("请先设置责任中心分摊参数对应");
  116. }
  117. Map<String, List<CostAccountShare>> accountShareResponsibilityMap = accountShareList.stream().collect(Collectors.groupingBy(CostAccountShare::getResponsibilityCode));
  118. List<Allocation> allocations = new LinkedList<>();
  119. // key 责任中心代码, value 分摊过来的钱
  120. // Map<String, BigDecimal> costMap = new ConcurrentReaderHashMap();
  121. List<Allocation> costList = new ArrayList<>();
  122. for (CostShareLevelVO shareLevelVO : shareLevelVOs) {
  123. // 分摊层级id
  124. Long levelId = shareLevelVO.getId();
  125. // 目标分摊层级,可能不存在
  126. String targetLevel = shareLevelVO.getTargetLevel();
  127. if (StrUtil.isBlank(targetLevel)) {
  128. throw new CostException("未设置目标层级");
  129. }
  130. // 计算方式 0是合并计算 1是分开计算
  131. Integer calcType = shareLevelVO.getCalcType();
  132. // 得到该分摊层级下责任中心列表,如果不存在,下一个
  133. List<Responsibility> responsibilities = responsibilityShareIdMap.get(levelId);
  134. // List<Responsibility> responsibilities = responsibilityService.getLevelIdByCode(levelId, hospId);
  135. // if (responsibilities.isEmpty()) {
  136. // continue;
  137. // }
  138. if(CollectionUtils.isEmpty(responsibilities)){
  139. continue;
  140. }
  141. // 优化
  142. // 遍历责任中心得到对应的分摊参数对应
  143. for (Responsibility responsibility : responsibilities) {
  144. // String responsibilityCode = responsibility.getResponsibilityCode();
  145. // 得到分摊参数对应记录,不存在,下一个
  146. List<CostAccountShare> accountShares = accountShareResponsibilityMap.get(responsibility.getResponsibilityCode());
  147. // List<CostAccountShare> accountShares = accountShareService.getByResponsibility(responsibilityCode, hospId);
  148. if (CollectionUtils.isEmpty(accountShares)) {
  149. continue;
  150. }
  151. // 遍历分摊参数对应记录
  152. for (CostAccountShare accountShare : accountShares) {
  153. Long accountShareId = accountShare.getId();
  154. String paramList = accountShare.getParamList();
  155. // 如果分摊比例未设置直接报错
  156. if (StrUtil.isBlank(paramList)) {
  157. throw new CostException("责任中心:" + accountShare.getResponsibilityName() + ";会计科目为:" + accountShare.getAccountingNames() + ";未设置分摊参数比例");
  158. }
  159. List<AccountShareVO> accountShareVOs = JacksonUtil.str2ObjList(paramList, List.class, AccountShareVO.class);
  160. // List<CostCostingGroup> groups = responsibilityCodeMap.get(responsibilityCode);
  161. // if (CollUtil.isEmpty(groups)) {
  162. // continue;
  163. // }
  164. // 计算本次分摊的钱
  165. BigDecimal totalAmount = this.getCostAmount(accountShare, calcType, responsibilityCodeMap, costList);
  166. if (totalAmount.equals(BigDecimal.ZERO)) {
  167. continue;
  168. }
  169. // 相关的分摊参数比例
  170. if (!CollectionUtils.isEmpty(accountShareVOs)) {
  171. for (AccountShareVO accountShareVO : accountShareVOs) {
  172. // String paramCode = accountShareVO.getShareParamCode();
  173. String shareParamPopout = accountShareVO.getShareParamPopout();
  174. BigDecimal bigDecimal = new BigDecimal(shareParamPopout);
  175. BigDecimal rate = bigDecimal.divide(new BigDecimal(100), 4, RoundingMode.HALF_UP);
  176. // BigDecimal rate = new BigDecimal("1");
  177. // if (!"100".equals(shareParamPopout)) {
  178. // rate = new BigDecimal("0." + shareParamPopout);
  179. // }
  180. // 本次的分摊比例计算
  181. BigDecimal thisAmount = rate.multiply(totalAmount);
  182. // 得到目标层级责任中心列表
  183. List<Responsibility> targetResponsibilities = this.getTargetResponsibility(targetLevel, hospId, shareLevelVO.getLeverSort());
  184. if (targetResponsibilities.isEmpty()) {
  185. throw new CostException("找不到目标责任中心");
  186. }
  187. // 目标责任中心得到对应
  188. List<ShareParamValue> targetShareParamValue = getTarget(targetResponsibilities, accountShareVO, paramValueRespCodeMap);
  189. if (CollUtil.isEmpty(targetShareParamValue)) {
  190. throw new CostException("找不到目标责任中心对应的分摊参数【"+accountShareVO.getShareParamCode()+"】值");
  191. }
  192. // 分母
  193. BigDecimal reduce = targetShareParamValue.stream().map(ShareParamValue::getValueNum).reduce(BigDecimal.ZERO, BigDecimal::add);
  194. for (ShareParamValue paramValue : targetShareParamValue) {
  195. // 分子
  196. BigDecimal numerator = paramValue.getValueNum();
  197. BigDecimal targetAmount = reduce.compareTo(BigDecimal.ZERO) == 0 ? BigDecimal.ZERO : thisAmount.multiply(numerator).divide(reduce, RoundingMode.HALF_UP);
  198. BigDecimal percent = reduce.compareTo(BigDecimal.ZERO) == 0 ? BigDecimal.ZERO : numerator.divide(reduce, RoundingMode.HALF_UP);
  199. Allocation targetAllocation = new Allocation();
  200. String valueResponsibilityCode = paramValue.getResponsibilityCode();
  201. //优化循环调用
  202. String targetRespName = responsibilityNameMap.get(valueResponsibilityCode);
  203. // String targetRespName = responsibilityService.getByCode(valueResponsibilityCode, hospId);
  204. Long targetShareLevelId = responsibilityShareIdDictMap.get(valueResponsibilityCode);
  205. // Long targetShareLevelId = responsibilityService.getLevelIdByCode(valueResponsibilityCode, hospId);
  206. if (Objects.isNull(targetShareLevelId)) {
  207. throw new CostException("目标责任中心分摊层级异常");
  208. }
  209. String shareParamName = ShareParamNameMap.get(paramValue.getShareParamCode());
  210. // String shareParamName = shareParamService.getByCode(paramValue.getShareParamCode(), hospId);
  211. targetAllocation.setDateMonth(startDTO.getMonth()).setDateYear(startDTO.getYear()).setLevelSort(shareLevelVO.getLeverSort())
  212. .setLevelName(shareLevelVO.getShareName()).setHospId(hospId).setResponsibilityCode(responsibility.getResponsibilityCode())
  213. .setResponsibilityName(responsibility.getResponsibilityName()).setAccountShareId(accountShareId).setAmount(targetAmount)
  214. .setCreateTime(timeMillis).setTargetResponsibilityCode(valueResponsibilityCode).setTargetResponsibilityName(targetRespName)
  215. .setShareParamCode(paramValue.getShareParamCode()).setShareParamName(shareParamName).setTotalAmount(totalAmount).setShareParamValueNum(paramValue.getValueNum())
  216. .setShareParamRate(percent).setShareLevelId(levelId).setTargetShareLevelId(targetShareLevelId);
  217. // todo 目标分摊层级责任中心 就是当前列个表中的责任中心
  218. allocations.add(targetAllocation);
  219. costList.add(targetAllocation);
  220. }
  221. }
  222. }
  223. }
  224. }
  225. }
  226. this.saveBatch(allocations);
  227. List<Allocation> list = this.list(
  228. new LambdaQueryWrapper<Allocation>()
  229. .eq(Allocation::getHospId, hospId).eq(Allocation::getDateYear, startDTO.getYear()).eq(Allocation::getDateMonth, startDTO.getMonth())
  230. );
  231. if (list.isEmpty()) {
  232. log.error("未分摊到数据......");
  233. return;
  234. }
  235. // 入cost_allocation_query 表 便于后续操作
  236. this.saveAllocationQuery(list, hospId, startDTO.getYear(), startDTO.getMonth(),shareLevelVOs,accountShareList);
  237. }
  238. private void removeData(StartDTO startDTO, Long hospId) {
  239. this.remove(
  240. new LambdaQueryWrapper<Allocation>()
  241. .eq(Allocation::getDateYear, startDTO.getYear())
  242. .eq(Allocation::getDateMonth, startDTO.getMonth())
  243. .eq(Allocation::getHospId, hospId)
  244. );
  245. allocationQueryService.remove(
  246. new LambdaQueryWrapper<AllocationQuery>()
  247. .eq(AllocationQuery::getDateYear, startDTO.getYear())
  248. .eq(AllocationQuery::getDateMonth, startDTO.getMonth())
  249. .eq(AllocationQuery::getHospId, hospId)
  250. );
  251. }
  252. @Transactional(propagation = Propagation.REQUIRED, rollbackFor = Throwable.class)
  253. public void saveAllocationQuery(List<Allocation> list, Long hospId,
  254. Integer year, Integer month, List<CostShareLevelVO> shareLevelVOs, List<CostAccountShare> accountShareList) {
  255. List<AllocationQuery> saveList = new ArrayList<>();
  256. List<Long> maxId = shareLevelService.getMaxId(hospId);
  257. // List<Allocation> maxList = list.stream().filter(i -> maxId.contains(i.getTargetShareLevelId())).collect(Collectors.toList());
  258. Map<Long, List<Allocation>> collect = list.stream().collect(Collectors.groupingBy(Allocation::getTargetShareLevelId));
  259. //优化 去除循环调用
  260. // List<CostAccountShare> all = accountShareService.getAll();
  261. Map<Long,CostAccountShare> accountShareMap = accountShareList.stream().collect(Collectors.toMap(CostAccountShare::getId, costAccountShare -> costAccountShare, (a, b) -> b));
  262. // 得到这个月的所有导入的成本数据用责任中心关联取得shareId 优化 去除循环调用
  263. List<CostCostingGroup> costingGroups = costCostingGroupService.getRealData(CollUtil.newArrayList(), hospId, year, month);
  264. Map<Long, List<CostCostingGroup>> costShareIdGroup = costingGroups.stream().collect(Collectors.groupingBy(CostCostingGroup::getShareId));
  265. for (CostShareLevelVO shareLevelVO : shareLevelVOs) {
  266. List<Allocation> allocations = collect.get(shareLevelVO.getId());
  267. if(!CollectionUtils.isEmpty(allocations)){
  268. setAfterAllocation(allocations, hospId, saveList,accountShareMap);
  269. }
  270. if(!CollectionUtils.isEmpty(costShareIdGroup.get(shareLevelVO.getId()))){
  271. setPreAllocation(hospId,saveList,shareLevelVO,costShareIdGroup.get(shareLevelVO.getId()));
  272. }
  273. }
  274. allocationQueryService.saveBatch(saveList);
  275. }
  276. private void setPreAllocation(Long hospId, List<AllocationQuery> saveList,
  277. CostShareLevelVO shareLevelVO, List<CostCostingGroup> costingGroups) {
  278. // List<CostCostingGroup> costingGroups = costCostingGroupService.getRealData(CollUtil.newArrayList(maxId), hospId, year, month);
  279. costingGroups.forEach(i -> {
  280. AllocationQuery allocationQuery = new AllocationQuery();
  281. allocationQuery.setDateYear(i.getDateYear()).setDateMonth(i.getDateMonth())
  282. .setHospId(hospId).setResponsibilityCode(i.getResponsibilityCode()).setResponsibilityName(i.getResponsibilityName())
  283. .setOriginId(i.getId()).setOriginType(1L).setAmount(i.getAmount())
  284. .setAccountingCode(i.getAccountCode()).setAccountingName(i.getAccountName())
  285. .setCreateTime(System.currentTimeMillis())
  286. .setLevelSort(shareLevelVO.getLeverSort()).setLevelName(shareLevelVO.getShareName())
  287. .setTargetResponsibilityCode(i.getResponsibilityCode())
  288. .setTargetResponsibilityName(i.getResponsibilityName())
  289. .setShareLevelId(0L);
  290. saveList.add(allocationQuery);
  291. });
  292. }
  293. private void setAfterAllocation(List<Allocation> list, Long hospId, List<AllocationQuery> saveList, Map<Long,
  294. CostAccountShare> accountShareMap) {
  295. list.forEach(i -> {
  296. Long accountShareId = i.getAccountShareId();
  297. CostAccountShare byId = accountShareMap.get(accountShareId);
  298. if (Objects.isNull(byId)) {
  299. return;
  300. }
  301. String accountingCodes = byId.getAccountingCodes();
  302. if (StrUtil.isBlank(accountingCodes)) {
  303. return;
  304. }
  305. String accountingNames = byId.getAccountingNames();
  306. String alias = byId.getAlias();
  307. if (StrUtil.isNotBlank(alias)) {
  308. accountingNames = alias;
  309. }
  310. AllocationQuery allocationQuery = new AllocationQuery();
  311. allocationQuery.setDateYear(i.getDateYear()).setDateMonth(i.getDateMonth())
  312. .setHospId(hospId).setResponsibilityCode(i.getResponsibilityCode())
  313. .setResponsibilityName(i.getResponsibilityName())
  314. .setOriginId(i.getId()).setOriginType(2L).setAmount(i.getAmount())
  315. .setAccountingCode(accountingCodes).setAccountingName(accountingNames)
  316. .setCreateTime(System.currentTimeMillis())
  317. .setLevelSort(i.getLevelSort()).setLevelName(i.getLevelName())
  318. .setTargetResponsibilityCode(i.getTargetResponsibilityCode())
  319. .setTargetResponsibilityName(i.getTargetResponsibilityName())
  320. .setShareLevelId(i.getShareLevelId());
  321. saveList.add(allocationQuery);
  322. });
  323. }
  324. /**
  325. * 得到目标月成本分摊参数值数据
  326. *
  327. * @param targetResponsibilities
  328. * @param map
  329. * @return
  330. */
  331. private List<ShareParamValue> getTarget(List<Responsibility> targetResponsibilities, AccountShareVO accountShareVO, Map<String, List<ShareParamValue>> map) {
  332. // 目标的责任中心
  333. List<ShareParamValue> shareParamValues = map.entrySet().stream().map(Map.Entry::getValue).flatMap(Collection::stream).collect(Collectors.toList());
  334. List<String> originRespCodes = targetResponsibilities.stream().map(Responsibility::getResponsibilityCode).collect(Collectors.toList());
  335. return shareParamValues.stream().filter(j -> originRespCodes.contains(j.getResponsibilityCode()))
  336. .filter(i -> i.getShareParamCode().equals(accountShareVO.getShareParamCode())).collect(Collectors.toList());
  337. }
  338. /**
  339. * 计算本次的成本金额
  340. *
  341. * @return
  342. */
  343. private BigDecimal getCostAmount(CostAccountShare accountShare, Integer calcType, Map<String, List<CostCostingGroup>> map, List<Allocation> costList) {
  344. // 是否包含分摊成本 0不包含 1 包含
  345. Integer isShareCost = accountShare.getIsShareCost();
  346. String accountingCodes = accountShare.getAccountingCodes();
  347. String responsibilityCode = accountShare.getResponsibilityCode();
  348. List<CostCostingGroup> costingGroups = map.get(responsibilityCode);
  349. if (CollUtil.isEmpty(costingGroups)) {
  350. List<Allocation> all = costList.stream().filter(i -> i.getTargetResponsibilityCode().equals(responsibilityCode)).collect(Collectors.toList());
  351. if (CollUtil.isEmpty(all) || isShareCost == 0) {
  352. return BigDecimal.ZERO;
  353. }
  354. BigDecimal reduce = all.stream().map(Allocation::getAmount).reduce(BigDecimal.ZERO, BigDecimal::add);
  355. return reduce;
  356. } else {
  357. BigDecimal costAmount = BigDecimal.ZERO;
  358. List<Allocation> all = new ArrayList<>();
  359. if (!costList.isEmpty()) {
  360. all = costList.stream().filter(i -> i.getTargetResponsibilityCode().equals(responsibilityCode)).collect(Collectors.toList());
  361. }
  362. // 计算方式 0是合并计算 1是分开计算
  363. if (calcType == 0) {
  364. costAmount = costingGroups.stream().map(CostCostingGroup::getAmount).reduce(BigDecimal.ZERO, BigDecimal::add);
  365. if (!all.isEmpty()) {
  366. BigDecimal bigDecimal = all.stream()
  367. .map(Allocation::getAmount)
  368. .reduce(BigDecimal.ZERO, BigDecimal::add);
  369. if (Objects.nonNull(bigDecimal)) {
  370. costAmount = costAmount.add(bigDecimal);
  371. }
  372. }
  373. } else {
  374. if (StrUtil.isBlank(accountingCodes)) {
  375. return BigDecimal.ZERO;
  376. }
  377. ArrayList<String> accountCodes = CollUtil.newArrayList(accountingCodes.split(StrUtil.COMMA));
  378. List<CostCostingGroup> costGroups = costingGroups.stream().filter(i -> accountCodes.contains(i.getAccountCode())).collect(Collectors.toList());
  379. costAmount = costGroups.stream().map(CostCostingGroup::getAmount).reduce(BigDecimal.ZERO, BigDecimal::add);
  380. if (isShareCost == 1) {
  381. if (!all.isEmpty()) {
  382. BigDecimal bigDecimal = all.stream()
  383. .map(Allocation::getAmount)
  384. .reduce(BigDecimal.ZERO, BigDecimal::add);
  385. if (Objects.nonNull(bigDecimal)) {
  386. costAmount = costAmount.add(bigDecimal);
  387. }
  388. }
  389. }
  390. }
  391. return costAmount;
  392. }
  393. }
  394. /**
  395. * 通过目标层级获取目标责任中心
  396. *
  397. * @param targetLevel 目标层级 2,3,4
  398. * @param leverSort
  399. * @return List
  400. */
  401. private List<Responsibility> getTargetResponsibility(String targetLevel, Long hospId, Integer leverSort) {
  402. ArrayList<String> targetLevelList = CollUtil.newArrayList(StrUtil.split(targetLevel, StrUtil.COMMA));
  403. if (targetLevelList.size() == 1) {
  404. if (leverSort.equals(Integer.parseInt(targetLevelList.get(0)))) {
  405. return new ArrayList<>();
  406. }
  407. }
  408. List<CostShareLevel> shareLevels = shareLevelService.getListByLevelSort(targetLevelList, hospId);
  409. if (shareLevels.isEmpty()) {
  410. throw new CostException("请重新设置分摊层级");
  411. }
  412. List<Long> shareLevelIds = shareLevels.stream().map(CostShareLevel::getId).collect(Collectors.toList());
  413. return responsibilityService.getByLevelIds(shareLevelIds, hospId);
  414. }
  415. /**
  416. * 分摊后查询列表
  417. *
  418. * @param year 年月 (yyyy-MM-dd)
  419. * @param responsibilityCode 责任中心代码
  420. * @param current 当前页
  421. * @param pageSize 当前页展示的数据大小
  422. * @param hospId 医院id
  423. * @return PageUtils
  424. */
  425. @Override
  426. public PageUtils queryAfterAllocation(String year, String responsibilityCode, Integer current, Integer pageSize, Long hospId) {
  427. Integer dateYear = null;
  428. Integer dateMonth = null;
  429. if (StrUtil.isNotBlank(year)) {
  430. DateTime dateTime = DateUtil.parseDate(year);
  431. dateYear = DateUtil.year(dateTime);
  432. dateMonth = DateUtil.month(dateTime) + 1;
  433. }
  434. Integer startIndex = (current - 1) * pageSize;
  435. List<AfterAllocationVO> list = baseMapper.queryAfterAllocationList(dateYear, dateMonth, responsibilityCode, startIndex, pageSize, hospId);
  436. int totalCount = baseMapper.queryAfterAllocationListCount(dateYear, dateMonth, responsibilityCode, hospId);
  437. BigDecimal sum = baseMapper.queryAfterAllocationListSum(dateYear, dateMonth, responsibilityCode, hospId);
  438. return new PageUtils(list, totalCount, pageSize, current, sum);
  439. }
  440. /**
  441. * 分摊报表导出
  442. *
  443. * @param writer {@link ExcelWriter}
  444. * @param levelSort 分摊层级 就是第几次分摊
  445. * @param sheet 报表
  446. * @param year 年
  447. * @param month 月
  448. * @param shareLevelId
  449. * @return
  450. */
  451. @Override
  452. public ExcelWriter getShareReportTemplate(ExcelWriter writer, Integer levelSort, Sheet sheet, Integer year, Integer month, Long shareLevelId) {
  453. // 获取数据
  454. Map<String,List<String>> targetTotalMoneys = new HashMap<>();
  455. List<AllocationReportVO> allocationReportVOList = getAllocationReportVOS(levelSort, year, month, shareLevelId,targetTotalMoneys);
  456. // 设置导出
  457. Map<String, List<AllocationReportVO>> responsibilityMap = allocationReportVOList.stream().collect(Collectors.groupingBy(AllocationReportVO::getResponsibilityCode));
  458. Map<String, List<AllocationReportVO>> targetResponsibilityMap = allocationReportVOList.stream().collect(Collectors.groupingBy(AllocationReportVO::getTargetResponsibilityCode));
  459. // 以会计科目查
  460. Map<String, AllocationReportVO> allAccMap = allocationReportVOList.stream().collect(Collectors.toMap(k -> k.getResponsibilityName() + k.getAccountName() + k.getTargetResponsibilityName() + k.getShareParamName(), synOne -> synOne));
  461. // 用别名查 过滤别名不为空的
  462. Map<String, AllocationReportVO> allAliMap = allocationReportVOList.stream().filter(i -> StrUtil.isNotBlank(i.getAlias())).collect(Collectors.toMap(k -> k.getResponsibilityName() + k.getAlias() + k.getTargetResponsibilityName() + k.getShareParamName(), synOne -> synOne));
  463. // Map<String, AllocationReportVO> allAliMap = allocationReportVOList.stream().collect(Collectors.toMap(k -> k.getResponsibilityName() + k.getAlias() + k.getTargetResponsibilityName() + k.getShareParamName(), synOne -> synOne));
  464. // 当前责任中心下面有几个会计科目 后面进行合并使用
  465. final int[] numResponsibility = new int[1];
  466. levelSort=levelSort+1;
  467. // // 从第几列开始编写数据
  468. final int[] column = {levelSort + 3};
  469. responsibilityMap.forEach((key,value)->{
  470. Map<String, AllocationReportVO> linkedHashMap = new LinkedHashMap<>();
  471. value.forEach(i -> {
  472. String s = i.getResponsibilityCode() + i.getAccountCode();
  473. if (!linkedHashMap.containsKey(s)) {
  474. linkedHashMap.put(s, i);
  475. }
  476. });
  477. numResponsibility[0] = linkedHashMap.size();
  478. if (numResponsibility[0] >= NumberConstant.TWO) {
  479. Set<String> strings = linkedHashMap.keySet();
  480. for (String s : strings) {
  481. AllocationReportVO allocationReportVO = linkedHashMap.get(s);
  482. if (StrUtil.isBlank(allocationReportVO.getAlias())) {
  483. writer.writeCellValue(column[0], 0, allocationReportVO.getResponsibilityName());
  484. // 别名不存在
  485. writer.writeCellValue(column[0], 1, allocationReportVO.getAccountName());
  486. } else {
  487. // 不为空 设置别名
  488. writer.writeCellValue(column[0], 0, allocationReportVO.getResponsibilityName());
  489. writer.writeCellValue(column[0], 1, allocationReportVO.getAlias());
  490. }
  491. writer.writeCellValue(column[0], 2, allocationReportVO.getTotalAmounts());
  492. column[0]++;
  493. }
  494. } else {
  495. // 不需要合并单元格
  496. writer.writeCellValue(column[0], 0, value.get(0).getResponsibilityName());
  497. if (StrUtil.isNotBlank(value.get(0).getAlias())) {
  498. writer.writeCellValue(column[0], 1, value.get(0).getAlias());
  499. } else {
  500. writer.writeCellValue(column[0], 1, value.get(0).getAccountName());
  501. }
  502. writer.writeCellValue(column[0], 2, value.get(0).getTotalAmounts());
  503. column[0]++;
  504. }
  505. });
  506. // for (String key : keySet) {
  507. // List<AllocationReportVO> allocationReportVOS = responsibilityMap.get(key);
  508. // Map<String, AllocationReportVO> linkedHashMap = new LinkedHashMap<>();
  509. // allocationReportVOS.forEach(i -> {
  510. // String s = i.getResponsibilityCode() + i.getAccountCode();
  511. // if (!linkedHashMap.containsKey(s)) {
  512. // linkedHashMap.put(s, i);
  513. // }
  514. // });
  515. // numResponsibility[0] = linkedHashMap.size();
  516. // if (numResponsibility[0] >= NumberConstant.TWO) {
  517. // Set<String> strings = linkedHashMap.keySet();
  518. // for (String s : strings) {
  519. // AllocationReportVO allocationReportVO = linkedHashMap.get(s);
  520. // if (StrUtil.isBlank(allocationReportVO.getAlias())) {
  521. // writer.writeCellValue(column[0], 0, allocationReportVO.getResponsibilityName());
  522. // // 别名不存在
  523. // writer.writeCellValue(column[0], 1, allocationReportVO.getAccountName());
  524. // } else {
  525. // // 不为空 设置别名
  526. // writer.writeCellValue(column[0], 0, allocationReportVO.getResponsibilityName());
  527. // writer.writeCellValue(column[0], 1, allocationReportVO.getAlias());
  528. // }
  529. // writer.writeCellValue(column[0], 2, allocationReportVO.getTotalAmounts());
  530. // column[0]++;
  531. // }
  532. // } else {
  533. // // 不需要合并单元格
  534. // writer.writeCellValue(column[0], 0, allocationReportVOS.get(0).getResponsibilityName());
  535. // if (StrUtil.isNotBlank(allocationReportVOS.get(0).getAlias())) {
  536. // writer.writeCellValue(column[0], 1, allocationReportVOS.get(0).getAlias());
  537. // } else {
  538. // writer.writeCellValue(column[0], 1, allocationReportVOS.get(0).getAccountName());
  539. // }
  540. // writer.writeCellValue(column[0], 2, allocationReportVOS.get(0).getTotalAmounts());
  541. // column[0]++;
  542. // }
  543. // }
  544. // 设置单元格合并
  545. for (int j = 1; j < levelSort; j++) {
  546. writer.merge(0, 1, j, j, "第" + j + "次分摊", false);
  547. }
  548. // 目标责任集合
  549. writer.passCurrentRow();
  550. // 从第三行开始
  551. int num = 3;
  552. Set<String> targetSet = targetResponsibilityMap.keySet();
  553. int t = 0;
  554. for (String target : targetSet) {
  555. List<AllocationReportVO> allocationReportVOS = targetResponsibilityMap.get(target);
  556. Map<String, AllocationReportVO> linkedHashMap = new LinkedHashMap<>();
  557. allocationReportVOS.forEach(i -> {
  558. String s = i.getTargetResponsibilityCode() + i.getShareParamName();
  559. if (!linkedHashMap.containsKey(s)) {
  560. linkedHashMap.put(s, i);
  561. }
  562. });
  563. int shareParamSize = linkedHashMap.size();
  564. if (shareParamSize >= NumberConstant.TWO) {
  565. // 责任中心
  566. AllocationReportVO costCostingVO = allocationReportVOS.get(0);
  567. // 设置第几次分摊的值
  568. List<String> targetShareMoneyList = targetTotalMoneys.get(target);
  569. // for (int k = 0; k < levelSort - 1; k++) {
  570. // writer.merge(num, num + shareParamSize - 1, k + 1, k + 1, costCostingVO.getTargetShareMoneys().get(t++), false);
  571. //
  572. // }
  573. for (int k = 0; k < levelSort - 1; k++) {
  574. Object allocationAmount = getAllocationAmount(levelSort, k, allocationReportVOS, targetShareMoneyList);
  575. writer.merge(num, num + shareParamSize - 1, k + 1, k + 1, allocationAmount, false);
  576. }
  577. // if(!CollectionUtils.isEmpty(targetShareMoneyList)){
  578. // for (int k = 0; k < levelSort - 1; k++) {
  579. // if(k==levelSort-2){
  580. // BigDecimal totalAmount = allocationReportVOS.stream().map(AllocationReportVO::getAmount)
  581. // .reduce(BigDecimal.ZERO, BigDecimal::add);
  582. // writer.merge(num, num + shareParamSize - 1, k + 1, k + 1, totalAmount, false);
  583. // }else {
  584. // writer.merge(num, num + shareParamSize - 1, k + 1, k + 1, targetShareMoneyList.get(k), false);
  585. // }
  586. // }
  587. // }else {
  588. // for (int k = 0; k < levelSort - 1; k++) {
  589. // if(k==levelSort-2){
  590. // BigDecimal totalAmount = allocationReportVOS.stream().map(AllocationReportVO::getAmount)
  591. // .reduce(BigDecimal.ZERO, BigDecimal::add);
  592. // writer.merge(num, num + shareParamSize - 1, k + 1, k + 1, totalAmount, false);
  593. // }else {
  594. // writer.merge(num, num + shareParamSize - 1, k + 1, k + 1, "0.0000", false);
  595. // }
  596. // }
  597. // }
  598. // 设置对应的分摊参数值
  599. Set<String> strings = linkedHashMap.keySet();
  600. for (String s : strings) {
  601. AllocationReportVO allocationReportVO = linkedHashMap.get(s);
  602. writer.writeCellValue(0, num, allocationReportVO.getTargetResponsibilityName());
  603. writer.writeCellValue(levelSort, num, allocationReportVO.getShareParamName());
  604. writer.writeCellValue(levelSort + 1, num, allocationReportVO.getShareParamValueNums());
  605. writer.writeCellValue(levelSort + 2, num, allocationReportVO.getShareParamRates());
  606. for (int m = levelSort + 3; m < column[0]; m++) {
  607. // x是m y是num
  608. // 获取当前这一列对应的责任中心 以及会计科目
  609. // 第一行责任中心
  610. String responsibilityName = sheet.getRow(0).getCell(m).getStringCellValue();
  611. // 第二行的会计科目或者
  612. String accountNameOrAlias = sheet.getRow(1).getCell(m).getStringCellValue();
  613. // 这一行的目标责任中心
  614. String otherResponsibilityName = sheet.getRow(num).getCell(0).getStringCellValue();
  615. // 分摊参数
  616. String shareName = sheet.getRow(num).getCell(levelSort).getStringCellValue();
  617. String sss = responsibilityName + accountNameOrAlias + otherResponsibilityName + shareName;
  618. AllocationReportVO vo = allAliMap.get(sss);
  619. AllocationReportVO allocationReportVO2 = allAccMap.get(responsibilityName + accountNameOrAlias + otherResponsibilityName + shareName);
  620. AllocationReportVO allocationReportVO3 = allAliMap.get(responsibilityName + accountNameOrAlias + otherResponsibilityName + shareName);
  621. if (Objects.nonNull(allocationReportVO2)) {
  622. writer.writeCellValue(m, num, allocationReportVO2.getAmounts());
  623. } else if (Objects.nonNull(allocationReportVO3)) {
  624. writer.writeCellValue(m, num, allocationReportVO3.getAmounts());
  625. } else {
  626. writer.writeCellValue(m, num, 0);
  627. }
  628. }
  629. num++;
  630. }
  631. }
  632. if (shareParamSize < NumberConstant.TWO) {
  633. writer.writeCellValue(0, num, allocationReportVOS.get(0).getTargetResponsibilityName());
  634. // for (int k = 0; k < levelSort - 1; k++) {
  635. // writer.writeCellValue(k + 1, num, allocationReportVOS.get(0).getTargetShareMoneys().get(k));
  636. // }
  637. List<String> targetShareMoneyList = targetTotalMoneys.get(target);
  638. for (int k = 0; k < levelSort - 1; k++) {
  639. Object allocationAmount = getAllocationAmount(levelSort, k, allocationReportVOS, targetShareMoneyList);
  640. writer.writeCellValue(k + 1, num, allocationAmount);
  641. }
  642. // if(!CollectionUtils.isEmpty(targetShareMoneyList)){
  643. // for (int k = 0; k < levelSort - 1; k++) {
  644. // if(k==levelSort-2){
  645. // BigDecimal totalAmount = allocationReportVOS.stream().map(AllocationReportVO::getAmount)
  646. // .reduce(BigDecimal.ZERO, BigDecimal::add);
  647. // writer.writeCellValue(k + 1, num, totalAmount);
  648. // }else {
  649. // writer.writeCellValue(k + 1, num, targetShareMoneyList.get(k));
  650. // }
  651. // }
  652. // }else {
  653. // for (int k = 0; k < levelSort - 1; k++) {
  654. // if(k==levelSort-2){
  655. // BigDecimal totalAmount = allocationReportVOS.stream().map(AllocationReportVO::getAmount)
  656. // .reduce(BigDecimal.ZERO, BigDecimal::add);
  657. // writer.writeCellValue(k + 1, num, totalAmount);
  658. // }else {
  659. // writer.writeCellValue(k + 1, num, "0.0000");
  660. // }
  661. // }
  662. // }
  663. writer.writeCellValue(levelSort, num, allocationReportVOS.get(0).getShareParamName());
  664. writer.writeCellValue(levelSort + 1, num, allocationReportVOS.get(0).getShareParamValueNums());
  665. writer.writeCellValue(levelSort + 2, num, allocationReportVOS.get(0).getShareParamRates());
  666. for (int m = levelSort + 3; m < column[0]; m++) {
  667. // x是m y是num
  668. // 获取当前这一列对应的责任中心 以及会计科目
  669. // 第一行责任中心
  670. String responsibilityName = sheet.getRow(0).getCell(m).getStringCellValue();
  671. // 第二行的会计科目或者
  672. String accountNameOrAlias = sheet.getRow(1).getCell(m).getStringCellValue();
  673. // 这一行的目标责任中心
  674. String otherResponsibilityName = sheet.getRow(num).getCell(0).getStringCellValue();
  675. // 分摊参数
  676. String shareName = sheet.getRow(num).getCell(levelSort).getStringCellValue();
  677. AllocationReportVO allocationReportVO2 = allAccMap.get(responsibilityName + accountNameOrAlias + otherResponsibilityName + shareName);
  678. AllocationReportVO allocationReportVO3 = allAliMap.get(responsibilityName + accountNameOrAlias + otherResponsibilityName + shareName);
  679. if (Objects.nonNull(allocationReportVO2)) {
  680. writer.writeCellValue(m, num, allocationReportVO2.getAmounts());
  681. } else if (Objects.nonNull(allocationReportVO3)) {
  682. writer.writeCellValue(m, num, allocationReportVO3.getAmounts());
  683. } else {
  684. writer.writeCellValue(m, num, 0);
  685. }
  686. }
  687. num++;
  688. }
  689. }
  690. Map<String, Integer> rowMap = new HashMap<>();
  691. int cc = levelSort + 3;
  692. // 合并行
  693. boolean otherData = false;
  694. for (int m = levelSort + 3; m < column[0] - 1; m++) {
  695. // String cellValue = sheet.getRow(0).getCell(m).getStringCellValue();
  696. // if (!rowMap.containsKey(cellValue)){
  697. // rowMap.put(cellValue,m);
  698. // Integer integer = rowMap.get(sheet.getRow(0).getCell(m).getStringCellValue());
  699. // String value = sheet.getRow(0).getCell(m ).getStringCellValue();
  700. // writer.merge(0, 0, rowMap.get(sheet.getRow(0).getCell(m-1).getStringCellValue()), m-1, sheet.getRow(0).getCell(m-1).getStringCellValue(), false);
  701. // }
  702. String cellValue1 = sheet.getRow(0).getCell(m).getStringCellValue();
  703. String cellValue2 = sheet.getRow(0).getCell(m + 1).getStringCellValue();
  704. if (!cellValue1.equals(cellValue2)) {
  705. if (cc != m) {
  706. writer.merge(0, 0, cc, m, cellValue1, false);
  707. } else {
  708. writer.writeCellValue(cc, 0, cellValue1);
  709. }
  710. cc = m + 1;
  711. } else if (m == column[0] - 2) {
  712. writer.merge(0, 0, cc, m + 1, sheet.getRow(0).getCell(m + 1).getStringCellValue(), false);
  713. }
  714. }
  715. // 合并列
  716. int jj = 3;
  717. for (int i = 3; i < num - 1; i++) {
  718. String cellValue1 = sheet.getRow(i).getCell(0).getStringCellValue();
  719. String cellValue2 = sheet.getRow(i + 1).getCell(0).getStringCellValue();
  720. if (!cellValue1.equals(cellValue2)) {
  721. if (jj != i) {
  722. writer.merge(jj, i, 0, 0, cellValue1, false);
  723. } else {
  724. writer.writeCellValue(0, jj, cellValue1);
  725. }
  726. jj = i + 1;
  727. } else if (i == num - 2) {
  728. writer.merge(jj, i + 1, 0, 0, cellValue1, false);
  729. }
  730. }
  731. for (int i = 0; i < 30; i++) {
  732. // 调整每一列宽度
  733. sheet.autoSizeColumn((short) i);
  734. // 解决自动设置列宽中文失效的问题
  735. sheet.setColumnWidth(i, sheet.getColumnWidth(i) * 14 / 10);
  736. }
  737. return writer;
  738. }
  739. /**
  740. * 获取责任中心对应层级的分摊金额
  741. * @param levelSort
  742. * @param index
  743. * @param allocationReportVOS
  744. * @param targetShareMoneyList
  745. * @return
  746. */
  747. public Object getAllocationAmount(int levelSort,int index,List<AllocationReportVO> allocationReportVOS,List<String> targetShareMoneyList){
  748. //当前层级取分摊金额加总
  749. if(index==levelSort-2){
  750. BigDecimal totalAmount = allocationReportVOS.stream().map(AllocationReportVO::getAmount)
  751. .reduce(BigDecimal.ZERO, BigDecimal::add);
  752. return totalAmount;
  753. }
  754. //取不到对应层级的分摊总金额
  755. if(CollectionUtils.isEmpty(targetShareMoneyList)||targetShareMoneyList.size()<=index){
  756. return BigDecimal.valueOf(NumberConstant.ZERO,NumberConstant.FOUR);
  757. }
  758. //取对应层级的分摊总金额
  759. return targetShareMoneyList.get(index);
  760. }
  761. /**
  762. * 查询数据
  763. *
  764. * @param levelSort
  765. * @param year
  766. * @param month
  767. * @param targetTotalMoneys
  768. * @return
  769. */
  770. private List<AllocationReportVO> getAllocationReportVOS(Integer levelSort, Integer year, Integer month, Long shareLevelId,
  771. Map<String, List<String>> targetTotalMoneys) {
  772. Long hospId = UserContext.getCurrentLoginHospId();
  773. if (Objects.isNull(levelSort) || Objects.isNull(year) || Objects.isNull(month)) {
  774. throw new CostException(500, "参数异常");
  775. }
  776. // 处理第几次分摊计算值
  777. List<Allocation> allocationList = baseMapper.selectList(new QueryWrapper<Allocation>().lambda()
  778. .eq(Allocation::getHospId, hospId).eq(Allocation::getLevelSort, levelSort).eq(Allocation::getShareLevelId, shareLevelId).eq(Allocation::getDateYear, year)
  779. .eq(Allocation::getDateMonth, month));
  780. // 找会计科室的时候使用的
  781. List<Allocation> allocations = baseMapper.selectList(new QueryWrapper<Allocation>().lambda()
  782. .eq(Allocation::getHospId, hospId).eq(Allocation::getDateYear, year)
  783. .eq(Allocation::getDateMonth, month));
  784. Map<String, List<Allocation>> accrepMap = allocations.stream().collect(Collectors.groupingBy(k -> k.getLevelSort() + "cost" + k.getTargetResponsibilityCode()));
  785. LinkedList<String> shareMoney = new LinkedList<>();
  786. List<CostAccountShare> costAccountShareList = accountShareService.list(new QueryWrapper<CostAccountShare>().lambda()
  787. .eq(CostAccountShare::getHospId, hospId));
  788. Map<Long, CostAccountShare> accountShareMap = costAccountShareList.stream().collect(Collectors.toMap(CostAccountShare::getId, synOne -> synOne));
  789. List<AllocationReportVO> allocationReportVOList = BeanUtil.convertList(allocationList, AllocationReportVO.class);
  790. List<CostShareParamVO> shareParamVOList = shareParamService.getAll(hospId);
  791. Map<String,Integer> shareParamStatusMap = shareParamVOList.stream().collect(Collectors.toMap(CostShareParamVO::getShareParamCode, paramVO -> paramVO.getStatus() == null ? NumberConstant.ONE : paramVO.getStatus(), (a, b) -> b));
  792. List<AllocationReportVO> removeList = new ArrayList<>();
  793. // 设置会计科目的
  794. allocationReportVOList.forEach(i -> {
  795. Long accountShareId = i.getAccountShareId();
  796. CostAccountShare costAccountShare = accountShareMap.get(accountShareId);
  797. if (Objects.isNull(costAccountShare)) {
  798. throw new CostException(500, "成本参数参数设置对应不存在");
  799. }
  800. i.setAccountCode(costAccountShare.getAccountingCodes());
  801. i.setAccountName(costAccountShare.getAccountingNames());
  802. i.setAlias(costAccountShare.getAlias());
  803. if (levelSort > 1) {
  804. List<String> targetMoney = new ArrayList<>();
  805. for (int j = 1; j < levelSort; j++) {
  806. // 每一次计算要设置为0
  807. AtomicReference<BigDecimal> money = new AtomicReference<>(new BigDecimal("0.0000"));
  808. List<Allocation> allocations1 = accrepMap.get(j + "cost" + i.getTargetResponsibilityCode());
  809. if (CollUtil.isNotEmpty(allocations1)) {
  810. allocations1.forEach(m -> {
  811. money.updateAndGet(v -> v.add(m.getAmount()));
  812. // System.out.println(m.getAmount());
  813. });
  814. } else {
  815. // TODO 封装测试数据
  816. shareMoney.add("0");
  817. }
  818. // System.out.println("第"+j+"次"+money);
  819. shareMoney.add(money.toString());
  820. targetMoney.add(money.toString());
  821. }
  822. if(!CollectionUtils.isEmpty(targetTotalMoneys)){
  823. List<String> strings = targetTotalMoneys.get(i.getTargetResponsibilityCode());
  824. if(CollectionUtils.isEmpty(strings)){
  825. targetTotalMoneys.put(i.getTargetResponsibilityCode(),targetMoney);
  826. }
  827. }else {
  828. targetTotalMoneys.put(i.getTargetResponsibilityCode(),targetMoney);
  829. }
  830. }
  831. i.setTargetShareMoneys(shareMoney);
  832. // 设置字符串类型数据
  833. i.setTotalAmounts(i.getTotalAmount().toString());
  834. i.setShareParamValueNums(i.getShareParamValueNum().toString());
  835. i.setShareParamRates(i.getShareParamRate().toString());
  836. i.setAmounts(i.getAmount().toString());
  837. //校验是否有分摊参数未启用
  838. Integer status = shareParamStatusMap.get(i.getShareParamCode());
  839. if(status != null&&status.equals(NumberConstant.ZERO)){
  840. removeList.add(i);
  841. }
  842. });
  843. //校验是否有分摊参数未启用 未启用分摊参数 移除
  844. if(!CollectionUtils.isEmpty(removeList)){
  845. allocationReportVOList.removeAll(removeList);
  846. }
  847. return allocationReportVOList;
  848. }
  849. /**
  850. * 分摊后报表
  851. *
  852. * @param year 年月(yyyy-MM-dd)
  853. * @param responsibilityCode 责任中心代码
  854. * @param hospId 医院id
  855. * @return List
  856. */
  857. @Override
  858. public CollectDataFormVO queryAfterAllocationForm(String year, String responsibilityCode, Long hospId) {
  859. DateTime dateTime = DateUtil.parseDate(year);
  860. int dateYear = DateUtil.year(dateTime);
  861. int month = DateUtil.month(dateTime) + 1;
  862. List<CodeAndNameVO> responsibilityCodeAndNames = allocationQueryService.getRespCodeAndName(hospId, dateYear, month);
  863. List<CodeAndNameVO> accountCodeAndNames = allocationQueryService.getAccountCodeAndName(hospId, dateYear, month);
  864. // todo 校验两个List是否为空
  865. // 填充
  866. responsibilityCodeAndNames.add(0, new CodeAndNameVO("#", "#"));
  867. responsibilityCodeAndNames.add(responsibilityCodeAndNames.size(), new CodeAndNameVO("合计", "合计"));
  868. List<String> titleData = responsibilityCodeAndNames.stream().map(CodeAndNameVO::getName).collect(Collectors.toList());
  869. List<String> respCodes = responsibilityCodeAndNames.stream().map(CodeAndNameVO::getCode).collect(Collectors.toList());
  870. Map<Integer, String> titleMap = new HashMap<>();
  871. for (int i = 0; i < titleData.size(); i++) {
  872. titleMap.put(i + 1, titleData.get(i));
  873. }
  874. List<Map<Integer, Object>> realDatas = new ArrayList<>();
  875. List<String> accountCodes = accountCodeAndNames.stream().map(CodeAndNameVO::getCode).collect(Collectors.toList());
  876. for (CodeAndNameVO account : accountCodeAndNames) {
  877. Map<Integer, Object> map = new HashMap<>();
  878. for (int i = 0; i < responsibilityCodeAndNames.size(); i++) {
  879. if (i == 0) {
  880. map.put(i + 1, account.getName());
  881. continue;
  882. } else if (i == responsibilityCodeAndNames.size() - 1) {
  883. // todo 计算最右侧合计的钱
  884. BigDecimal amount = allocationQueryService.getTotalByAccountAndResps(hospId, dateYear, month, account.getCode(), respCodes);
  885. map.put(i + 1, amount);
  886. continue;
  887. }
  888. // TODO: 2021/8/26 计算 中间的钱
  889. BigDecimal amount = allocationQueryService.getTotalByAccountAndRespCode(hospId, dateYear, month, account.getCode(), respCodes.get(i));
  890. map.put(i + 1, amount);
  891. }
  892. realDatas.add(map);
  893. }
  894. // 尾栏计算
  895. Map<Integer, Object> map = new HashMap<>();
  896. for (int i = 0; i < titleData.size(); i++) {
  897. if (i == 0) {
  898. map.put(i + 1, "合计");
  899. continue;
  900. } else if (i == titleData.size() - 1) {
  901. // TODO: 2021/8/26 计算
  902. BigDecimal bigDecimal = allocationQueryService.getTotalMoney(dateYear, month, hospId);
  903. map.put(i + 1, bigDecimal);
  904. continue;
  905. }
  906. BigDecimal bigDecimal = allocationQueryService.getCountByRespAndAccounts(hospId, dateYear, month, responsibilityCodeAndNames.get(i).getCode(), accountCodes);
  907. map.put(i + 1, bigDecimal);
  908. }
  909. return new CollectDataFormVO(titleMap, realDatas, map);
  910. }
  911. /**
  912. * 分摊后报表输出
  913. *
  914. * @param date yyyy-MM-dd
  915. * @param hospId 医院id
  916. * @return List
  917. */
  918. @Override
  919. public List<AfterAllocationFormVO> afterAllocationFormList(String date, Long hospId) {
  920. DateTime parse = DateUtil.parse(date);
  921. int year = DateUtil.year(parse);
  922. int month = DateUtil.month(parse) + 1;
  923. // 得到这个月的分摊过的分摊层级
  924. List<Allocation> list = baseMapper.getAllSortLevel(hospId, year, month);
  925. Map<Long, CostShareLevel> map = shareLevelService.list(new QueryWrapper<CostShareLevel>().lambda().eq(CostShareLevel::getHospId, hospId)).stream().collect(Collectors.toMap(CostShareLevel::getId, synOne -> synOne));
  926. // list.
  927. List<AfterAllocationFormVO> vos = list.stream().map(i -> {
  928. AfterAllocationFormVO vo = new AfterAllocationFormVO();
  929. vo.setId(i.getId());
  930. vo.setYear(i.getDateYear());
  931. vo.setMonth(i.getDateMonth());
  932. vo.setShareLevel(i.getLevelSort());
  933. vo.setShareReportName(map.get(i.getShareLevelId()).getShareName() + "分摊");
  934. vo.setShareTime(DateUtil.date(i.getCreateTime()));
  935. vo.setShareLevelId(i.getShareLevelId());
  936. return vo;
  937. }).collect(Collectors.toList());
  938. return vos;
  939. }
  940. /**
  941. * 按时间计算分摊数据
  942. *
  943. * @param year 年月
  944. * @param month 月
  945. * @param hospId
  946. * @return
  947. */
  948. @Override
  949. public List<Allocation> getByDate(int year, int month, Long hospId) {
  950. return this.list(
  951. new LambdaQueryWrapper<Allocation>()
  952. .eq(Allocation::getDateYear, year)
  953. .eq(Allocation::getDateMonth, month)
  954. .eq(Allocation::getHospId, hospId)
  955. );
  956. }
  957. }