From ec5e245fb0bc29a32713ee2b15bbd636f2c148cd Mon Sep 17 00:00:00 2001 From: dzc <2388224167@qq.com> Date: Thu, 23 Jan 2025 10:03:52 +0800 Subject: [PATCH] =?UTF-8?q?feat:=E9=92=B1=E5=8C=85=E5=AF=BC=E5=87=BA?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../admin/controller/SysUserController.java | 1 + .../wallet/api/dto/WalletManageDto.java | 4 + .../controller/WalletManageController.java | 16 ++-- .../WalletTransactionController.java | 12 +-- .../wallet/mapper/WalletManageMapper.java | 25 ++++-- .../wallet/service/WalletManageService.java | 23 +++--- .../service/impl/WalletManageServiceImpl.java | 74 +++++++++++++++--- .../src/main/resources/file/账户余额.xlsx | Bin 0 -> 10046 bytes 8 files changed, 117 insertions(+), 38 deletions(-) create mode 100644 pjcloud-wallet/pjcloud-wallet-biz/src/main/resources/file/账户余额.xlsx diff --git a/pjcloud-upms/pjcloud-upms-biz/src/main/java/com/bsd/pjcloud/admin/controller/SysUserController.java b/pjcloud-upms/pjcloud-upms-biz/src/main/java/com/bsd/pjcloud/admin/controller/SysUserController.java index bd43c2dd3..df43e0495 100644 --- a/pjcloud-upms/pjcloud-upms-biz/src/main/java/com/bsd/pjcloud/admin/controller/SysUserController.java +++ b/pjcloud-upms/pjcloud-upms-biz/src/main/java/com/bsd/pjcloud/admin/controller/SysUserController.java @@ -20,6 +20,7 @@ package com.bsd.pjcloud.admin.controller; import cn.hutool.core.collection.CollUtil; +import cn.hutool.core.util.ObjectUtil; import com.baomidou.mybatisplus.core.toolkit.Wrappers; import com.baomidou.mybatisplus.extension.plugins.pagination.Page; import com.bsd.pjcloud.admin.api.dto.UserDTO; diff --git a/pjcloud-wallet/pjcloud-wallet-api/src/main/java/com/bsd/pjcloud/wallet/api/dto/WalletManageDto.java b/pjcloud-wallet/pjcloud-wallet-api/src/main/java/com/bsd/pjcloud/wallet/api/dto/WalletManageDto.java index 4ec219993..d9470b02e 100644 --- a/pjcloud-wallet/pjcloud-wallet-api/src/main/java/com/bsd/pjcloud/wallet/api/dto/WalletManageDto.java +++ b/pjcloud-wallet/pjcloud-wallet-api/src/main/java/com/bsd/pjcloud/wallet/api/dto/WalletManageDto.java @@ -3,6 +3,8 @@ package com.bsd.pjcloud.wallet.api.dto; import com.bsd.pjcloud.wallet.api.entity.WalletManageEntity; import lombok.Data; +import java.time.LocalDate; +import java.time.LocalDateTime; import java.util.List; @Data @@ -12,4 +14,6 @@ public class WalletManageDto extends WalletManageEntity { private List walletIds; + private LocalDateTime[] createTimeList; + } \ No newline at end of file diff --git a/pjcloud-wallet/pjcloud-wallet-biz/src/main/java/com/bsd/pjcloud/wallet/controller/WalletManageController.java b/pjcloud-wallet/pjcloud-wallet-biz/src/main/java/com/bsd/pjcloud/wallet/controller/WalletManageController.java index 091b42029..57015aced 100644 --- a/pjcloud-wallet/pjcloud-wallet-biz/src/main/java/com/bsd/pjcloud/wallet/controller/WalletManageController.java +++ b/pjcloud-wallet/pjcloud-wallet-biz/src/main/java/com/bsd/pjcloud/wallet/controller/WalletManageController.java @@ -7,6 +7,8 @@ import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper; import com.baomidou.mybatisplus.core.toolkit.Wrappers; import com.baomidou.mybatisplus.extension.plugins.pagination.Page; import com.bsd.pjcloud.common.core.util.R; +import com.bsd.pjcloud.common.data.datascope.DataScope; +import com.bsd.pjcloud.common.data.datascope.DataScopeFuncEnum; import com.bsd.pjcloud.common.log.annotation.SysLog; import com.bsd.pjcloud.common.security.annotation.Inner; import com.bsd.pjcloud.common.security.service.PjcloudUser; @@ -18,6 +20,7 @@ import com.bsd.pjcloud.wallet.api.vo.WalletManageVo; import com.bsd.pjcloud.wallet.mapper.WalletManageMapper; import com.bsd.pjcloud.wallet.service.WalletCodeUseService; import com.bsd.pjcloud.wallet.service.WalletManageService; +import jakarta.servlet.http.HttpServletResponse; import org.springframework.security.access.prepost.PreAuthorize; import com.bsd.pjcloud.common.excel.annotation.ResponseExcel; import io.swagger.v3.oas.annotations.security.SecurityRequirement; @@ -112,7 +115,9 @@ public class WalletManageController { PjcloudUser user = SecurityUtils.getUser(); WalletManageDto dto = new WalletManageDto(); dto.setUserId(user.getId()); - return R.ok(walletManageService.pageJoin(page, dto)); + DataScope dataScope = new DataScope(); + dataScope.func(DataScopeFuncEnum.ALL); + return R.ok(walletManageService.scopePageList(page, dto, dataScope)); } @Operation(summary = "分页查询", description = "分页查询") @@ -142,7 +147,7 @@ public class WalletManageController { @GetMapping("/page-join") @PreAuthorize("@pms.hasPermission('wallet_walletManage_view')") public R getWalletManagePageJoin(@ParameterObject Page page, @ParameterObject WalletManageDto dto) { - return R.ok(walletManageService.scopePageList(page, dto)); + return R.ok(walletManageService.scopePageList(page, dto, DataScope.of())); } @Operation(summary = "通过id查询", description = "通过id查询") @@ -175,11 +180,10 @@ public class WalletManageController { public R removeById(@RequestBody Long[] ids) { return R.ok(walletManageService.removeBatchByIds(CollUtil.toList(ids))); } - - @ResponseExcel + @GetMapping("/export") @PreAuthorize("@pms.hasPermission('wallet_walletManage_export')") - public List export(WalletManageEntity walletManage, Long[] ids) { - return walletManageService.list(Wrappers.lambdaQuery(walletManage).in(ArrayUtil.isNotEmpty(ids), WalletManageEntity::getId, ids)); + public void export(HttpServletResponse response, @ParameterObject Page page, @ParameterObject WalletManageDto dto) { + walletManageService.export(response, page, dto); } } \ No newline at end of file diff --git a/pjcloud-wallet/pjcloud-wallet-biz/src/main/java/com/bsd/pjcloud/wallet/controller/WalletTransactionController.java b/pjcloud-wallet/pjcloud-wallet-biz/src/main/java/com/bsd/pjcloud/wallet/controller/WalletTransactionController.java index 595385e48..108bd2c99 100644 --- a/pjcloud-wallet/pjcloud-wallet-biz/src/main/java/com/bsd/pjcloud/wallet/controller/WalletTransactionController.java +++ b/pjcloud-wallet/pjcloud-wallet-biz/src/main/java/com/bsd/pjcloud/wallet/controller/WalletTransactionController.java @@ -149,28 +149,28 @@ public class WalletTransactionController { @Operation(summary = "充值导出", description = "充值导出") @GetMapping("/export-cz") @PreAuthorize("@pms.hasPermission('wallet_walletTransaction_export')") - public void exportCz(HttpServletResponse response, WalletTransactionDto dto) { + public void exportCz(HttpServletResponse response, @ParameterObject Page page, WalletTransactionDto dto) { dto.setBizTypes(List.of(WalletBizEnum.RECHARGE.getCode())); - List list = walletTransactionService.pageList(dto); + List list = walletTransactionService.scopePageList(page, dto, DataScope.of()).getRecords(); walletTransactionService.exportByTemplate(response, dto, "file/个人充值明细.xlsx", list); } @Operation(summary = "消费导出", description = "消费导出") @GetMapping("/export-xf") @PreAuthorize("@pms.hasPermission('wallet_walletTransaction_export')") - public void exportXf(HttpServletResponse response, WalletTransactionDto dto) { + public void exportXf(HttpServletResponse response, @ParameterObject Page page, WalletTransactionDto dto) { dto.setBizTypes(List.of(WalletBizEnum.PAYMENT.getCode())); - List list = walletTransactionService.pageList(dto); + List list = walletTransactionService.scopePageList(page, dto, DataScope.of()).getRecords(); walletTransactionService.exportByTemplate(response, dto, "file/个人消费明细.xlsx", list); } @Operation(summary = "退款导出", description = "退款导出") @GetMapping("/export-tk") @PreAuthorize("@pms.hasPermission('wallet_walletTransaction_export')") - public void exportTk(HttpServletResponse response, WalletTransactionDto dto) { + public void exportTk(HttpServletResponse response, @ParameterObject Page page, WalletTransactionDto dto) { dto.setBizTypes(List.of(WalletBizEnum.REFUND.getCode())); dto.setIsFindOrder(true); - List list = walletTransactionService.pageList(dto); + List list = walletTransactionService.scopePageList(page, dto, DataScope.of()).getRecords(); walletTransactionService.exportByTemplate(response, dto, "file/个人退款明细.xlsx", list); } } \ No newline at end of file diff --git a/pjcloud-wallet/pjcloud-wallet-biz/src/main/java/com/bsd/pjcloud/wallet/mapper/WalletManageMapper.java b/pjcloud-wallet/pjcloud-wallet-biz/src/main/java/com/bsd/pjcloud/wallet/mapper/WalletManageMapper.java index bdcbde69b..e1c871278 100644 --- a/pjcloud-wallet/pjcloud-wallet-biz/src/main/java/com/bsd/pjcloud/wallet/mapper/WalletManageMapper.java +++ b/pjcloud-wallet/pjcloud-wallet-biz/src/main/java/com/bsd/pjcloud/wallet/mapper/WalletManageMapper.java @@ -13,7 +13,6 @@ import com.bsd.pjcloud.wallet.api.entity.WalletTypeEntity; import com.bsd.pjcloud.wallet.api.vo.WalletManageVo; import com.github.yulichang.wrapper.MPJLambdaWrapper; import org.apache.ibatis.annotations.Mapper; -import org.apache.ibatis.annotations.Param; import java.util.List; @@ -59,7 +58,7 @@ public interface WalletManageMapper extends PjcloudBaseMapper pageJoin(Page page, @Param("pa") WalletManageDto dto) { + default List joinList(WalletManageDto dto) { MPJLambdaWrapper wrapper = new MPJLambdaWrapper() .selectAll(WalletManageEntity.class) .selectAs(WalletTypeEntity::getName, WalletManageVo::getWalletTypeName) @@ -70,8 +69,14 @@ public interface WalletManageMapper extends PjcloudBaseMapper list(WalletManageDto dto) { @@ -95,14 +100,20 @@ public interface WalletManageMapper extends PjcloudBaseMapper scopePageList(Page page, WalletManageDto dto) { + default Page scopePageList(Page page, WalletManageDto dto, DataScope dataScope) { LambdaQueryWrapper wrapper = new LambdaQueryWrapper() .eq(ObjectUtil.isNotEmpty(dto.getUserId()), WalletManageEntity::getUserId, dto.getUserId()) .eq(ObjectUtil.isNotEmpty(dto.getWalletTypeId()), WalletManageEntity::getWalletTypeId, dto.getWalletTypeId()) .eq(ObjectUtil.isNotEmpty(dto.getIsFreeze()), WalletManageEntity::getIsFreeze, dto.getIsFreeze()) .in(ObjectUtil.isNotEmpty(dto.getWalletIds()), WalletManageEntity::getId, dto.getWalletIds()) - .in(ObjectUtil.isNotEmpty(dto.getUserIds()), WalletManageEntity::getUserId, dto.getUserIds()); - Page list = selectPageByScope(page, wrapper, DataScope.of()); + .in(ObjectUtil.isNotEmpty(dto.getUserIds()), WalletManageEntity::getUserId, dto.getUserIds()) + .between( + ObjectUtil.isNotEmpty(dto.getCreateTimeList()), + WalletManageEntity::getCreateTime, + ObjectUtil.isNotEmpty(dto.getCreateTimeList()) ? dto.getCreateTimeList()[0] : null, + ObjectUtil.isNotEmpty(dto.getCreateTimeList()) ? dto.getCreateTimeList()[1] : null + ); + Page list = selectPageByScope(page, wrapper, dataScope); list.setRecords(BeanUtils.toBean(list.getRecords(), WalletManageVo.class)); return list; } diff --git a/pjcloud-wallet/pjcloud-wallet-biz/src/main/java/com/bsd/pjcloud/wallet/service/WalletManageService.java b/pjcloud-wallet/pjcloud-wallet-biz/src/main/java/com/bsd/pjcloud/wallet/service/WalletManageService.java index 55af4c61d..53feeb7b6 100644 --- a/pjcloud-wallet/pjcloud-wallet-biz/src/main/java/com/bsd/pjcloud/wallet/service/WalletManageService.java +++ b/pjcloud-wallet/pjcloud-wallet-biz/src/main/java/com/bsd/pjcloud/wallet/service/WalletManageService.java @@ -3,10 +3,12 @@ package com.bsd.pjcloud.wallet.service; import com.baomidou.mybatisplus.extension.plugins.pagination.Page; import com.baomidou.mybatisplus.extension.service.IService; import com.bsd.pjcloud.common.core.util.R; +import com.bsd.pjcloud.common.data.datascope.DataScope; import com.bsd.pjcloud.wallet.api.constant.WalletTypeEnum; import com.bsd.pjcloud.wallet.api.dto.WalletManageDto; import com.bsd.pjcloud.wallet.api.entity.WalletManageEntity; import com.bsd.pjcloud.wallet.api.vo.WalletManageVo; +import jakarta.servlet.http.HttpServletResponse; import jakarta.validation.constraints.NotNull; import java.util.List; @@ -47,6 +49,7 @@ public interface WalletManageService extends IService { /** * 获取钱包(没有缓存) + * * @param cardNumber * @return */ @@ -70,7 +73,6 @@ public interface WalletManageService extends IService { */ WalletManageEntity getWallet(@NotNull Long walletId); - /** * 根据用户id删除用户钱包 * @@ -79,16 +81,9 @@ public interface WalletManageService extends IService { */ Boolean delWalletByUserIds(List<@NotNull Long> userIds); - /** - * 分页连表查询 - * - * @param page - * @param dto - * @return - */ - Page pageJoin(Page page, WalletManageDto dto); + Page scopePageList(Page page, WalletManageDto dto, DataScope dataScope); - Page scopePageList(Page page, WalletManageDto dto); + List joinList(WalletManageDto dto); WalletManageVo join(Long user, Long walletId); @@ -98,4 +93,12 @@ public interface WalletManageService extends IService { * @param walletId 钱包id */ String getQrCode(Long walletId); + + /** + * 导出 + * + * @param response + * @param dto + */ + void export(HttpServletResponse response, Page page, WalletManageDto dto); } \ No newline at end of file diff --git a/pjcloud-wallet/pjcloud-wallet-biz/src/main/java/com/bsd/pjcloud/wallet/service/impl/WalletManageServiceImpl.java b/pjcloud-wallet/pjcloud-wallet-biz/src/main/java/com/bsd/pjcloud/wallet/service/impl/WalletManageServiceImpl.java index 146841a91..aaad3d1ea 100644 --- a/pjcloud-wallet/pjcloud-wallet-biz/src/main/java/com/bsd/pjcloud/wallet/service/impl/WalletManageServiceImpl.java +++ b/pjcloud-wallet/pjcloud-wallet-biz/src/main/java/com/bsd/pjcloud/wallet/service/impl/WalletManageServiceImpl.java @@ -1,8 +1,15 @@ package com.bsd.pjcloud.wallet.service.impl; import cn.hutool.core.codec.Base64; +import cn.hutool.core.date.DatePattern; +import cn.hutool.core.date.LocalDateTimeUtil; +import cn.hutool.core.io.resource.ResourceUtil; import cn.hutool.core.util.ObjectUtil; import cn.hutool.extra.spring.SpringUtil; +import com.alibaba.excel.EasyExcel; +import com.alibaba.excel.ExcelWriter; +import com.alibaba.excel.write.metadata.WriteSheet; +import com.alibaba.excel.write.metadata.fill.FillConfig; import com.alibaba.fastjson.JSON; import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper; import com.baomidou.mybatisplus.extension.plugins.pagination.Page; @@ -18,6 +25,7 @@ import com.bsd.pjcloud.common.core.constant.enums.YesNoEnum; import com.bsd.pjcloud.common.core.util.BeanUtils; import com.bsd.pjcloud.common.core.util.CollectionUtils; import com.bsd.pjcloud.common.core.util.R; +import com.bsd.pjcloud.common.data.datascope.DataScope; import com.bsd.pjcloud.common.data.resolver.ParamResolver; import com.bsd.pjcloud.hard.api.constant.order.HardOrderTypeEnum; import com.bsd.pjcloud.hard.api.constant.order.HardPayTypeEnum; @@ -31,11 +39,13 @@ import com.bsd.pjcloud.wallet.api.entity.WalletTypeEntity; import com.bsd.pjcloud.wallet.api.utils.WalletDataUtil; import com.bsd.pjcloud.wallet.api.vo.WalletManageVo; import com.bsd.pjcloud.wallet.api.vo.WalletSettingVo; +import com.bsd.pjcloud.wallet.api.vo.transaction.WalletTransactionVo; import com.bsd.pjcloud.wallet.mapper.WalletManageMapper; import com.bsd.pjcloud.wallet.mapper.WalletTypeMapper; import com.bsd.pjcloud.wallet.service.WalletManageService; import com.bsd.pjcloud.wallet.service.WalletSettingService; import com.bsd.pjcloud.wallet.service.WalletTypeService; +import jakarta.servlet.http.HttpServletResponse; import jakarta.validation.constraints.NotNull; import lombok.RequiredArgsConstructor; import lombok.extern.slf4j.Slf4j; @@ -45,6 +55,9 @@ import org.springframework.stereotype.Service; import org.springframework.transaction.annotation.Transactional; import org.springframework.validation.annotation.Validated; +import java.io.IOException; +import java.math.BigDecimal; +import java.math.RoundingMode; import java.time.LocalDateTime; import java.time.ZoneId; import java.util.*; @@ -206,28 +219,28 @@ public class WalletManageServiceImpl extends ServiceImpl pageJoin(Page page, WalletManageDto dto) { - Page list = baseMapper.pageJoin(page, dto); - if (ObjectUtil.isNotEmpty(list.getRecords())) { + public List joinList(WalletManageDto dto) { + List list = baseMapper.joinList(dto); + if (ObjectUtil.isNotEmpty(list)) { // 用户 - List userIds = list.getRecords().stream().map(WalletManageVo::getUserId).distinct().toList(); + List userIds = list.stream().map(WalletManageVo::getUserId).distinct().toList(); R> userList = userService.getUserById(new ArrayList<>(userIds)); if (ObjectUtil.isNotEmpty(userList.getData())) { - DataUtil.convertUserList(list.getRecords(), CollectionUtils.convertMap(userList.getData(), SysUser::getUserId)); + DataUtil.convertUserList(list, CollectionUtils.convertMap(userList.getData(), SysUser::getUserId)); } // 部门 - List deptIds = list.getRecords().stream().map(WalletManageVo::getDeptId).distinct().toList(); + List deptIds = list.stream().map(WalletManageVo::getDeptId).distinct().toList(); R> deptList = deptService.getDeptByDeptIds(deptIds); if (ObjectUtil.isNotEmpty(deptList.getData())) { - DataUtil.convertDeptList(list.getRecords(), deptList.getData()); + DataUtil.convertDeptList(list, deptList.getData()); } } return list; } @Override - public Page scopePageList(Page page, WalletManageDto dto) { - Page list = baseMapper.scopePageList(page, dto); + public Page scopePageList(Page page, WalletManageDto dto, DataScope dataScope) { + Page list = baseMapper.scopePageList(page, dto, dataScope); if (ObjectUtil.isNotEmpty(list.getRecords())) { // 用户 List userIds = list.getRecords().stream().map(WalletManageVo::getUserId).distinct().toList(); @@ -267,6 +280,49 @@ public class WalletManageServiceImpl extends ServiceImpl list = scopePageList(page, dto, DataScope.of()).getRecords(); + try (ExcelWriter excelWriter = EasyExcel.write(response.getOutputStream()).withTemplate(ResourceUtil.getStream(fileName)).build()) { + WriteSheet writeSheet = EasyExcel.writerSheet().build(); + FillConfig fillConfig = FillConfig.builder().forceNewRow(Boolean.TRUE).build(); + Map map = new HashMap(); + if (ObjectUtil.isNotEmpty(dto.getCreateTimeList())) { + map.put("timeSpan", " 到 "); + map.put("startTime", LocalDateTimeUtil.format(dto.getCreateTimeList()[0], DatePattern.NORM_DATETIME_PATTERN)); + map.put("endTime", LocalDateTimeUtil.format(dto.getCreateTimeList()[0], DatePattern.NORM_DATETIME_PATTERN)); + } + if (ObjectUtil.isNotEmpty(list)) { + BigDecimal balanceSum = BigDecimal.ZERO; + BigDecimal totalExpenseSum = BigDecimal.ZERO; + BigDecimal totalRechargeSum = BigDecimal.ZERO; + for (WalletManageVo v : list) { + if (ObjectUtil.isNotEmpty(v.getBalance())) { + balanceSum = balanceSum.add(BigDecimal.valueOf(v.getBalance())); + v.setBalance(BigDecimal.valueOf(v.getBalance()).divide(BigDecimal.valueOf(100)).setScale(2, RoundingMode.HALF_UP).intValue()); + } + if (ObjectUtil.isNotEmpty(v.getTotalExpense())) { + totalExpenseSum = totalExpenseSum.add(BigDecimal.valueOf(v.getTotalExpense())); + v.setTotalExpense(BigDecimal.valueOf(v.getTotalExpense()).divide(BigDecimal.valueOf(100)).setScale(2, RoundingMode.HALF_UP).intValue()); + } + if (ObjectUtil.isNotEmpty(v.getTotalRecharge())) { + totalRechargeSum = totalRechargeSum.add(BigDecimal.valueOf(v.getTotalRecharge())); + v.setTotalRecharge(BigDecimal.valueOf(v.getTotalRecharge()).divide(BigDecimal.valueOf(100)).setScale(2, RoundingMode.HALF_UP).intValue()); + } + } + map.put("balanceSum", balanceSum.divide(BigDecimal.valueOf(100)).setScale(2, RoundingMode.HALF_UP).toString()); + map.put("totalExpenseSum", totalExpenseSum.divide(BigDecimal.valueOf(100)).setScale(2, RoundingMode.HALF_UP).toString()); + map.put("totalRechargeSum", totalRechargeSum.divide(BigDecimal.valueOf(100)).setScale(2, RoundingMode.HALF_UP).toString()); + } + excelWriter.fill(map, writeSheet); + excelWriter.fill(list, fillConfig, writeSheet); + } catch (IOException e) { + e.printStackTrace(); + log.error("|{}|导入错误,dto:|{}|,fileName:|{}|,error:|{}|", TAG, JSON.toJSONString(dto), fileName, e.getMessage()); + } + } + private WalletManageServiceImpl getSelf() { return SpringUtil.getBean(getClass()); } diff --git a/pjcloud-wallet/pjcloud-wallet-biz/src/main/resources/file/账户余额.xlsx b/pjcloud-wallet/pjcloud-wallet-biz/src/main/resources/file/账户余额.xlsx new file mode 100644 index 0000000000000000000000000000000000000000..e0c7f7c366c8256b0e0094e3d074e4370d9bb6fe GIT binary patch literal 10046 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