|
|
@@ -23,9 +23,7 @@ import javax.annotation.Resource;
|
|
|
import javax.crypto.Cipher;
|
|
|
import javax.crypto.spec.GCMParameterSpec;
|
|
|
import javax.crypto.spec.SecretKeySpec;
|
|
|
-import java.io.BufferedReader;
|
|
|
-import java.io.FileInputStream;
|
|
|
-import java.io.InputStreamReader;
|
|
|
+import java.io.*;
|
|
|
import java.nio.charset.StandardCharsets;
|
|
|
import java.security.KeyFactory;
|
|
|
import java.security.MessageDigest;
|
|
|
@@ -97,15 +95,20 @@ public class PaymentService implements PaymentServiceInterface {
|
|
|
return;
|
|
|
}
|
|
|
if (privateKeyPath != null && !privateKeyPath.isEmpty()) {
|
|
|
- try (BufferedReader reader = new BufferedReader(new InputStreamReader(
|
|
|
- new FileInputStream(privateKeyPath), StandardCharsets.UTF_8))) {
|
|
|
- String keyContent = reader.lines()
|
|
|
- .filter(line -> !line.startsWith("-----"))
|
|
|
- .collect(Collectors.joining());
|
|
|
- byte[] keyBytes = Base64.getDecoder().decode(keyContent);
|
|
|
- PKCS8EncodedKeySpec spec = new PKCS8EncodedKeySpec(keyBytes);
|
|
|
- KeyFactory kf = KeyFactory.getInstance("RSA");
|
|
|
- privateKey = kf.generatePrivate(spec);
|
|
|
+ try (InputStream is = getClass().getClassLoader().getResourceAsStream(
|
|
|
+ privateKeyPath.replace("\\", "/"))) {
|
|
|
+ if (is == null) {
|
|
|
+ throw new FileNotFoundException("私钥文件未在classpath中找到: " + privateKeyPath);
|
|
|
+ }
|
|
|
+ try (BufferedReader reader = new BufferedReader(new InputStreamReader(is, StandardCharsets.UTF_8))) {
|
|
|
+ String keyContent = reader.lines()
|
|
|
+ .filter(line -> !line.startsWith("-----"))
|
|
|
+ .collect(Collectors.joining());
|
|
|
+ byte[] keyBytes = Base64.getDecoder().decode(keyContent);
|
|
|
+ PKCS8EncodedKeySpec spec = new PKCS8EncodedKeySpec(keyBytes);
|
|
|
+ KeyFactory kf = KeyFactory.getInstance("RSA");
|
|
|
+ privateKey = kf.generatePrivate(spec);
|
|
|
+ }
|
|
|
} catch (Exception e) {
|
|
|
log.error("加载微信支付私钥失败: {}", e.getMessage());
|
|
|
}
|
|
|
@@ -114,7 +117,7 @@ public class PaymentService implements PaymentServiceInterface {
|
|
|
|
|
|
@Override
|
|
|
public Map<String, Object> createWechatPayOrder(String orderNo, String description, Integer amount) {
|
|
|
- return createWechatPrepay(orderNo, description, amount);
|
|
|
+ return createWechatPrepay(orderNo, description, amount, "");
|
|
|
}
|
|
|
|
|
|
@Override
|
|
|
@@ -161,7 +164,7 @@ public class PaymentService implements PaymentServiceInterface {
|
|
|
return true;
|
|
|
}
|
|
|
|
|
|
- public Map<String, Object> createWechatPrepay(String orderNo, String description, Integer totalFee) {
|
|
|
+ public Map<String, Object> createWechatPrepay(String orderNo, String description, Integer totalFee, String openid) {
|
|
|
try {
|
|
|
JSONObject body = new JSONObject();
|
|
|
body.put("appid", appid);
|
|
|
@@ -170,6 +173,10 @@ public class PaymentService implements PaymentServiceInterface {
|
|
|
body.put("out_trade_no", orderNo);
|
|
|
body.put("notify_url", notifyUrl);
|
|
|
|
|
|
+ JSONObject payer = new JSONObject();
|
|
|
+ payer.put("openid", openid);
|
|
|
+ body.put("payer", payer);
|
|
|
+
|
|
|
JSONObject amount = new JSONObject();
|
|
|
amount.put("total", totalFee);
|
|
|
amount.put("currency", "CNY");
|
|
|
@@ -317,6 +324,10 @@ public class PaymentService implements PaymentServiceInterface {
|
|
|
}
|
|
|
|
|
|
private String doGet(String path) throws Exception {
|
|
|
+ if (testMode) {
|
|
|
+ log.info("【测试模式】跳过微信API请求: GET {}", path);
|
|
|
+ return "{\"code\":\"TEST\",\"message\":\"mock\"}";
|
|
|
+ }
|
|
|
String url = WECHAT_API_BASE + path;
|
|
|
String auth = buildAuthHeader("GET", path, "");
|
|
|
|
|
|
@@ -338,6 +349,10 @@ public class PaymentService implements PaymentServiceInterface {
|
|
|
}
|
|
|
|
|
|
private String doPost(String path, String body) throws Exception {
|
|
|
+ if (testMode) {
|
|
|
+ log.info("【测试模式】跳过微信API请求: POST {}", path);
|
|
|
+ return "{\"code\":\"TEST\",\"message\":\"mock\",\"prepay_id\":\"mock_prepay_id_" + System.currentTimeMillis() + "\"}";
|
|
|
+ }
|
|
|
String url = WECHAT_API_BASE + path;
|
|
|
String auth = buildAuthHeader("POST", path, body);
|
|
|
|