package com.imed.costaccount.service.impl; import cn.hutool.core.collection.CollUtil; import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper; import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper; import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl; import com.imed.costaccount.common.exception.CostException; import com.imed.costaccount.mapper.AccountingMapper; import com.imed.costaccount.model.Accounting; import com.imed.costaccount.model.User; import com.imed.costaccount.model.dto.AccountingEditDTO; import com.imed.costaccount.model.dto.AccountingSaveDTO; import com.imed.costaccount.model.vo.AccountVO; import com.imed.costaccount.model.vo.SelectAccountingVO; import com.imed.costaccount.service.AccountingService; import com.imed.costaccount.service.CostShareParamService; import com.imed.costaccount.utils.BeanUtil; import lombok.extern.slf4j.Slf4j; import org.springframework.stereotype.Service; import org.springframework.transaction.annotation.Propagation; import org.springframework.transaction.annotation.Transactional; import java.util.*; import java.util.stream.Collectors; @Slf4j @Service("accountingService") public class AccountingServiceImpl extends ServiceImpl implements AccountingService { private final CostShareParamService shareParamService; public AccountingServiceImpl(CostShareParamService shareParamService) { this.shareParamService = shareParamService; } /** * 获取会计科目列表按收入支出类型 * * @param accountType 会计科目类型1.收入,2.支出 * @param user * @param shareParamId * @return */ @Override public List getListByAccountType(Integer accountType, User user, Integer shareParamId, Integer incomeGroutSetId) { // 1. 得到所有的会计科目 List list = this.list( new LambdaQueryWrapper() .eq(Accounting::getHospId, user.getHospId()) .eq(Accounting::getAccountingType, accountType) .orderByDesc(Accounting::getCreateTime) ); if (CollUtil.isEmpty(list)) { return Collections.emptyList(); } // 所有的 // List all = list.stream().map(i -> BeanUtil.con(i, AccountVO.class)).collect(Collectors.toList()); List all = BeanUtil.convertList(list, AccountVO.class); // 查询所有的已绑定的分摊参数 if (Objects.nonNull(shareParamId)) { List ids = shareParamService.selectIsSelect(shareParamId); if (CollUtil.isNotEmpty(ids)) { all.forEach(i -> { if (ids.contains(i.getId())) { i.setIsShareParamSelect(true); } }); } } // 顶层的 List parents = all.stream().filter(i -> i.getParentId() == 0).collect(Collectors.toList()); List accountVOS = new ArrayList<>(); for (AccountVO parent : parents) { List accountTree = this.getAccountTree(parent, all); accountVOS.addAll(accountTree); } return accountVOS; } /** * 递归处理 * * @param accountVO * @param list * @return */ private List getAccountTree(AccountVO accountVO, List list) { List accountVOS = new ArrayList<>(); accountVOS.add(accountVO); for (AccountVO account : list) { // 如果是父子关系 if (accountVO.getId().equals(account.getParentId())) { List child = accountVO.getChildren(); if (CollUtil.isEmpty(child)) { child = new ArrayList<>(); } child.add(account); accountVO.setChildren(child); // 处理子节点 this.getAccountTree(account, list); } } return accountVOS; } /** * 保存会计科目 * * @param accountingSaveDTO * @param user */ @Override @Transactional(propagation = Propagation.REQUIRED) public void saveAccounting(AccountingSaveDTO accountingSaveDTO, User user) { // 校验会计科目代码 this.checkAccountingCode(accountingSaveDTO.getAccountingCode(), user.getHospId()); // 新增逻辑 Long parentId = accountingSaveDTO.getId(); // 不是顶层的 String allParentIds = "0"; if (parentId != 0) { Accounting byId = this.getById(parentId); if (Objects.isNull(byId)) { throw new CostException(500, "上层级别会计科目已被移除"); } // 如果父子节点的会计科目类型不一致,退出 if (!byId.getAccountingType().equals(accountingSaveDTO.getAccountingType())) { throw new CostException(500, "会计科目类型要与上层一致"); } String oldParentIds = byId.getAllParentIds(); if ("0".equals(oldParentIds)) { allParentIds = parentId + ""; } else { allParentIds = oldParentIds + "-" + parentId; } } Accounting accounting = BeanUtil.convertObj(accountingSaveDTO, Accounting.class); accounting.setHospId(user.getHospId()); accounting.setParentId(parentId); accounting.setAllParentIds(allParentIds); accounting.setCreateTime(System.currentTimeMillis()); // 如果是支出类型 if (accountingSaveDTO.getAccountingType().equals(2)) { Integer isBaseCode = accountingSaveDTO.getIsBaseCode(); if (Objects.isNull(isBaseCode)) { throw new CostException(500, "支出类型需要选择是否固定支出成本"); } accounting.setIsBaseCost(isBaseCode); } this.save(accounting); } private void checkAccountingCode(String code, Long hospId) { List list = this.baseMapper.selectList( new QueryWrapper().lambda().select(Accounting::getId) .eq(Accounting::getAccountingCode, code) .eq(Accounting::getHospId, hospId) ); if (CollUtil.isNotEmpty(list)) { throw new CostException(500, "会计科目代码已存在,请重新生成"); } } /** * 选择会计科目列表 * * @param user * @return */ @Override public List selectAccounting(User user) { List list = this.list( new LambdaQueryWrapper().select(Accounting::getId, Accounting::getAccountingName, Accounting::getParentId, Accounting::getAllParentIds) .eq(Accounting::getHospId, user.getHospId()) ); if (CollUtil.isEmpty(list)) { return Collections.emptyList(); } // 所有的 List all = list.stream().map(i -> { SelectAccountingVO vo = new SelectAccountingVO(); vo.setValue(i.getId()); vo.setLabel(i.getAccountingName()); vo.setChildren(null); vo.setParentId(i.getParentId()); vo.setAllParentIds(i.getAllParentIds()); return vo; }).collect(Collectors.toList()); // 顶层的 List parents = all.stream().filter(i -> i.getParentId() == 0).collect(Collectors.toList()); List accountVOS = new ArrayList<>(); for (SelectAccountingVO parent : parents) { List accountTree = this.getSelectAccountTree(parent, all); accountVOS.addAll(accountTree); } return accountVOS; } private List getSelectAccountTree(SelectAccountingVO parent, List all) { List accountVOS = new ArrayList<>(); accountVOS.add(parent); for (SelectAccountingVO account : all) { // 如果是父子关系 if (parent.getValue().equals(account.getParentId())) { List child = parent.getChildren(); if (CollUtil.isEmpty(child)) { child = new ArrayList<>(); } child.add(account); parent.setChildren(child); // 处理子节点 this.getSelectAccountTree(account, all); } } return accountVOS; } /** * 编辑科目代码 * * @param accountingEditDTO * @param user */ @Override @Transactional(propagation = Propagation.REQUIRED, rollbackFor = Exception.class) public void updateAccount(AccountingEditDTO accountingEditDTO, User user) { // TODO: 2021/7/28 追踪溯源需求不满足 Long id = accountingEditDTO.getId(); // this.checkAccountingCode(accountingEditDTO.getAccountingCode(), user.getHospId()); Accounting one = this.baseMapper.selectOne( new QueryWrapper().lambda() .eq(Accounting::getAccountingCode, accountingEditDTO.getAccountingCode()) .eq(Accounting::getHospId, user.getHospId()) .last("limit 1") ); Accounting byId = this.getById(id); if (Objects.isNull(byId)) { throw new CostException(500, "当前选中会计科目已被移除"); } if (Objects.nonNull(one) && !byId.getAccountingCode().equals(one.getAccountingCode())) { throw new CostException(500, "会计科目代码已存在,请重新生成"); } // 直接修改 TODO 不修改会计科目Code byId.setAccountingCode(byId.getAccountingCode()); byId.setAccountingName(accountingEditDTO.getAccountingName()); byId.setCreateTime(System.currentTimeMillis()); // byId.setAccountingType(accountingEditDTO.getAccountingType()); this.updateById(byId); // this.removeById(id); // Accounting accounting = BeanUtil.convertObj(byId, Accounting.class); // saveAccount(accountingEditDTO, user, byId, accounting); // List list = new ArrayList<>(); // this.getAndAllChild(Arrays.asList(id), user.getHospId(), list); // log.info("list:{}", list); // if (CollUtil.isEmpty(list)) { // return; // } // // 第一个子节点 // List childList = list.stream().filter(i -> i.getParentId().equals(id)).collect(Collectors.toList()); // if (CollUtil.isEmpty(childList)) { // throw new CostException(500, "数据异常"); // } // childList.forEach(i -> { // i.setParentId(accounting.getId()); // String allParentIds = setAllParentIds(byId); // i.setAllParentIds(allParentIds); // }); // this.updateBatchById(childList); // // } // private String setAllParentIds(Accounting byId) { // Integer parentId = byId.getParentId(); // // 不是顶层的 // String allParentIds = "0"; // if (parentId != 0) { // String oldParentIds = byId.getAllParentIds(); // if ("0".equals(oldParentIds)) { // allParentIds = parentId + ""; // } else { // allParentIds = oldParentIds + "-" + parentId; // } // } // return allParentIds; // } @Transactional(propagation = Propagation.REQUIRED, rollbackFor = Exception.class) public void saveAccount(AccountingEditDTO accountingEditDTO, User user, Accounting byId, Accounting accounting) { this.checkAccountingCode(accountingEditDTO.getAccountingCode(), user.getHospId()); accounting.setAccountingCode(accounting.getAccountingCode()); accounting.setCreateTime(System.currentTimeMillis()); // 新增逻辑 Long parentId = byId.getParentId(); // 不是顶层的 String allParentIds = "0"; if (parentId != 0) { String oldParentIds = byId.getAllParentIds(); if ("0".equals(oldParentIds)) { allParentIds = parentId + ""; } else { allParentIds = oldParentIds + "-" + parentId; } } accounting.setHospId(user.getHospId()); accounting.setParentId(parentId); accounting.setAllParentIds(allParentIds); accounting.setCreateTime(System.currentTimeMillis()); this.save(accounting); } /** * 得到自己还有所有的子节点 * * @param ids * @param accounts * @return */ private List getAndAllChild(List ids, Long hospId, List accounts) { List list = this.list( new LambdaQueryWrapper() .in(Accounting::getParentId, ids).eq(Accounting::getHospId, hospId) ); if (CollUtil.isEmpty(list)) { return accounts; } accounts.addAll(list); this.getAndAllChild(list.stream().map(Accounting::getId).collect(Collectors.toList()), hospId, accounts); return accounts; } /** * 删除 * * @param id * @param user */ @Override @Transactional(propagation = Propagation.REQUIRED, rollbackFor = Exception.class) public void deleteAccount(Long id, User user) { List list = new ArrayList<>(); List andAllChild = this.getAndAllChild(Arrays.asList(id), user.getHospId(), list); if (CollUtil.isEmpty(andAllChild)) { this.removeById(id); } List collect = andAllChild.stream().map(Accounting::getId).collect(Collectors.toList()); collect.add(id); this.removeByIds(collect); } }