Merge remote-tracking branch 'origin/master'

This commit is contained in:
zjf committed 2025-06-24 14:54:32 +08:00
commit 5735dbb445
15 files changed
+585 -2

No files matched your search

+28
View File
@@ -385,6 +385,34 @@ CREATE TABLE wallet_recharge_apply
COLLATE = utf8mb4_general_ci COMMENT ='充值申请表';
CREATE INDEX idx_dept_id ON wallet_recharge_apply (user_id);
-- ----------------------------
-- Table structure for wallet_recharge_invoice
-- ----------------------------
DROP TABLE IF EXISTS wallet_recharge_invoice;
CREATE TABLE wallet_recharge_invoice
(
id bigint NOT NULL COMMENT '主键ID',
apply_id bigint NOT NULL COMMENT '申请id',
code varchar(32) NOT NULL COMMENT '发票代码(七位数)',
time datetime DEFAULT NULL COMMENT '发票日期',
dept_or_user varchar(64) DEFAULT NULL COMMENT '交款单位或个人',
total_price int DEFAULT NULL COMMENT '合计人民币',
payee_dept varchar(64) DEFAULT NULL COMMENT '收款单位',
payee_user varchar(64) DEFAULT NULL COMMENT '收款人',
item_json varchar(2048) DEFAULT NULL COMMENT '备注',
remark varchar(1024) DEFAULT NULL COMMENT '备注',
status varchar(32) DEFAULT NULL COMMENT '状态',
create_by varchar(64) COLLATE utf8mb4_general_ci DEFAULT NULL COMMENT '创建人',
create_time datetime DEFAULT NULL COMMENT '创建时间',
update_by varchar(64) COLLATE utf8mb4_general_ci DEFAULT NULL COMMENT '修改人',
update_time datetime DEFAULT NULL COMMENT '修改时间',
del_flag char(1) COLLATE utf8mb4_general_ci DEFAULT '0' COMMENT '删除标记',
tenant_id bigint DEFAULT NULL COMMENT '租户ID',
PRIMARY KEY (id)
) ENGINE = InnoDB
DEFAULT CHARSET = utf8mb4
COLLATE = utf8mb4_general_ci COMMENT ='充值申请发票表';
-- ----------------------------
-- Table structure for wallet_recharge_import
-- ----------------------------
@@ -0,0 +1,27 @@
package com.bsd.pjcloud.wallet.api.constant;
import cn.hutool.core.util.ObjectUtil;
import lombok.AllArgsConstructor;
import lombok.Getter;
import java.util.Arrays;
// cancellation
@Getter
@AllArgsConstructor
public enum WalletRechargeInvoiceStatusEnum {
DEFAULT("1", "默认"),
CANCELLATION("2", "作废"),
;
private final String code;
private final String desc;
public static WalletRechargeInvoiceStatusEnum descOf(String description) {
return Arrays.stream(WalletRechargeInvoiceStatusEnum.values())
.filter(v -> ObjectUtil.equal(v.getDesc(), description))
.findFirst().get();
}
}
@@ -81,6 +81,16 @@ public class WalletSettingEntity extends Model<WalletSettingEntity> {
@Schema(description = "退货理由")
private String afterSaleReturnReasons;
/**
* 充值收款单位
*/
private String topupDeptStr;
/**
* 充值收款人
*/
private Long topupUserId;
/**
* 创建人
*/
@@ -0,0 +1,131 @@
package com.bsd.pjcloud.wallet.api.entity.recharge;
import com.baomidou.mybatisplus.annotation.*;
import com.baomidou.mybatisplus.extension.activerecord.Model;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;
import lombok.EqualsAndHashCode;
import com.bsd.pjcloud.common.core.util.TenantTable;
import java.time.LocalDateTime;
/**
* 充值/扣款申请发票记录
*/
@Data
@TenantTable
@TableName("wallet_recharge_invoice")
@EqualsAndHashCode(callSuper = true)
@Schema(description = "充值/扣款申请发票记录")
public class WalletRechargeInvoiceEntity extends Model<WalletRechargeInvoiceEntity> {
/**
* 主键ID
*/
@TableId(type = IdType.ASSIGN_ID)
@Schema(description = "主键ID")
private Long id;
/**
* 申请id
*/
@Schema(description = "申请id")
private Long applyId;
/**
* 发票代码(七位数)
*/
@Schema(description = "发票代码(七位数)")
private String code;
/**
* 发票日期
*/
@Schema(description = "发票日期")
private LocalDateTime time;
/**
* 交款单位或个人
*/
@Schema(description = "交款单位或个人")
private String deptOrUser;
/**
* 合计人民币
*/
@Schema(description = "合计人民币")
private Integer totalPrice;
/**
* 收款单位
*/
@Schema(description = "收款单位")
private String payeeDept;
/**
* 收款人
*/
@Schema(description = "收款人")
private String payeeUser;
/**
* 备注
*/
@Schema(description = "备注")
private String remark;
/**
* 款项json
*/
@Schema(description = "款项json")
private String itemJson;
/**
* 状态
*/
@Schema(description = "状态")
private String status;
/**
* 创建人
*/
@TableField(fill = FieldFill.INSERT)
@Schema(description = "创建人")
private String createBy;
/**
* 创建时间
*/
@TableField(fill = FieldFill.INSERT)
@Schema(description = "创建时间")
private LocalDateTime createTime;
/**
* 修改人
*/
@TableField(fill = FieldFill.INSERT_UPDATE)
@Schema(description = "修改人")
private String updateBy;
/**
* 修改时间
*/
@TableField(fill = FieldFill.INSERT_UPDATE)
@Schema(description = "修改时间")
private LocalDateTime updateTime;
/**
* 删除标记
*/
@TableLogic
@TableField(fill = FieldFill.INSERT)
@Schema(description = "删除标记")
private String delFlag;
/**
* 租户ID
*/
@Schema(description = "租户ID")
private Long tenantId;
}
@@ -0,0 +1,21 @@
package com.bsd.pjcloud.wallet.api.vo.recharge;
import lombok.Data;
/**
* 充值/扣款申请发票记录款项
*/
@Data
public class WalletRechargeInvoiceEntityItemVo {
/**
* 款项内容
*/
private String name;
/**
* 款项金额
*/
private double price;
}
@@ -0,0 +1,11 @@
package com.bsd.pjcloud.wallet.api.vo.recharge;
import com.bsd.pjcloud.wallet.api.entity.recharge.WalletRechargeInvoiceEntity;
import lombok.Data;
@Data
public class WalletRechargeInvoiceEntityVo extends WalletRechargeInvoiceEntity {
private String totalPriceCnStr;
}
@@ -54,6 +54,7 @@ public class WalletRechargeApplyController {
return R.ok(walletTransactionComposeService.pageJoin(page, dto));
}
@Operation(summary = "提交申请", description = "提交申请")
@SysLog("提交申请")
@GetMapping("/apply")
@@ -0,0 +1,89 @@
package com.bsd.pjcloud.wallet.controller.recharge;
import cn.hutool.core.util.ArrayUtil;
import cn.hutool.core.collection.CollUtil;
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.log.annotation.SysLog;
import com.bsd.pjcloud.wallet.api.entity.recharge.WalletRechargeInvoiceEntity;
import com.bsd.pjcloud.wallet.api.vo.recharge.WalletRechargeInvoiceEntityVo;
import com.bsd.pjcloud.wallet.service.WalletRechargeInvoiceService;
import org.springframework.security.access.prepost.PreAuthorize;
import com.bsd.pjcloud.common.excel.annotation.ResponseExcel;
import io.swagger.v3.oas.annotations.security.SecurityRequirement;
import org.springdoc.core.annotations.ParameterObject;
import org.springframework.http.HttpHeaders;
import io.swagger.v3.oas.annotations.tags.Tag;
import io.swagger.v3.oas.annotations.Operation;
import lombok.RequiredArgsConstructor;
import org.springframework.web.bind.annotation.*;
import java.util.List;
import java.util.Objects;
/**
* 充值/扣款申请发票记录
*/
@RestController
@RequiredArgsConstructor
@RequestMapping("/walletRechargeInvoice")
@Tag(description = "walletRechargeInvoice", name = "充值/扣款申请发票记录管理")
@SecurityRequirement(name = HttpHeaders.AUTHORIZATION)
public class WalletRechargeInvoiceController {
private final WalletRechargeInvoiceService walletRechargeInvoiceService;
@GetMapping("/get-invoice")
@Operation(summary = "批量充值/扣款发票信息")
public R<WalletRechargeInvoiceEntityVo> getInvoice(@RequestParam Long id) {
return R.ok(walletRechargeInvoiceService.getInvoice(id));
}
@Operation(summary = "分页查询", description = "分页查询")
@GetMapping("/page")
@PreAuthorize("@pms.hasPermission('wallet_walletRechargeInvoice_view')")
public R getWalletRechargeInvoicePage(@ParameterObject Page page, @ParameterObject WalletRechargeInvoiceEntity walletRechargeInvoice) {
LambdaQueryWrapper<WalletRechargeInvoiceEntity> wrapper = Wrappers.lambdaQuery();
return R.ok(walletRechargeInvoiceService.page(page, wrapper));
}
@Operation(summary = "通过id查询", description = "通过id查询")
@GetMapping("/{id}")
@PreAuthorize("@pms.hasPermission('wallet_walletRechargeInvoice_view')")
public R getById(@PathVariable("id") Long id) {
return R.ok(walletRechargeInvoiceService.getById(id));
}
@Operation(summary = "新增充值/扣款申请发票记录", description = "新增充值/扣款申请发票记录")
@SysLog("新增充值/扣款申请发票记录")
@PostMapping
@PreAuthorize("@pms.hasPermission('wallet_walletRechargeInvoice_add')")
public R save(@RequestBody WalletRechargeInvoiceEntity walletRechargeInvoice) {
return R.ok(walletRechargeInvoiceService.save(walletRechargeInvoice));
}
@Operation(summary = "修改充值/扣款申请发票记录", description = "修改充值/扣款申请发票记录")
@SysLog("修改充值/扣款申请发票记录")
@PutMapping
@PreAuthorize("@pms.hasPermission('wallet_walletRechargeInvoice_edit')")
public R updateById(@RequestBody WalletRechargeInvoiceEntity walletRechargeInvoice) {
return R.ok(walletRechargeInvoiceService.updateById(walletRechargeInvoice));
}
@Operation(summary = "通过id删除充值/扣款申请发票记录", description = "通过id删除充值/扣款申请发票记录")
@SysLog("通过id删除充值/扣款申请发票记录")
@DeleteMapping
@PreAuthorize("@pms.hasPermission('wallet_walletRechargeInvoice_del')")
public R removeById(@RequestBody Long[] ids) {
return R.ok(walletRechargeInvoiceService.removeBatchByIds(CollUtil.toList(ids)));
}
@ResponseExcel
@GetMapping("/export")
@PreAuthorize("@pms.hasPermission('wallet_walletRechargeInvoice_export')")
public List<WalletRechargeInvoiceEntity> export(WalletRechargeInvoiceEntity walletRechargeInvoice, Long[] ids) {
return walletRechargeInvoiceService.list(Wrappers.lambdaQuery(walletRechargeInvoice).in(ArrayUtil.isNotEmpty(ids), WalletRechargeInvoiceEntity::getId, ids));
}
}
@@ -0,0 +1,14 @@
package com.bsd.pjcloud.wallet.mapper.recharge;
import com.bsd.pjcloud.common.data.datascope.PjcloudBaseMapper;
import com.bsd.pjcloud.wallet.api.entity.recharge.WalletRechargeInvoiceEntity;
import org.apache.ibatis.annotations.Mapper;
@Mapper
public interface WalletRechargeInvoiceMapper extends PjcloudBaseMapper<WalletRechargeInvoiceEntity> {
/**
* 查询所有数量包括删除
*/
Long selectAllCount();
}
@@ -7,5 +7,4 @@ import com.bsd.pjcloud.wallet.api.vo.recharge.WalletRechargeApplyCompareAceVo;
public interface WalletRechargeApplyComposeService {
WalletRechargeApplyCompareAceVo pageJoin(Page page, WalletRechargeApplyDto dto);
}
@@ -0,0 +1,18 @@
package com.bsd.pjcloud.wallet.service;
import com.baomidou.mybatisplus.extension.service.IService;
import com.bsd.pjcloud.wallet.api.entity.recharge.WalletRechargeInvoiceEntity;
import com.bsd.pjcloud.wallet.api.vo.recharge.WalletRechargeInvoiceEntityVo;
public interface WalletRechargeInvoiceService extends IService<WalletRechargeInvoiceEntity> {
/**
* 批量充值/扣款发票信息
*/
WalletRechargeInvoiceEntityVo getInvoice(Long id);
/**
* 获取发票代码
*/
String getInvoiceCode();
}
@@ -39,7 +39,6 @@ import com.bsd.pjcloud.wallet.api.dto.WalletTypeDto;
import com.bsd.pjcloud.wallet.api.dto.recharge.WalletRechargeApplyDto;
import com.bsd.pjcloud.wallet.api.dto.recharge.WalletRechargeImportDto;
import com.bsd.pjcloud.wallet.api.dto.recharge.excel.WalletRechargeExcelDto;
import com.bsd.pjcloud.wallet.api.entity.WalletFreezeEntity;
import com.bsd.pjcloud.wallet.api.entity.WalletManageEntity;
import com.bsd.pjcloud.wallet.api.entity.WalletTypeEntity;
import com.bsd.pjcloud.wallet.api.entity.recharge.WalletRechargeApplyEntity;
@@ -124,6 +123,7 @@ public class WalletRechargeApplyServiceImpl extends ServiceImpl<WalletRechargeAp
return true;
}
/**
* 通过id删除充值/扣款申请
*/
@@ -0,0 +1,112 @@
package com.bsd.pjcloud.wallet.service.impl.recharge;
import cn.hutool.core.date.DatePattern;
import cn.hutool.core.date.LocalDateTimeUtil;
import cn.hutool.core.util.ObjectUtil;
import cn.hutool.json.JSONUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.bsd.pjcloud.admin.api.dto.UserInfo;
import com.bsd.pjcloud.admin.api.feign.RemoteUserService;
import com.bsd.pjcloud.flow.task.constant.TaskCheckStatusEnum;
import com.bsd.pjcloud.wallet.api.constant.WalletRechargeInvoiceStatusEnum;
import com.bsd.pjcloud.wallet.api.entity.recharge.WalletRechargeApplyEntity;
import com.bsd.pjcloud.wallet.api.entity.recharge.WalletRechargeImportEntity;
import com.bsd.pjcloud.wallet.api.entity.recharge.WalletRechargeInvoiceEntity;
import com.bsd.pjcloud.wallet.api.feign.RemoteWalletSettingService;
import com.bsd.pjcloud.wallet.api.vo.WalletSettingVo;
import com.bsd.pjcloud.wallet.api.vo.recharge.WalletRechargeInvoiceEntityItemVo;
import com.bsd.pjcloud.wallet.api.vo.recharge.WalletRechargeInvoiceEntityVo;
import com.bsd.pjcloud.wallet.mapper.recharge.WalletRechargeImportMapper;
import com.bsd.pjcloud.wallet.mapper.recharge.WalletRechargeInvoiceMapper;
import com.bsd.pjcloud.wallet.service.WalletRechargeApplyService;
import com.bsd.pjcloud.wallet.service.WalletRechargeInvoiceService;
import com.bsd.pjcloud.wallet.utils.ConvertCnPriceUtil;
import lombok.AllArgsConstructor;
import org.springframework.stereotype.Service;
import java.math.BigDecimal;
import java.util.List;
/**
* 充值/扣款申请发票记录
*/
@Service
@AllArgsConstructor
public class WalletRechargeInvoiceServiceImpl extends ServiceImpl<WalletRechargeInvoiceMapper, WalletRechargeInvoiceEntity> implements WalletRechargeInvoiceService {
private final WalletRechargeImportMapper importMapper;
private final WalletRechargeApplyService applyService;
private final RemoteUserService remoteUserService;
private final RemoteWalletSettingService remoteWalletSettingService;
/**
* 批量充值/扣款发票信息
*/
@Override
public WalletRechargeInvoiceEntityVo getInvoice(Long id) {
// 查询申请记录
WalletRechargeApplyEntity applyDetail = applyService.getById(id);
if (ObjectUtil.isEmpty(applyDetail)) {
throw new RuntimeException(" 批量充值/扣款申请不存在");
}
// 查询申请记录有没有编辑过
if (!ObjectUtil.isAllNotEmpty(applyDetail.getImportTime(), applyDetail.getWalletTypeId())) {
throw new RuntimeException("请先编辑导入时间等信息");
}
// 只有申请中才能获取发票
if (ObjectUtil.notEqual(applyDetail.getProcessStatus(), TaskCheckStatusEnum.PADDING.getCode())) {
throw new RuntimeException("只有申请中才能获取发票");
}
// 获取配置
WalletSettingVo walletSetting = remoteWalletSettingService.get().getData();
// 查询申请人
UserInfo userInfo = remoteUserService.getByUserId(applyDetail.getUserId()).getData();
if (ObjectUtil.isEmpty(userInfo)) {
throw new RuntimeException("申请用户不存在");
}
// 查询收款人
String payeeUser = "";
if (ObjectUtil.isNotEmpty(walletSetting.getTopupUserId())) {
UserInfo payeeUserDetail = remoteUserService.getByUserId(walletSetting.getTopupUserId()).getData();
if (ObjectUtil.isNotEmpty(payeeUserDetail)) {
payeeUser = payeeUserDetail.getSysUser().getName();
}
}
// 查询总金额
List<WalletRechargeImportEntity> importList = importMapper.selectList(new LambdaQueryWrapper<WalletRechargeImportEntity>().eq(WalletRechargeImportEntity::getApplyId, id));
Integer totalPrice = importList.stream().map(WalletRechargeImportEntity::getPrice).reduce(Integer::sum).orElse(0);
// 转换为元
double price = BigDecimal.valueOf(totalPrice).divide(BigDecimal.valueOf(100)).setScale(2, BigDecimal.ROUND_HALF_UP).doubleValue();
// 生成款项
WalletRechargeInvoiceEntityItemVo item = new WalletRechargeInvoiceEntityItemVo();
item.setName(LocalDateTimeUtil.format(applyDetail.getImportTime(), DatePattern.NORM_MONTH_PATTERN));
item.setPrice(price);
WalletRechargeInvoiceEntityVo result = new WalletRechargeInvoiceEntityVo();
result.setApplyId(applyDetail.getId());
result.setCode(getInvoiceCode());
result.setTime(applyDetail.getApplyTime());
result.setDeptOrUser(userInfo.getSysUser().getName());
result.setTotalPrice(totalPrice);
result.setTotalPriceCnStr(ConvertCnPriceUtil.convert(String.valueOf(price)));
result.setPayeeDept(walletSetting.getTopupDeptStr());
result.setPayeeUser(payeeUser);
result.setStatus(WalletRechargeInvoiceStatusEnum.DEFAULT.getCode());
result.setItemJson(JSONUtil.toJsonStr(item));
result.setRemark("");
return null;
}
/**
* 获取发票代码
*/
@Override
public String getInvoiceCode() {
Long count = baseMapper.selectAllCount();
count += 1;
return String.format("%07d", count);
}
}
@@ -0,0 +1,92 @@
package com.bsd.pjcloud.wallet.utils;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
/**
* 把数字金额转换为中文的大写金额
*/
public class ConvertCnPriceUtil {
private static final Pattern AMOUNT_PATTERN = Pattern.compile("^(0|[1-9]\\d{0,11})\\.(\\d\\d)$"); // 不考虑分隔符的正确性
private static final char[] RMB_NUMS = "零壹贰叁肆伍陆柒捌玖".toCharArray();
private static final String[] UNITS = {"元", "角", "分", "整"};
private static final String[] U1 = {"", "拾", "佰", "仟"};
private static final String[] U2 = {"", "万", "亿"};
/**
* 将金额(整数部分等于或少于12位,小数部分2位)转换为中文大写形式.
*
* @param amount 金额数字
* @return 中文大写
* @throws IllegalArgumentException
*/
public static String convert(String amount) throws IllegalArgumentException {
// 去掉分隔符
amount = amount.replace(",", "");
// 验证金额正确性
if (amount.equals("0.00")) {
throw new IllegalArgumentException("金额不能为零.");
}
Matcher matcher = AMOUNT_PATTERN.matcher(amount);
if (!matcher.find()) {
throw new IllegalArgumentException("输入金额有误.");
}
String integer = matcher.group(1); // 整数部分
String fraction = matcher.group(2); // 小数部分
String result = "";
if (!integer.equals("0")) {
result += integer2rmb(integer) + UNITS[0]; // 整数部分
}
if (fraction.equals("00")) {
result += UNITS[3]; // 添加[整]
} else if (fraction.startsWith("0") && integer.equals("0")) {
result += fraction2rmb(fraction).substring(1); // 去掉分前面的[零]
} else {
result += fraction2rmb(fraction); // 小数部分
}
return result;
}
// 将金额小数部分转换为中文大写
private static String fraction2rmb(String fraction) {
char jiao = fraction.charAt(0); // 角
char fen = fraction.charAt(1); // 分
return (RMB_NUMS[jiao - '0'] + (jiao > '0' ? UNITS[1] : ""))
+ (fen > '0' ? RMB_NUMS[fen - '0'] + UNITS[2] : "");
}
// 将金额整数部分转换为中文大写
private static String integer2rmb(String integer) {
StringBuilder buffer = new StringBuilder();
// 从个位数开始转换
int i, j;
for (i = integer.length() - 1, j = 0; i >= 0; i--, j++) {
char n = integer.charAt(i);
if (n == '0') {
// 当n是0且n的右边一位不是0时,插入[零]
if (i < integer.length() - 1 && integer.charAt(i + 1) != '0') {
buffer.append(RMB_NUMS[0]);
}
// 插入[万]或者[亿]
if (j % 4 == 0) {
if (i > 0 && integer.charAt(i - 1) != '0'
|| i > 1 && integer.charAt(i - 2) != '0'
|| i > 2 && integer.charAt(i - 3) != '0') {
buffer.append(U2[j / 4]);
}
}
} else {
if (j % 4 == 0) {
buffer.append(U2[j / 4]); // 插入[万]或者[亿]
}
buffer.append(U1[j % 4]); // 插入[拾]、[佰]或[仟]
buffer.append(RMB_NUMS[n - '0']); // 插入数字
}
}
return buffer.reverse().toString();
}
}
@@ -0,0 +1,30 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.bsd.pjcloud.wallet.mapper.recharge.WalletRechargeInvoiceMapper">
<resultMap id="walletRechargeInvoiceMap"
type="com.bsd.pjcloud.wallet.api.entity.recharge.WalletRechargeInvoiceEntity">
<id property="id" column="id"/>
<result property="applyId" column="apply_id"/>
<result property="code" column="code"/>
<result property="time" column="time"/>
<result property="deptOrUser" column="dept_or_user"/>
<result property="totalPrice" column="total_price"/>
<result property="payeeDept" column="payee_dept"/>
<result property="payeeUser" column="payee_user"/>
<result property="remark" column="remark"/>
<result property="status" column="status"/>
<result property="createBy" column="create_by"/>
<result property="createTime" column="create_time"/>
<result property="updateBy" column="update_by"/>
<result property="updateTime" column="update_time"/>
<result property="delFlag" column="del_flag"/>
<result property="tenantId" column="tenant_id"/>
</resultMap>
<select id="selectAllCount" resultType="java.lang.Long">
SELECT COUNT(0)
FROM wallet_recharge_invoice
</select>
</mapper>