AccountingServiceImpl.java 14 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358
  1. package com.imed.costaccount.service.impl;
  2. import cn.hutool.core.collection.CollUtil;
  3. import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
  4. import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
  5. import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
  6. import com.imed.costaccount.common.exception.CostException;
  7. import com.imed.costaccount.mapper.AccountingMapper;
  8. import com.imed.costaccount.model.Accounting;
  9. import com.imed.costaccount.model.User;
  10. import com.imed.costaccount.model.dto.AccountingEditDTO;
  11. import com.imed.costaccount.model.dto.AccountingSaveDTO;
  12. import com.imed.costaccount.model.vo.AccountVO;
  13. import com.imed.costaccount.model.vo.SelectAccountingVO;
  14. import com.imed.costaccount.service.AccountingService;
  15. import com.imed.costaccount.service.CostShareParamService;
  16. import com.imed.costaccount.utils.BeanUtil;
  17. import lombok.extern.slf4j.Slf4j;
  18. import org.springframework.stereotype.Service;
  19. import org.springframework.transaction.annotation.Propagation;
  20. import org.springframework.transaction.annotation.Transactional;
  21. import java.util.*;
  22. import java.util.stream.Collectors;
  23. @Slf4j
  24. @Service("accountingService")
  25. public class AccountingServiceImpl extends ServiceImpl<AccountingMapper, Accounting> implements AccountingService {
  26. private final CostShareParamService shareParamService;
  27. public AccountingServiceImpl(CostShareParamService shareParamService) {
  28. this.shareParamService = shareParamService;
  29. }
  30. /**
  31. * 获取会计科目列表按收入支出类型
  32. *
  33. * @param accountType 会计科目类型1.收入,2.支出
  34. * @param user
  35. * @param shareParamId
  36. * @return
  37. */
  38. @Override
  39. public List<AccountVO> getListByAccountType(Integer accountType, User user, Integer shareParamId, Integer incomeGroutSetId) {
  40. // 1. 得到所有的会计科目
  41. List<Accounting> list = this.list(
  42. new LambdaQueryWrapper<Accounting>()
  43. .eq(Accounting::getHospId, user.getHospId())
  44. .eq(Accounting::getAccountingType, accountType)
  45. .orderByDesc(Accounting::getCreateTime)
  46. );
  47. if (CollUtil.isEmpty(list)) {
  48. return Collections.emptyList();
  49. }
  50. // 所有的
  51. // List<AccountVO> all = list.stream().map(i -> BeanUtil.con(i, AccountVO.class)).collect(Collectors.toList());
  52. List<AccountVO> all = BeanUtil.convertList(list, AccountVO.class);
  53. // 查询所有的已绑定的分摊参数
  54. if (Objects.nonNull(shareParamId)) {
  55. List<Integer> ids = shareParamService.selectIsSelect(shareParamId);
  56. if (CollUtil.isNotEmpty(ids)) {
  57. all.forEach(i -> {
  58. if (ids.contains(i.getId())) {
  59. i.setIsShareParamSelect(true);
  60. }
  61. });
  62. }
  63. }
  64. // 顶层的
  65. List<AccountVO> parents = all.stream().filter(i -> i.getParentId() == 0).collect(Collectors.toList());
  66. List<AccountVO> accountVOS = new ArrayList<>();
  67. for (AccountVO parent : parents) {
  68. List<AccountVO> accountTree = this.getAccountTree(parent, all);
  69. accountVOS.addAll(accountTree);
  70. }
  71. return accountVOS;
  72. }
  73. /**
  74. * 递归处理
  75. *
  76. * @param accountVO
  77. * @param list
  78. * @return
  79. */
  80. private List<AccountVO> getAccountTree(AccountVO accountVO, List<AccountVO> list) {
  81. List<AccountVO> accountVOS = new ArrayList<>();
  82. accountVOS.add(accountVO);
  83. for (AccountVO account : list) {
  84. // 如果是父子关系
  85. if (accountVO.getId().equals(account.getParentId())) {
  86. List<AccountVO> child = accountVO.getChildren();
  87. if (CollUtil.isEmpty(child)) {
  88. child = new ArrayList<>();
  89. }
  90. child.add(account);
  91. accountVO.setChildren(child);
  92. // 处理子节点
  93. this.getAccountTree(account, list);
  94. }
  95. }
  96. return accountVOS;
  97. }
  98. /**
  99. * 保存会计科目
  100. *
  101. * @param accountingSaveDTO
  102. * @param user
  103. */
  104. @Override
  105. @Transactional(propagation = Propagation.REQUIRED)
  106. public void saveAccounting(AccountingSaveDTO accountingSaveDTO, User user) {
  107. // 校验会计科目代码
  108. this.checkAccountingCode(accountingSaveDTO.getAccountingCode(), user.getHospId());
  109. // 新增逻辑
  110. Long parentId = accountingSaveDTO.getId();
  111. // 不是顶层的
  112. String allParentIds = "0";
  113. if (parentId != 0) {
  114. Accounting byId = this.getById(parentId);
  115. if (Objects.isNull(byId)) {
  116. throw new CostException(500, "上层级别会计科目已被移除");
  117. }
  118. // 如果父子节点的会计科目类型不一致,退出
  119. if (!byId.getAccountingType().equals(accountingSaveDTO.getAccountingType())) {
  120. throw new CostException(500, "会计科目类型要与上层一致");
  121. }
  122. String oldParentIds = byId.getAllParentIds();
  123. if ("0".equals(oldParentIds)) {
  124. allParentIds = parentId + "";
  125. } else {
  126. allParentIds = oldParentIds + "-" + parentId;
  127. }
  128. }
  129. Accounting accounting = BeanUtil.convertObj(accountingSaveDTO, Accounting.class);
  130. accounting.setHospId(user.getHospId());
  131. accounting.setParentId(parentId);
  132. accounting.setAllParentIds(allParentIds);
  133. accounting.setCreateTime(System.currentTimeMillis());
  134. // 如果是支出类型
  135. if (accountingSaveDTO.getAccountingType().equals(2)) {
  136. Integer isBaseCode = accountingSaveDTO.getIsBaseCode();
  137. if (Objects.isNull(isBaseCode)) {
  138. throw new CostException(500, "支出类型需要选择是否固定支出成本");
  139. }
  140. accounting.setIsBaseCost(isBaseCode);
  141. }
  142. this.save(accounting);
  143. }
  144. private void checkAccountingCode(String code, Long hospId) {
  145. List<Accounting> list = this.baseMapper.selectList(
  146. new QueryWrapper<Accounting>().lambda().select(Accounting::getId)
  147. .eq(Accounting::getAccountingCode, code)
  148. .eq(Accounting::getHospId, hospId)
  149. );
  150. if (CollUtil.isNotEmpty(list)) {
  151. throw new CostException(500, "会计科目代码已存在,请重新生成");
  152. }
  153. }
  154. /**
  155. * 选择会计科目列表
  156. *
  157. * @param user
  158. * @return
  159. */
  160. @Override
  161. public List<SelectAccountingVO> selectAccounting(User user) {
  162. List<Accounting> list = this.list(
  163. new LambdaQueryWrapper<Accounting>().select(Accounting::getId, Accounting::getAccountingName, Accounting::getParentId, Accounting::getAllParentIds)
  164. .eq(Accounting::getHospId, user.getHospId())
  165. );
  166. if (CollUtil.isEmpty(list)) {
  167. return Collections.emptyList();
  168. }
  169. // 所有的
  170. List<SelectAccountingVO> all = list.stream().map(i -> {
  171. SelectAccountingVO vo = new SelectAccountingVO();
  172. vo.setValue(i.getId());
  173. vo.setLabel(i.getAccountingName());
  174. vo.setChildren(null);
  175. vo.setParentId(i.getParentId());
  176. vo.setAllParentIds(i.getAllParentIds());
  177. return vo;
  178. }).collect(Collectors.toList());
  179. // 顶层的
  180. List<SelectAccountingVO> parents = all.stream().filter(i -> i.getParentId() == 0).collect(Collectors.toList());
  181. List<SelectAccountingVO> accountVOS = new ArrayList<>();
  182. for (SelectAccountingVO parent : parents) {
  183. List<SelectAccountingVO> accountTree = this.getSelectAccountTree(parent, all);
  184. accountVOS.addAll(accountTree);
  185. }
  186. return accountVOS;
  187. }
  188. private List<SelectAccountingVO> getSelectAccountTree(SelectAccountingVO parent, List<SelectAccountingVO> all) {
  189. List<SelectAccountingVO> accountVOS = new ArrayList<>();
  190. accountVOS.add(parent);
  191. for (SelectAccountingVO account : all) {
  192. // 如果是父子关系
  193. if (parent.getValue().equals(account.getParentId())) {
  194. List<SelectAccountingVO> child = parent.getChildren();
  195. if (CollUtil.isEmpty(child)) {
  196. child = new ArrayList<>();
  197. }
  198. child.add(account);
  199. parent.setChildren(child);
  200. // 处理子节点
  201. this.getSelectAccountTree(account, all);
  202. }
  203. }
  204. return accountVOS;
  205. }
  206. /**
  207. * 编辑科目代码
  208. *
  209. * @param accountingEditDTO
  210. * @param user
  211. */
  212. @Override
  213. @Transactional(propagation = Propagation.REQUIRED, rollbackFor = Exception.class)
  214. public void updateAccount(AccountingEditDTO accountingEditDTO, User user) {
  215. // TODO: 2021/7/28 追踪溯源需求不满足
  216. Long id = accountingEditDTO.getId();
  217. // this.checkAccountingCode(accountingEditDTO.getAccountingCode(), user.getHospId());
  218. Accounting one = this.baseMapper.selectOne(
  219. new QueryWrapper<Accounting>().lambda()
  220. .eq(Accounting::getAccountingCode, accountingEditDTO.getAccountingCode())
  221. .eq(Accounting::getHospId, user.getHospId())
  222. .last("limit 1")
  223. );
  224. Accounting byId = this.getById(id);
  225. if (Objects.isNull(byId)) {
  226. throw new CostException(500, "当前选中会计科目已被移除");
  227. }
  228. if (Objects.nonNull(one) && !byId.getAccountingCode().equals(one.getAccountingCode())) {
  229. throw new CostException(500, "会计科目代码已存在,请重新生成");
  230. }
  231. // 直接修改 TODO 不修改会计科目Code
  232. byId.setAccountingCode(byId.getAccountingCode());
  233. byId.setAccountingName(accountingEditDTO.getAccountingName());
  234. byId.setCreateTime(System.currentTimeMillis());
  235. // byId.setAccountingType(accountingEditDTO.getAccountingType());
  236. this.updateById(byId);
  237. // this.removeById(id);
  238. // Accounting accounting = BeanUtil.convertObj(byId, Accounting.class);
  239. // saveAccount(accountingEditDTO, user, byId, accounting);
  240. // List<Accounting> list = new ArrayList<>();
  241. // this.getAndAllChild(Arrays.asList(id), user.getHospId(), list);
  242. // log.info("list:{}", list);
  243. // if (CollUtil.isEmpty(list)) {
  244. // return;
  245. // }
  246. // // 第一个子节点
  247. // List<Accounting> childList = list.stream().filter(i -> i.getParentId().equals(id)).collect(Collectors.toList());
  248. // if (CollUtil.isEmpty(childList)) {
  249. // throw new CostException(500, "数据异常");
  250. // }
  251. // childList.forEach(i -> {
  252. // i.setParentId(accounting.getId());
  253. // String allParentIds = setAllParentIds(byId);
  254. // i.setAllParentIds(allParentIds);
  255. // });
  256. // this.updateBatchById(childList);
  257. //
  258. //
  259. }
  260. // private String setAllParentIds(Accounting byId) {
  261. // Integer parentId = byId.getParentId();
  262. // // 不是顶层的
  263. // String allParentIds = "0";
  264. // if (parentId != 0) {
  265. // String oldParentIds = byId.getAllParentIds();
  266. // if ("0".equals(oldParentIds)) {
  267. // allParentIds = parentId + "";
  268. // } else {
  269. // allParentIds = oldParentIds + "-" + parentId;
  270. // }
  271. // }
  272. // return allParentIds;
  273. // }
  274. @Transactional(propagation = Propagation.REQUIRED, rollbackFor = Exception.class)
  275. public void saveAccount(AccountingEditDTO accountingEditDTO, User user, Accounting byId, Accounting accounting) {
  276. this.checkAccountingCode(accountingEditDTO.getAccountingCode(), user.getHospId());
  277. accounting.setAccountingCode(accounting.getAccountingCode());
  278. accounting.setCreateTime(System.currentTimeMillis());
  279. // 新增逻辑
  280. Long parentId = byId.getParentId();
  281. // 不是顶层的
  282. String allParentIds = "0";
  283. if (parentId != 0) {
  284. String oldParentIds = byId.getAllParentIds();
  285. if ("0".equals(oldParentIds)) {
  286. allParentIds = parentId + "";
  287. } else {
  288. allParentIds = oldParentIds + "-" + parentId;
  289. }
  290. }
  291. accounting.setHospId(user.getHospId());
  292. accounting.setParentId(parentId);
  293. accounting.setAllParentIds(allParentIds);
  294. accounting.setCreateTime(System.currentTimeMillis());
  295. this.save(accounting);
  296. }
  297. /**
  298. * 得到自己还有所有的子节点
  299. *
  300. * @param ids
  301. * @param accounts
  302. * @return
  303. */
  304. private List<Accounting> getAndAllChild(List<Long> ids, Long hospId, List<Accounting> accounts) {
  305. List<Accounting> list = this.list(
  306. new LambdaQueryWrapper<Accounting>()
  307. .in(Accounting::getParentId, ids).eq(Accounting::getHospId, hospId)
  308. );
  309. if (CollUtil.isEmpty(list)) {
  310. return accounts;
  311. }
  312. accounts.addAll(list);
  313. this.getAndAllChild(list.stream().map(Accounting::getId).collect(Collectors.toList()), hospId, accounts);
  314. return accounts;
  315. }
  316. /**
  317. * 删除
  318. *
  319. * @param id
  320. * @param user
  321. */
  322. @Override
  323. @Transactional(propagation = Propagation.REQUIRED, rollbackFor = Exception.class)
  324. public void deleteAccount(Long id, User user) {
  325. List<Accounting> list = new ArrayList<>();
  326. List<Accounting> andAllChild = this.getAndAllChild(Arrays.asList(id), user.getHospId(), list);
  327. if (CollUtil.isEmpty(andAllChild)) {
  328. this.removeById(id);
  329. }
  330. List<Long> collect = andAllChild.stream().map(Accounting::getId).collect(Collectors.toList());
  331. collect.add(id);
  332. this.removeByIds(collect);
  333. }
  334. }