|
|
@@ -1,8 +1,13 @@
|
|
|
package modules.deposit;
|
|
|
|
|
|
+import com.alibaba.fastjson.JSON;
|
|
|
import com.jfinal.plugin.activerecord.Db;
|
|
|
+import com.jfinal.plugin.activerecord.Record;
|
|
|
import common.model.Deposit;
|
|
|
+import common.model.User;
|
|
|
+import common.model.BalanceLog;
|
|
|
import common.utils.http.MyRet;
|
|
|
+import common.utils.tl.AllinpaySDK;
|
|
|
|
|
|
import java.util.ArrayList;
|
|
|
import java.util.HashMap;
|
|
|
@@ -13,45 +18,228 @@ public class DepositService {
|
|
|
public String hello() {
|
|
|
return "Hello deposit";
|
|
|
}
|
|
|
-
|
|
|
- // public MyRet createDepositOrder(Integer amount, String ip, long userId) {
|
|
|
- // String notifyUrl = System.getenv("URL_BASE") + "/deposit/deposited";
|
|
|
- // String outTradeNo = "DLTBH_WX_" + System.currentTimeMillis() + "_" + userId;
|
|
|
- //
|
|
|
- // // 场景信息
|
|
|
- // H5Info h5Info = new H5Info();
|
|
|
- // h5Info.setType("Wrp"); // 使用H5支付的场景:Wap、iOS、Android
|
|
|
- //
|
|
|
- // SceneInfo sceneInfo = new SceneInfo();
|
|
|
- // sceneInfo.setPayerClientIp(ip);
|
|
|
- // sceneInfo.setH5Info(h5Info);
|
|
|
- //
|
|
|
- // // 方便获取报错信息
|
|
|
- // try {
|
|
|
- // // 获取微信支付订单结果
|
|
|
- // PrepayResponse response = prepay(amount, outTradeNo, notifyUrl, sceneInfo);
|
|
|
- //
|
|
|
- // // 微信支付订单创建成功,创建内部订单
|
|
|
- // Deposit deposit = new Deposit();
|
|
|
- //
|
|
|
- // // put各类参数
|
|
|
- // deposit.setUserId(userId);
|
|
|
- // deposit.setWxOrderNo(outTradeNo);
|
|
|
- // deposit.setAmount(amount);
|
|
|
- // deposit.setCreateTime(System.currentTimeMillis());
|
|
|
- //
|
|
|
- // if (deposit.save()) {
|
|
|
- // return MyRet.ok("微信支付订单创建成功").setData(response.getH5Url());
|
|
|
- // } else {
|
|
|
- // return MyRet.fail("微信支付订单创建失败:Deposit入库失败").setData(deposit);
|
|
|
- // }
|
|
|
- // } catch (Exception e) {
|
|
|
- // return MyRet.fail("微信支付订单创建失败").setData(e.getMessage());
|
|
|
- // }
|
|
|
- // }
|
|
|
-
|
|
|
- public Deposit findDepositByWxOrderNo(String wxOrderNo) {
|
|
|
- return Deposit.dao.findFirst("SELECT * FROM t_deposit WHERE wx_order_no=?", wxOrderNo);
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 创建通联充值订单
|
|
|
+ *
|
|
|
+ * @param amount 充值金额(分)
|
|
|
+ * @param userId 用户ID
|
|
|
+ * @return 充值结果,包含支付链接和订单号
|
|
|
+ */
|
|
|
+ public MyRet createTLDepositOrder(Integer amount, Long userId) {
|
|
|
+ try {
|
|
|
+ // 生成通联订单号
|
|
|
+ String tlOrderNo = "DLTBH_TL_" + System.currentTimeMillis() + "_" + userId;
|
|
|
+
|
|
|
+ // 设置异步通知地址
|
|
|
+ String notifyUrl = System.getenv("URL_BASE") + "/deposit/tl-notify";
|
|
|
+ // 设置同步跳转地址
|
|
|
+ String returnUrl = System.getenv("URL_BASE") + "/deposit/return";
|
|
|
+
|
|
|
+ // 调用通联支付SDK生成H5支付链接
|
|
|
+ AllinpaySDK.PaymentResult payResult = AllinpaySDK.h5Pay(
|
|
|
+ amount.longValue(), // 交易金额(分)
|
|
|
+ tlOrderNo, // 商户订单号
|
|
|
+ "购买大连特别火商品", // 订单标题
|
|
|
+ (amount / 100.0) + "元", // 订单备注
|
|
|
+ notifyUrl, // 异步通知地址
|
|
|
+ returnUrl, // 同步跳转地址
|
|
|
+ "UTF-8", // 字符编码
|
|
|
+ 30, // 有效期30分钟
|
|
|
+ null, // 支付限制
|
|
|
+ null, // 真实姓名
|
|
|
+ null // 证件号
|
|
|
+ );
|
|
|
+
|
|
|
+ if (!payResult.isSuccess()) {
|
|
|
+ return MyRet.fail("通联支付订单创建失败").setData(payResult.getMessage());
|
|
|
+ }
|
|
|
+
|
|
|
+ // 创建充值记录
|
|
|
+ Deposit deposit = new Deposit();
|
|
|
+ deposit.setUserId(userId);
|
|
|
+ deposit.setTlOrderNo(tlOrderNo);
|
|
|
+ deposit.setTlPayUrl(payResult.getPayUrl());
|
|
|
+ deposit.setAmount(amount);
|
|
|
+ deposit.setTlStatus("PENDING"); // 初始状态为处理中
|
|
|
+ deposit.setDescription("通联充值订单创建");
|
|
|
+
|
|
|
+ if (deposit.save()) {
|
|
|
+ Map<String, Object> resultData = new HashMap<>();
|
|
|
+ resultData.put("tl_pay_url", payResult.getPayUrl());
|
|
|
+ resultData.put("tl_order_no", tlOrderNo);
|
|
|
+ resultData.put("amount", amount);
|
|
|
+
|
|
|
+ return MyRet.ok("通联支付订单创建成功").setData(resultData);
|
|
|
+ } else {
|
|
|
+ return MyRet.fail("通联支付订单创建失败:充值记录入库失败");
|
|
|
+ }
|
|
|
+
|
|
|
+ } catch (Exception e) {
|
|
|
+ return MyRet.fail("通联支付订单创建失败:" + e.getMessage());
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 查询通联支付状态并处理充值
|
|
|
+ *
|
|
|
+ * @param tlOrderNo 通联订单号
|
|
|
+ * @return 查询结果
|
|
|
+ */
|
|
|
+ public MyRet queryOrderStatus(String tlOrderNo) {
|
|
|
+ try {
|
|
|
+ // 根据订单号查找充值记录
|
|
|
+ Deposit deposit = findDepositByTLOrderNo(tlOrderNo);
|
|
|
+ if (deposit == null) {
|
|
|
+ return MyRet.fail("充值记录不存在");
|
|
|
+ }
|
|
|
+
|
|
|
+ // 如果已经充值成功,直接返回
|
|
|
+ if ("SUCCESS".equals(deposit.getTlStatus())) {
|
|
|
+ User user = User.dao.findById(deposit.getUserId());
|
|
|
+ Map<String, Object> resultData = new HashMap<>();
|
|
|
+ resultData.put("tl_status", "SUCCESS");
|
|
|
+ resultData.put("balance", user != null ? user.getBalance() : 0);
|
|
|
+ resultData.put("message", "订单已处理完成");
|
|
|
+
|
|
|
+ return MyRet.ok("订单已处理完成").setData(resultData);
|
|
|
+ }
|
|
|
+
|
|
|
+ // 调用通联查单接口
|
|
|
+ AllinpaySDK.QueryResult queryResult = AllinpaySDK.queryPayment(tlOrderNo);
|
|
|
+
|
|
|
+ // 保存查单结果
|
|
|
+ deposit.setTlLastQueryResult(JSON.toJSONString(queryResult));
|
|
|
+
|
|
|
+ if (!queryResult.isSuccess()) {
|
|
|
+ deposit.setTlStatus("QUERY_FAILED");
|
|
|
+ deposit.update();
|
|
|
+ return MyRet.fail("查询通联支付状态失败:" + queryResult.getMessage());
|
|
|
+ }
|
|
|
+
|
|
|
+ // 验证金额一致性
|
|
|
+ Integer queryAmount = Integer.parseInt(queryResult.getTrxamt());
|
|
|
+ if (!queryAmount.equals(deposit.getAmount())) {
|
|
|
+ deposit.setTlStatus("AMOUNT_MISMATCH");
|
|
|
+ deposit.update();
|
|
|
+ return MyRet.fail("金额校验失败:订单金额与实际支付金额不符");
|
|
|
+ }
|
|
|
+
|
|
|
+ // 根据通联返回状态处理
|
|
|
+ String tlStatus = mapTlStatus(queryResult.getTrxstatus());
|
|
|
+
|
|
|
+ if ("SUCCESS".equals(tlStatus)) {
|
|
|
+ // 支付成功,执行充值
|
|
|
+ boolean rechargeResult = addUserBalance(deposit.getUserId(), deposit.getAmount(), tlOrderNo);
|
|
|
+
|
|
|
+ if (rechargeResult) {
|
|
|
+ deposit.setTlStatus("SUCCESS");
|
|
|
+ // deposit.setTlTrxId(queryResult.getTrxid());
|
|
|
+ deposit.setDescription("通联充值成功,交易ID:" + queryResult.getTrxid());
|
|
|
+
|
|
|
+ // 获取更新后的用户余额
|
|
|
+ User user = User.dao.findById(deposit.getUserId());
|
|
|
+
|
|
|
+ Map<String, Object> resultData = new HashMap<>();
|
|
|
+ resultData.put("tl_status", "SUCCESS");
|
|
|
+ resultData.put("balance", user != null ? user.getBalance() : 0);
|
|
|
+ resultData.put("message", "充值成功");
|
|
|
+ resultData.put("trx_id", queryResult.getTrxid());
|
|
|
+
|
|
|
+ deposit.update();
|
|
|
+ return MyRet.ok("充值成功").setData(resultData);
|
|
|
+ } else {
|
|
|
+ deposit.setTlStatus("RECHARGE_FAILED");
|
|
|
+ deposit.update();
|
|
|
+ return MyRet.fail("充值失败:余额更新异常");
|
|
|
+ }
|
|
|
+ } else {
|
|
|
+ // 其他状态,更新状态并返回
|
|
|
+ deposit.setTlStatus(tlStatus);
|
|
|
+ deposit.setDescription("通联支付状态:" + tlStatus + "," + queryResult.getMessage());
|
|
|
+ deposit.update();
|
|
|
+
|
|
|
+ Map<String, Object> resultData = new HashMap<>();
|
|
|
+ resultData.put("tl_status", tlStatus);
|
|
|
+ resultData.put("message", queryResult.getMessage());
|
|
|
+
|
|
|
+ return MyRet.ok("状态更新成功").setData(resultData);
|
|
|
+ }
|
|
|
+
|
|
|
+ } catch (Exception e) {
|
|
|
+ return MyRet.fail("查询支付状态失败:" + e.getMessage());
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 根据通联订单号查找充值记录
|
|
|
+ */
|
|
|
+ public Deposit findDepositByTLOrderNo(String tlOrderNo) {
|
|
|
+ return Deposit.dao.findFirst("SELECT * FROM t_deposit WHERE tl_order_no=?", tlOrderNo);
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 用户余额充值
|
|
|
+ *
|
|
|
+ * @param userId 用户ID
|
|
|
+ * @param amount 充值金额(分)
|
|
|
+ * @param tlOrderNo 通联订单号
|
|
|
+ * @return 是否充值成功
|
|
|
+ */
|
|
|
+ public boolean addUserBalance(Long userId, Integer amount, String tlOrderNo) {
|
|
|
+ try {
|
|
|
+ return Db.tx(() -> {
|
|
|
+ // 1. 查询用户信息
|
|
|
+ User user = User.dao.findById(userId);
|
|
|
+ if (user == null) {
|
|
|
+ return false;
|
|
|
+ }
|
|
|
+
|
|
|
+ // 2. 更新用户余额
|
|
|
+ float oldBalance = user.getBalance();
|
|
|
+ user.setBalance(oldBalance + amount);
|
|
|
+ if (!user.update()) {
|
|
|
+ return false;
|
|
|
+ }
|
|
|
+
|
|
|
+ // 3. 记录余额变动日志
|
|
|
+ BalanceLog balanceLog = new BalanceLog();
|
|
|
+ balanceLog.setUserId(userId);
|
|
|
+ balanceLog.setAmount(amount); // 正数表示增加
|
|
|
+ balanceLog.setDescription("通联充值成功,订单号:" + tlOrderNo);
|
|
|
+ balanceLog.setCreateTime(System.currentTimeMillis());
|
|
|
+ balanceLog.setIsDeleted(0);
|
|
|
+
|
|
|
+ if (!balanceLog.save()) {
|
|
|
+ return false;
|
|
|
+ }
|
|
|
+
|
|
|
+ return true;
|
|
|
+ });
|
|
|
+ } catch (Exception e) {
|
|
|
+ e.printStackTrace();
|
|
|
+ return false;
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 映射通联支付状态码
|
|
|
+ *
|
|
|
+ * @param trxstatus 通联返回的状态码
|
|
|
+ * @return 标准化状态
|
|
|
+ */
|
|
|
+ private String mapTlStatus(String trxstatus) {
|
|
|
+ if ("0000".equals(trxstatus)) {
|
|
|
+ return "SUCCESS"; // 支付成功
|
|
|
+ } else if ("1001".equals(trxstatus)) {
|
|
|
+ return "FAILED"; // 支付失败
|
|
|
+ } else if ("2001".equals(trxstatus)) {
|
|
|
+ return "PENDING"; // 支付处理中
|
|
|
+ } else if ("2002".equals(trxstatus)) {
|
|
|
+ return "TIMEOUT"; // 支付超时
|
|
|
+ } else {
|
|
|
+ return "PENDING"; // 默认处理中
|
|
|
+ }
|
|
|
}
|
|
|
|
|
|
public MyRet list(int pageNumber, int pageSize, Long userId) {
|