Commit 9cbd32ff by renyizhao

保存协议

parent cc25ba7c
...@@ -91,6 +91,13 @@ ...@@ -91,6 +91,13 @@
<artifactId>computility-spring-boot-starter-biz-ip</artifactId> <artifactId>computility-spring-boot-starter-biz-ip</artifactId>
</dependency> </dependency>
<!-- 充值协议 PDF 生成:HTML 模板渲染 + Flying Saucer 转 PDF -->
<dependency>
<groupId>org.xhtmlrenderer</groupId>
<artifactId>flying-saucer-pdf</artifactId>
<version>9.5.1</version>
</dependency>
</dependencies> </dependencies>
</project> </project>
...@@ -87,4 +87,7 @@ public class MemberRechargeRespVO { ...@@ -87,4 +87,7 @@ public class MemberRechargeRespVO {
@Schema(description = "人工处理时间") @Schema(description = "人工处理时间")
private LocalDateTime manualProcessTime; private LocalDateTime manualProcessTime;
@Schema(description = "充值协议 PDF 地址")
private String agreementPdfUrl;
} }
...@@ -5,6 +5,7 @@ import com.luhu.computility.module.member.controller.admin.recharge.vo.MemberRec ...@@ -5,6 +5,7 @@ import com.luhu.computility.module.member.controller.admin.recharge.vo.MemberRec
import com.luhu.computility.module.member.controller.admin.recharge.vo.MemberRechargeRespVO; import com.luhu.computility.module.member.controller.admin.recharge.vo.MemberRechargeRespVO;
import com.luhu.computility.module.member.dal.dataobject.recharge.MemberRechargeDO; import com.luhu.computility.module.member.dal.dataobject.recharge.MemberRechargeDO;
import com.luhu.computility.module.member.service.recharge.MemberRechargeService; import com.luhu.computility.module.member.service.recharge.MemberRechargeService;
import com.luhu.computility.module.member.service.recharge.RechargeAgreementPdfService;
import com.luhu.computility.module.pay.api.wpgj.CommonWpgjPayApi; import com.luhu.computility.module.pay.api.wpgj.CommonWpgjPayApi;
import com.luhu.computility.module.pay.api.wpgj.dto.CommonWpgjCreateReqDTO; import com.luhu.computility.module.pay.api.wpgj.dto.CommonWpgjCreateReqDTO;
import com.luhu.computility.module.pay.api.wpgj.vo.CommonWpgjPayOrderSubmitRespVO; import com.luhu.computility.module.pay.api.wpgj.vo.CommonWpgjPayOrderSubmitRespVO;
...@@ -29,6 +30,7 @@ import static com.luhu.computility.framework.security.core.util.SecurityFramewor ...@@ -29,6 +30,7 @@ import static com.luhu.computility.framework.security.core.util.SecurityFramewor
public class AppRechargeController { public class AppRechargeController {
private final MemberRechargeService rechargeService; private final MemberRechargeService rechargeService;
private final RechargeAgreementPdfService agreementPdfService;
private final CommonWpgjPayApi commonWpgjPayApi; private final CommonWpgjPayApi commonWpgjPayApi;
/** /**
...@@ -47,6 +49,9 @@ public class AppRechargeController { ...@@ -47,6 +49,9 @@ public class AppRechargeController {
String transactionId = "R" + System.currentTimeMillis() + userId; String transactionId = "R" + System.currentTimeMillis() + userId;
Long rechargeId = rechargeService.createRecharge(userId, amount, quota, "wpgj", transactionId); Long rechargeId = rechargeService.createRecharge(userId, amount, quota, "wpgj", transactionId);
// 1.1 生成充值协议 PDF(失败已在内部吞掉,不影响主流程)
agreementPdfService.generateAndSavePdf(rechargeId);
// 2. 调用旺铺聚合支付 // 2. 调用旺铺聚合支付
try { try {
CommonWpgjCreateReqDTO createReqDTO = new CommonWpgjCreateReqDTO(); CommonWpgjCreateReqDTO createReqDTO = new CommonWpgjCreateReqDTO();
......
...@@ -96,4 +96,9 @@ public class MemberRechargeDO extends BaseDO { ...@@ -96,4 +96,9 @@ public class MemberRechargeDO extends BaseDO {
*/ */
private LocalDateTime manualProcessTime; private LocalDateTime manualProcessTime;
/**
* 充值协议 PDF 地址(每次充值生成一份,存对象存储)
*/
private String agreementPdfUrl;
} }
...@@ -507,6 +507,7 @@ public class MemberRechargeServiceImpl implements MemberRechargeService { ...@@ -507,6 +507,7 @@ public class MemberRechargeServiceImpl implements MemberRechargeService {
vo.setManualOperatorId(recharge.getManualOperatorId()); vo.setManualOperatorId(recharge.getManualOperatorId());
vo.setManualOperatorName(adminUser != null ? adminUser.getNickname() : null); vo.setManualOperatorName(adminUser != null ? adminUser.getNickname() : null);
vo.setManualProcessTime(recharge.getManualProcessTime()); vo.setManualProcessTime(recharge.getManualProcessTime());
vo.setAgreementPdfUrl(recharge.getAgreementPdfUrl());
return vo; return vo;
} }
......
# 中文字体
## 用途
`RechargeAgreementPdfService` 使用 Flying Saucer 把 HTML 协议模板渲染成 PDF 时,
中文字符需要指定一个支持中文的字体,否则 PDF 里中文会显示为方块 □。
## 部署说明
请将一个支持简体中文的 TTF/OTF 字体放在本目录下,命名为:
```
NotoSansSC-Regular.otf
```
推荐使用 **Noto Sans SC**(Google 开源,OFL 协议,可商用),下载地址:
- GitHub: <https://github.com/googlefonts/noto-cjk/releases>
- 找到 `NotoSansSC-Regular.otf`(约 9MB,包含完整简体中文字形)
> ⚠️ 不要上传到 git 仓库,bin 体积大;放服务器部署目录的 `resources/fonts/`
> 或将本目录加入 `.gitignore`(建议)。
## 加载逻辑
`RechargeAgreementPdfService#loadChineseFont()` 启动时会从 classpath:`/fonts/` 加载
`NotoSansSC-Regular.otf`(找不到时也接受 `NotoSansCJKsc-Regular.otf`),加载失败会
**记录 warn 日志但不会中断**,此时 PDF 中的中文字符会以方块显示(不影响主流程)。
## 备选字体
如果不想用 Noto Sans SC,也可以替换为以下任一开源字体(改对应文件名即可):
- 思源黑体(Source Han Sans / Noto Sans CJK)
- 思源宋体(Source Han Serif / Noto Serif CJK)
- 霞鹜文楷(LXGW WenKai)
- 文泉驿微米黑(WenQuanYi Micro Hei)
-- ============================================================
-- 会员充值协议 PDF:新增 agreement_pdf_url 字段
-- 适用数据库:MySQL 5.7+ / 8.0
-- 适用表: member_recharge
-- 创建时间: 2026-07-22
-- ============================================================
ALTER TABLE `member_recharge`
ADD COLUMN `agreement_pdf_url` VARCHAR(512) NULL DEFAULT NULL
COMMENT '充值协议 PDF 地址(每次充值生成一份,存对象存储)'
AFTER `remark`;
-- 验证:
-- SHOW COLUMNS FROM `member_recharge` LIKE 'agreement_pdf_url';
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or sign in to comment