Sfoglia il codice sorgente

feat : SDK代码修改

bilingfeng 1 anno fa
parent
commit
a3ebac5921

+ 6 - 1
game-module/game-mybatis/src/main/java/com/zanxiang/mybatis/entity/User.java

@@ -64,10 +64,15 @@ public class User {
     private String mobile;
     private String mobile;
 
 
     /**
     /**
-     * 微信小游戏用户openId
+     * 微信用户openId
      */
      */
     private String openId;
     private String openId;
 
 
+    /**
+     * 微信用户会话密钥
+     */
+    private String sessionKey;
+
     /**
     /**
      * 绑定支付宝账号
      * 绑定支付宝账号
      */
      */

+ 19 - 16
game-module/game-sdk/src/main/java/com/zanxiang/sdk/service/api/WxApiService.java

@@ -42,14 +42,17 @@ public class WxApiService {
      * @return {@link String}
      * @return {@link String}
      */
      */
     public String getOpenIdByType(String code, String appId, String secret, Integer type) {
     public String getOpenIdByType(String code, String appId, String secret, Integer type) {
+        Map<String, String> resultMap = null;
         if (Objects.equals(type, PayApplicationTypeEnum.WX_MINI_APP.getType())) {
         if (Objects.equals(type, PayApplicationTypeEnum.WX_MINI_APP.getType())) {
-            return this.getAppletOpenId(code, appId, secret);
+            resultMap = this.getAppletOpenId(code, appId, secret);
         }
         }
         if (Objects.equals(type, PayApplicationTypeEnum.WX_MP.getType())) {
         if (Objects.equals(type, PayApplicationTypeEnum.WX_MP.getType())) {
-            return this.getMpOpenId(code, appId, secret);
+            resultMap = this.getMpOpenId(code, appId, secret);
         }
         }
-        log.error("应用类型不存在, 获取应用openId失败");
-        throw new BaseException("应用类型不存在, 获取应用openId失败");
+        if (resultMap != null && resultMap.containsKey("openid")) {
+            return resultMap.get("openid");
+        }
+        return null;
     }
     }
 
 
     /**
     /**
@@ -60,7 +63,7 @@ public class WxApiService {
      * @param secret : 应用密钥
      * @param secret : 应用密钥
      * @return {@link String}
      * @return {@link String}
      */
      */
-    public String getAppletOpenId(String code, String appId, String secret) {
+    public Map<String, String> getAppletOpenId(String code, String appId, String secret) {
         // 请求微信服务器,使用code获取openid
         // 请求微信服务器,使用code获取openid
         Map<String, String> paramMap = new HashMap<>(4);
         Map<String, String> paramMap = new HashMap<>(4);
         paramMap.put("appid", appId);
         paramMap.put("appid", appId);
@@ -71,11 +74,11 @@ public class WxApiService {
         String url = URIUtil.fillUrlParams("https://api.weixin.qq.com/sns/jscode2session", paramMap, Boolean.FALSE);
         String url = URIUtil.fillUrlParams("https://api.weixin.qq.com/sns/jscode2session", paramMap, Boolean.FALSE);
         String sr = restTemplate.getForObject(url, String.class);
         String sr = restTemplate.getForObject(url, String.class);
         // 解析相应内容(转换成json对象)
         // 解析相应内容(转换成json对象)
-        Map<String, String> userMap = JsonUtil.toMap(sr, Map.class, String.class);
-        if (userMap == null || Strings.isBlank(userMap.get("openid"))) {
+        Map<String, String> resultMap = JsonUtil.toMap(sr, Map.class, String.class);
+        if (resultMap == null || Strings.isBlank(resultMap.get("openid"))) {
             throw new BaseException("获取用户小程序/小游戏openId失败");
             throw new BaseException("获取用户小程序/小游戏openId失败");
         }
         }
-        return userMap.get("openid");
+        return resultMap;
     }
     }
 
 
     /**
     /**
@@ -86,7 +89,7 @@ public class WxApiService {
      * @param secret : 应用密钥
      * @param secret : 应用密钥
      * @return {@link String}
      * @return {@link String}
      */
      */
-    public String getMpOpenId(String code, String appId, String secret) {
+    private Map<String, String> getMpOpenId(String code, String appId, String secret) {
         // 请求微信服务器,使用code获取openid
         // 请求微信服务器,使用code获取openid
         Map<String, String> paramMap = new HashMap<>(4);
         Map<String, String> paramMap = new HashMap<>(4);
         paramMap.put("appid", appId);
         paramMap.put("appid", appId);
@@ -97,11 +100,11 @@ public class WxApiService {
         String url = URIUtil.fillUrlParams("https://api.weixin.qq.com/sns/oauth2/access_token", paramMap, Boolean.FALSE);
         String url = URIUtil.fillUrlParams("https://api.weixin.qq.com/sns/oauth2/access_token", paramMap, Boolean.FALSE);
         String sr = restTemplate.getForObject(url, String.class);
         String sr = restTemplate.getForObject(url, String.class);
         // 解析相应内容(转换成json对象)
         // 解析相应内容(转换成json对象)
-        Map<String, String> userMap = JsonUtil.toMap(sr, Map.class, String.class);
-        if (userMap == null || Strings.isBlank(userMap.get("openid"))) {
+        Map<String, String> resultMap = JsonUtil.toMap(sr, Map.class, String.class);
+        if (resultMap == null || Strings.isBlank(resultMap.get("openid"))) {
             throw new BaseException("获取用户公众号openId失败");
             throw new BaseException("获取用户公众号openId失败");
         }
         }
-        return userMap.get("openid");
+        return resultMap;
     }
     }
 
 
     /**
     /**
@@ -125,11 +128,11 @@ public class WxApiService {
         String url = URIUtil.fillUrlParams("https://api.weixin.qq.com/cgi-bin/token", paramMap, Boolean.FALSE);
         String url = URIUtil.fillUrlParams("https://api.weixin.qq.com/cgi-bin/token", paramMap, Boolean.FALSE);
         String sr = restTemplate.getForObject(url, String.class);
         String sr = restTemplate.getForObject(url, String.class);
         // 解析相应内容(转换成json对象)
         // 解析相应内容(转换成json对象)
-        Map<String, String> userMap = JsonUtil.toMap(sr, Map.class, String.class);
-        if (userMap == null || Strings.isBlank(userMap.get("access_token"))) {
+        Map<String, String> resultMap = JsonUtil.toMap(sr, Map.class, String.class);
+        if (resultMap == null || Strings.isBlank(resultMap.get("access_token"))) {
             throw new BaseException("获取应用token失败");
             throw new BaseException("获取应用token失败");
         }
         }
-        redisUtil.setCache(key, userMap.get("access_token"), ExpireTimeEnum.ONE_HOUR.getTime());
-        return userMap.get("access_token");
+        redisUtil.setCache(key, resultMap.get("access_token"), ExpireTimeEnum.ONE_HOUR.getTime());
+        return resultMap.get("access_token");
     }
     }
 }
 }

+ 4 - 9
game-module/game-sdk/src/main/java/com/zanxiang/sdk/service/impl/LoginServiceImpl.java

@@ -119,22 +119,16 @@ public class LoginServiceImpl implements IRegisterLoginService {
     @Override
     @Override
     @Transactional(rollbackFor = Exception.class)
     @Transactional(rollbackFor = Exception.class)
     public ResultVO<UserLoginVO> loginWxCode(LoginVxCodeParam param, UserData userData) {
     public ResultVO<UserLoginVO> loginWxCode(LoginVxCodeParam param, UserData userData) {
-
-        log.error("param : {}, userData : {}", JsonUtil.toString(param), JsonUtil.toString(userData));
-
         //验证登录ip是否封禁
         //验证登录ip是否封禁
         if (ipBanService.checkIpBan(userData.getIp())) {
         if (ipBanService.checkIpBan(userData.getIp())) {
             return ResultVO.fail(HttpStatusEnum.IP_HALT.getMsg());
             return ResultVO.fail(HttpStatusEnum.IP_HALT.getMsg());
         }
         }
         //查询微信小游戏信息
         //查询微信小游戏信息
         GameAppletDTO gameAppletDTO = gameAppletService.getByGameId(userData.getGameId());
         GameAppletDTO gameAppletDTO = gameAppletService.getByGameId(userData.getGameId());
-
-
-        log.error("gameAppletDTO : {}", JsonUtil.toString(gameAppletDTO));
-
-
         //获取用户微信小游戏的openId
         //获取用户微信小游戏的openId
-        String openId = wxApiService.getAppletOpenId(param.getCode(), gameAppletDTO.getAppId(), gameAppletDTO.getAppSecret());
+        Map<String, String> resultMap = wxApiService.getAppletOpenId(param.getCode(), gameAppletDTO.getAppId(), gameAppletDTO.getAppSecret());
+        String openId = resultMap.get("openid");
+        String sessionKey = resultMap.get("session_key");
         //根据openId查询用户
         //根据openId查询用户
         User user = userService.getOne(new LambdaQueryWrapper<User>()
         User user = userService.getOne(new LambdaQueryWrapper<User>()
                 .eq(User::getGameId, userData.getGameId()).eq(User::getOpenId, openId));
                 .eq(User::getGameId, userData.getGameId()).eq(User::getOpenId, openId));
@@ -164,6 +158,7 @@ public class LoginServiceImpl implements IRegisterLoginService {
                 .username(openId)
                 .username(openId)
                 .nickname(RegisterUtil.randomNickName(openId))
                 .nickname(RegisterUtil.randomNickName(openId))
                 .openId(openId)
                 .openId(openId)
+                .sessionKey(sessionKey)
                 .deviceType(userData.getDeviceType())
                 .deviceType(userData.getDeviceType())
                 .status(BanStatusEnum.NORMAL_STATUS.getStatus())
                 .status(BanStatusEnum.NORMAL_STATUS.getStatus())
                 .authentication(0)
                 .authentication(0)

+ 1 - 1
game-module/game-sdk/src/main/java/com/zanxiang/sdk/service/impl/PayApplicationServiceImpl.java

@@ -111,7 +111,7 @@ public class PayApplicationServiceImpl extends ServiceImpl<PayApplicationMapper,
         //下单参数
         //下单参数
         Map<String, String> payConfigMap = JsonUtil.toMap(payMerchantDTO.getPayConfig(), Map.class, String.class);
         Map<String, String> payConfigMap = JsonUtil.toMap(payMerchantDTO.getPayConfig(), Map.class, String.class);
         //获取用户openId
         //获取用户openId
-        String openId = wxApiService.getAppletOpenId(payParam.getCode(), payApplication.getAppId(), payApplication.getAppSecret());
+        String openId = wxApiService.getOpenIdByType(payParam.getCode(), payApplication.getAppId(), payApplication.getAppSecret(), payApplication.getType());
         //订单id
         //订单id
         String orderId = this.getOrderNum(openId);
         String orderId = this.getOrderNum(openId);
         try {
         try {

+ 124 - 0
game-module/game-sdk/src/main/java/com/zanxiang/sdk/service/pay/MiPay2Service.java

@@ -0,0 +1,124 @@
+package com.zanxiang.sdk.service.pay;
+
+import com.zanxiang.common.exception.BaseException;
+import com.zanxiang.common.utils.URIUtil;
+import com.zanxiang.module.util.JsonUtil;
+import lombok.extern.slf4j.Slf4j;
+import org.apache.logging.log4j.util.Strings;
+import org.springframework.stereotype.Service;
+import org.springframework.web.client.RestTemplate;
+
+import javax.crypto.Mac;
+import javax.crypto.spec.SecretKeySpec;
+import java.nio.charset.StandardCharsets;
+import java.security.InvalidKeyException;
+import java.security.NoSuchAlgorithmException;
+import java.util.HashMap;
+import java.util.Map;
+
+/**
+ * @author : lingfeng
+ * @time : 2023-05-26
+ * @description : 米大师支付2.0
+ */
+@Slf4j
+@Service
+public class MiPay2Service {
+
+    public static void main(String[] args) throws NoSuchAlgorithmException, InvalidKeyException{
+        String appId = "wx79b493916563c377";
+        String secret = "e5b1825a288ea5b54b724c64cc57e5a4";
+        String miPayAppId = "1450050301";
+        String miPaySecret = "OkjSkPgCzPoRa6KMWxXdDjH4mnceJAdU";
+        String openId = "oA-YO5YY2VVhwuSGst1gHfDBGo6s";
+
+        Map<String, Object> postBodyMap = new HashMap<>();
+        postBodyMap.put("offer_id", miPayAppId);
+        postBodyMap.put("openid", openId);
+        postBodyMap.put("ts", System.currentTimeMillis() / 1000);
+        postBodyMap.put("zone_id", "1");
+        postBodyMap.put("env", 1);
+
+        String postBody = JsonUtil.toString(postBodyMap);
+
+        //接口token
+        String accessToken = getAccessToken(appId, secret);
+
+        //登录签名
+        String signature = calcSignature(postBody, accessToken);
+
+        //支付签名
+        String paySig = calcPaySig("/wxa/game/getbalance", postBody, miPaySecret);
+
+
+        Map<String, String> headParamMap = new HashMap<>();
+        headParamMap.put("access_token", accessToken);
+        headParamMap.put("signature", signature);
+        headParamMap.put("pay_sig", paySig);
+
+
+        //调用接口获取余额
+        RestTemplate restTemplate = new RestTemplate();
+
+        String url = URIUtil.fillUrlParams("https://api.weixin.qq.com/wxa/game/getbalance", headParamMap, Boolean.FALSE);
+
+
+        String result = restTemplate.postForObject(url, postBody, String.class);
+
+        System.out.println("result -----> " + result);
+
+    }
+
+    public static String calcPaySig(String uri, String postBody, String appKey) throws NoSuchAlgorithmException, InvalidKeyException {
+        String needSignMsg = uri + "&" + postBody;
+        Mac hmacSha256 = Mac.getInstance("HmacSHA256");
+        SecretKeySpec secretKey = new SecretKeySpec(appKey.getBytes(StandardCharsets.UTF_8), "HmacSHA256");
+        hmacSha256.init(secretKey);
+        byte[] signatureBytes = hmacSha256.doFinal(needSignMsg.getBytes(StandardCharsets.UTF_8));
+        return bytesToHex(signatureBytes);
+    }
+
+    public static String calcSignature(String postBody, String sessionKey) throws NoSuchAlgorithmException, InvalidKeyException {
+        Mac hmacSha256 = Mac.getInstance("HmacSHA256");
+        SecretKeySpec secretKey = new SecretKeySpec(sessionKey.getBytes(StandardCharsets.UTF_8), "HmacSHA256");
+        hmacSha256.init(secretKey);
+        byte[] signatureBytes = hmacSha256.doFinal(postBody.getBytes(StandardCharsets.UTF_8));
+        return bytesToHex(signatureBytes);
+    }
+
+    private static String bytesToHex(byte[] bytes) {
+        StringBuilder hexString = new StringBuilder();
+        for (byte b : bytes) {
+            String hex = Integer.toHexString(0xff & b);
+            if (hex.length() == 1) {
+                hexString.append('0');
+            }
+            hexString.append(hex);
+        }
+        return hexString.toString();
+    }
+
+    /**
+     * 获取访问令牌
+     *
+     * @param appId  应用程序id
+     * @param secret 秘密
+     * @return {@link String}
+     */
+    public static String getAccessToken(String appId, String secret) {
+        Map<String, String> paramMap = new HashMap<>(4);
+        paramMap.put("appid", appId);
+        paramMap.put("secret", secret);
+        paramMap.put("grant_type", "client_credential");
+        // 发送请求
+        String url = URIUtil.fillUrlParams("https://api.weixin.qq.com/cgi-bin/token", paramMap, Boolean.FALSE);
+        RestTemplate restTemplate = new RestTemplate();
+        String sr = restTemplate.getForObject(url, String.class);
+        // 解析相应内容(转换成json对象)
+        Map<String, String> userMap = JsonUtil.toMap(sr, Map.class, String.class);
+        if (userMap == null || Strings.isBlank(userMap.get("access_token"))) {
+            throw new BaseException("获取应用token失败");
+        }
+        return userMap.get("access_token");
+    }
+}

+ 57 - 0
game-module/game-sdk/src/main/java/com/zanxiang/sdk/service/pay/TestService.java

@@ -0,0 +1,57 @@
+package com.zanxiang.sdk.service.pay;
+
+import javax.crypto.Mac;
+import javax.crypto.spec.SecretKeySpec;
+import java.nio.charset.StandardCharsets;
+import java.security.InvalidKeyException;
+import java.security.NoSuchAlgorithmException;
+
+/**
+ * @author : lingfeng
+ * @time : 2023-05-26
+ * @description :
+ */
+public class TestService {
+
+    public static String calcPaySig(String uri, String postBody, String appKey) throws NoSuchAlgorithmException, InvalidKeyException {
+        String needSignMsg = uri + "&" + postBody;
+        Mac hmacSha256 = Mac.getInstance("HmacSHA256");
+        SecretKeySpec secretKey = new SecretKeySpec(appKey.getBytes(StandardCharsets.UTF_8), "HmacSHA256");
+        hmacSha256.init(secretKey);
+        byte[] signatureBytes = hmacSha256.doFinal(needSignMsg.getBytes(StandardCharsets.UTF_8));
+        return bytesToHex(signatureBytes);
+    }
+
+    public static String calcSignature(String postBody, String sessionKey) throws NoSuchAlgorithmException, InvalidKeyException {
+        Mac hmacSha256 = Mac.getInstance("HmacSHA256");
+        SecretKeySpec secretKey = new SecretKeySpec(sessionKey.getBytes(StandardCharsets.UTF_8), "HmacSHA256");
+        hmacSha256.init(secretKey);
+        byte[] signatureBytes = hmacSha256.doFinal(postBody.getBytes(StandardCharsets.UTF_8));
+        return bytesToHex(signatureBytes);
+    }
+
+    private static String bytesToHex(byte[] bytes) {
+        StringBuilder hexString = new StringBuilder();
+        for (byte b : bytes) {
+            String hex = Integer.toHexString(0xff & b);
+            if (hex.length() == 1) {
+                hexString.append('0');
+            }
+            hexString.append(hex);
+        }
+        return hexString.toString();
+    }
+
+    public static void main(String[] args) throws NoSuchAlgorithmException, InvalidKeyException {
+        String uri = "/wxa/game/getbalance";
+        String appKey = "12345";
+        String postBody = "{\"offer_id\": \"12345678\", \"openid\": \"oUrsfxxxxxxxxxx\", \"ts\": 1668136271, \"zone_id\": \"1\", \"env\": 0}";
+
+        String paySig = calcPaySig(uri, postBody, appKey);
+        System.out.println("pay_sig: " + paySig);
+
+        String sessionKey = "9hAb/NEYUlkaMBEsmFgzig==";
+        String signature = calcSignature(postBody, sessionKey);
+        System.out.println("signature: " + signature);
+    }
+}