From c80fdb76471251faa8d672b7db31f9632b67be5a Mon Sep 17 00:00:00 2001 From: nili Date: Sun, 19 May 2024 14:12:45 +0800 Subject: [PATCH] =?UTF-8?q?=E6=8F=90=E7=8E=B0=E7=9A=84=E4=B8=80=E5=A4=A7?= =?UTF-8?q?=E5=A0=86=E5=8A=9F=E8=83=BD?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../group/game/dao/bean/MatrixApp.java | 9 + .../game/dao/bean/MatrixMoneyRecord.java | 21 ++ .../group/game/dao/bean/MatrixUser.java | 2 +- .../dao/mapper/MatrixMoneyRecordMapper.java | 30 +++ .../game/dao/mapper/MatrixUserMapper.java | 7 + .../group/game/service/ScheduleService.java | 39 ++++ .../group/game/service/UMengService.java | 125 +++++++++++ .../group/game/service/bo/citrus/AppBo.java | 40 ++++ .../game/service/bo/citrus/CashRecord.java | 18 ++ .../game/service/bo/citrus/LoginReq.java | 1 + .../group/game/service/bo/citrus/UserBo.java | 2 + .../service/bo/matrix/AliPayConfigBo.java | 9 + .../game/service/bo/matrix/UmengConfigBo.java | 8 + .../game/service/bo/matrix/WxConfigBo.java | 6 + .../game/service/citrus/CitrusAppService.java | 18 ++ .../game/service/citrus/UserService.java | 88 ++++++++ .../pay/AlipayFundTransUniTransfer.java | 114 ++++++++++ .../group/game/ServiceTestApplication.java | 2 + .../group/game/service/UMengServiceTest.java | 18 ++ .../pay/AlipayFundTransUniTransferTest.java | 198 ++++++++++++++++++ .../game/web/filter/CitrusLoginFilter.java | 9 +- .../web/rest/citrus/CitrusAppController.java | 24 +++ .../game/web/rest/citrus/OpenController.java | 8 + .../game/web/rest/citrus/UserController.java | 27 ++- 24 files changed, 811 insertions(+), 12 deletions(-) create mode 100644 game-dao/src/main/java/awesome/group/game/dao/bean/MatrixMoneyRecord.java create mode 100644 game-dao/src/main/java/awesome/group/game/dao/mapper/MatrixMoneyRecordMapper.java create mode 100644 game-service/src/main/java/awesome/group/game/service/ScheduleService.java create mode 100644 game-service/src/main/java/awesome/group/game/service/UMengService.java create mode 100644 game-service/src/main/java/awesome/group/game/service/bo/citrus/AppBo.java create mode 100644 game-service/src/main/java/awesome/group/game/service/bo/citrus/CashRecord.java create mode 100644 game-service/src/main/java/awesome/group/game/service/bo/matrix/AliPayConfigBo.java create mode 100644 game-service/src/main/java/awesome/group/game/service/bo/matrix/UmengConfigBo.java create mode 100644 game-service/src/main/java/awesome/group/game/service/bo/matrix/WxConfigBo.java create mode 100644 game-service/src/main/java/awesome/group/game/service/citrus/CitrusAppService.java create mode 100644 game-service/src/main/java/awesome/group/game/service/pay/AlipayFundTransUniTransfer.java create mode 100644 game-service/src/test/java/awesome/group/game/service/UMengServiceTest.java create mode 100644 game-service/src/test/java/awesome/group/game/service/pay/AlipayFundTransUniTransferTest.java create mode 100644 game-web/src/main/java/awesome/group/game/web/rest/citrus/CitrusAppController.java diff --git a/game-dao/src/main/java/awesome/group/game/dao/bean/MatrixApp.java b/game-dao/src/main/java/awesome/group/game/dao/bean/MatrixApp.java index 65b5863..32cd540 100644 --- a/game-dao/src/main/java/awesome/group/game/dao/bean/MatrixApp.java +++ b/game-dao/src/main/java/awesome/group/game/dao/bean/MatrixApp.java @@ -16,4 +16,13 @@ public class MatrixApp { private String channel; private Integer hide; private String secret; + + private String umeng;//友盟的配置数据 + private String aliPay;//支付宝的配置数据 + private String wx;//微信的配置数据 + + private String moneyLadder; + private Integer noAuditMoney; + private String qqUrl; + private Integer dayLimit;//每日提现次数限制 } diff --git a/game-dao/src/main/java/awesome/group/game/dao/bean/MatrixMoneyRecord.java b/game-dao/src/main/java/awesome/group/game/dao/bean/MatrixMoneyRecord.java new file mode 100644 index 0000000..a96864f --- /dev/null +++ b/game-dao/src/main/java/awesome/group/game/dao/bean/MatrixMoneyRecord.java @@ -0,0 +1,21 @@ +package awesome.group.game.dao.bean; + +import com.baomidou.mybatisplus.annotation.IdType; +import com.baomidou.mybatisplus.annotation.TableId; +import lombok.Data; + +import java.sql.Timestamp; + +@Data +public class MatrixMoneyRecord { + @TableId(value = "id", type = IdType.AUTO) + private Integer id; + private Integer userId; + private Integer appId; + private Integer cent; + private String aliPayAccount; + private String name; + private String reason; + private Integer status;//0发起申请,1审批成功,2转账中,3转账成功,-1转账失败 + private Timestamp createdAt; +} diff --git a/game-dao/src/main/java/awesome/group/game/dao/bean/MatrixUser.java b/game-dao/src/main/java/awesome/group/game/dao/bean/MatrixUser.java index 4bddf9c..50f3bff 100644 --- a/game-dao/src/main/java/awesome/group/game/dao/bean/MatrixUser.java +++ b/game-dao/src/main/java/awesome/group/game/dao/bean/MatrixUser.java @@ -18,5 +18,5 @@ public class MatrixUser { private String pwd; private String inviteCode; private Integer upUid; - private Long income; + private Long income;//分,累计收益 } diff --git a/game-dao/src/main/java/awesome/group/game/dao/mapper/MatrixMoneyRecordMapper.java b/game-dao/src/main/java/awesome/group/game/dao/mapper/MatrixMoneyRecordMapper.java new file mode 100644 index 0000000..a7a2501 --- /dev/null +++ b/game-dao/src/main/java/awesome/group/game/dao/mapper/MatrixMoneyRecordMapper.java @@ -0,0 +1,30 @@ +package awesome.group.game.dao.mapper; + +import awesome.group.game.dao.bean.MatrixMoneyRecord; +import com.baomidou.mybatisplus.core.mapper.BaseMapper; +import org.apache.ibatis.annotations.Select; +import org.apache.ibatis.annotations.Update; + +import java.sql.Timestamp; +import java.util.List; + +public interface MatrixMoneyRecordMapper extends BaseMapper { + + @Select("select count(*) from matrix_money_record where status != -1 and user_id = #{userId} and created_at > #{timestamp}") + int queryAfter(Integer userId, Timestamp timestamp); + + @Select("select count(*) from matrix_money_record where status != -1 and ali_pay_account = #{aliPayAccount} and created_at > #{timestamp}") + int queryByAliPayAccount(String aliPayAccount, Timestamp timestamp); + + @Select("select * from matrix_money_record where status = #{status}") + List queryByStatus(Integer status); + + @Update("update matrix_money_record set status = #{status} where id = #{id} and status = #{prevStatus}") + int updateStatusWithPrev(int id, int prevStatus, int status); + + @Update("update matrix_money_record set status = #{status}, reason=#{reason} where id = #{id}") + int updateStatusAndReason(int id, int status, String reason); + + @Select("select * from matrix_money_record where user_id = #{userId}") + List queryByUserId(Integer userId); +} diff --git a/game-dao/src/main/java/awesome/group/game/dao/mapper/MatrixUserMapper.java b/game-dao/src/main/java/awesome/group/game/dao/mapper/MatrixUserMapper.java index 924e05a..2de2521 100644 --- a/game-dao/src/main/java/awesome/group/game/dao/mapper/MatrixUserMapper.java +++ b/game-dao/src/main/java/awesome/group/game/dao/mapper/MatrixUserMapper.java @@ -3,6 +3,7 @@ package awesome.group.game.dao.mapper; import awesome.group.game.dao.bean.MatrixUser; import com.baomidou.mybatisplus.core.mapper.BaseMapper; import org.apache.ibatis.annotations.Select; +import org.apache.ibatis.annotations.Update; public interface MatrixUserMapper extends BaseMapper { @@ -11,4 +12,10 @@ public interface MatrixUserMapper extends BaseMapper { @Select("select * from matrix_user where app_id = #{appId} and mobile = #{mobile}") MatrixUser selectByAppIdAndMobile(int appId, String mobile); + + @Update("update matrix_user set money = money + #{cent} where id = #{userId}") + int incMoney(int userId, int cent); + + @Update("update matrix_user set ali_pay_account = #{aliPayAccount}, name = #{name} where id = #{userId}") + int updateAliPayAccount(int userId, String aliPayAccount, String name); } diff --git a/game-service/src/main/java/awesome/group/game/service/ScheduleService.java b/game-service/src/main/java/awesome/group/game/service/ScheduleService.java new file mode 100644 index 0000000..785ca21 --- /dev/null +++ b/game-service/src/main/java/awesome/group/game/service/ScheduleService.java @@ -0,0 +1,39 @@ +package awesome.group.game.service; + +import awesome.group.game.dao.bean.MatrixMoneyRecord; +import awesome.group.game.dao.mapper.MatrixMoneyRecordMapper; +import awesome.group.game.dao.mapper.MatrixUserMapper; +import awesome.group.game.service.citrus.UserService; +import awesome.group.game.service.pay.AlipayFundTransUniTransfer; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.scheduling.annotation.Scheduled; +import org.springframework.stereotype.Service; + +import java.util.List; + +@Service +public class ScheduleService { + @Autowired + private MatrixMoneyRecordMapper moneyRecordMapper; + @Autowired + private AlipayFundTransUniTransfer aliTransfer; + + @Autowired + private MatrixUserMapper userMapper; + + @Scheduled(cron = "0 0/1 * * * ?") + public void transfer() { + List list = moneyRecordMapper.queryByStatus(UserService.STATUS_AUDIT_PASS); + for (MatrixMoneyRecord r : list) { + int rows = moneyRecordMapper.updateStatusWithPrev(r.getId(), UserService.STATUS_AUDIT_PASS, UserService.STATUS_TRANSFERRING); + if (rows < 1) { + continue; + } + boolean success = aliTransfer.transfer(r); + moneyRecordMapper.updateStatusAndReason(r.getId(), r.getStatus(), r.getReason()); + if (!success) { + userMapper.incMoney(r.getUserId(), -r.getCent()); + } + } + } +} diff --git a/game-service/src/main/java/awesome/group/game/service/UMengService.java b/game-service/src/main/java/awesome/group/game/service/UMengService.java new file mode 100644 index 0000000..0e93815 --- /dev/null +++ b/game-service/src/main/java/awesome/group/game/service/UMengService.java @@ -0,0 +1,125 @@ +package awesome.group.game.service; + +import awesome.group.game.service.common.exception.PaganiException; +import awesome.group.game.service.common.exception.PaganiExceptionCode; +import awesome.group.game.service.common.log.L; +import com.google.gson.Gson; +import okhttp3.*; +import org.apache.commons.codec.binary.Base64; +import org.apache.commons.codec.digest.DigestUtils; +import org.springframework.stereotype.Service; +import org.springframework.util.CollectionUtils; + +import javax.crypto.Mac; +import javax.crypto.spec.SecretKeySpec; +import java.io.IOException; +import java.nio.charset.StandardCharsets; +import java.security.InvalidKeyException; +import java.security.NoSuchAlgorithmException; +import java.util.HashMap; +import java.util.Map; +import java.util.Objects; +import java.util.UUID; +import java.util.concurrent.TimeUnit; + +@Service +public class UMengService { + public static final String APP_KEY = "24785365";//阿里云 + public static final String APP_SECRET = "7e3a9e8ae85cd8c1ff58343e241ec154"; + public static final String APP_CODE = "2c62d2208aa640f09a55449efa634424"; + + public static final String APP_KEY_UMENT = "66403e5dcac2a664de3234d4";//友盟 + public static final String API_PREFIX = "https://verify5.market.alicloudapi.com"; + + public static Gson gson = new Gson(); + private static final MediaType JSON = MediaType.parse("application/json; charset=utf-8"); + + private final OkHttpClient httpClient = new OkHttpClient().newBuilder().connectTimeout(2, TimeUnit.SECONDS).readTimeout(5, TimeUnit.SECONDS).connectionPool(new ConnectionPool(8, 5, TimeUnit.MINUTES)).build(); + + public String getMobile(String token) { + Map data = new HashMap<>(); + data.put("token", token); + String api = "/api/v1/mobile/info?appkey=" + APP_KEY_UMENT; + String res = doHttpPost(api, data); + System.out.println(res); + + return res; + } + + public String doHttpPost(String url, Map jsonBody) { + Map header = new HashMap<>(); + String body = gson.toJson(jsonBody); + + header.put("Content-Type", "application/json; charset=utf-8"); + header.put("Accept", "application/json"); + header.put("X-Ca-Version", "1"); + header.put("X-Ca-Signature-Headers", "X-Ca-Version,X-Ca-Stage,X-Ca-Key,X-Ca-Timestamp"); + header.put("X-Ca-Stage", "RELEASE"); + header.put("X-Ca-Key", APP_KEY); + header.put("X-Ca-Timestamp", String.valueOf(System.currentTimeMillis())); + header.put("X-Ca-Nonce", UUID.randomUUID().toString()); + header.put("Content-MD5", Base64.encodeBase64String(DigestUtils.md5(body.getBytes()))); + /** + * sign + */ + String stringToSign = getSignString(header, "POST", url); + + try { + Mac hmacSha256 = Mac.getInstance("HmacSHA256"); + byte[] keyBytes = APP_SECRET.getBytes(StandardCharsets.UTF_8); + hmacSha256.init(new SecretKeySpec(keyBytes, 0, keyBytes.length, "HmacSHA256")); + String sign = new String(Base64.encodeBase64(hmacSha256.doFinal(stringToSign.getBytes(StandardCharsets.UTF_8)))); + header.put("X-Ca-Signature", sign); + return postJson(url, jsonBody, header); + + } catch (InvalidKeyException | NoSuchAlgorithmException e) { + throw new PaganiException(PaganiExceptionCode.GENERAL_ERROR, "验证失败,请重试"); + } + } + + private static String getSignString(Map header, String method, String url) { + + return method.toUpperCase() + "\n" + + header.get("Accept") + "\n" + + header.get("Content-MD5") + "\n" + + header.get("Content-Type") + "\n\n" + + "X-Ca-Key:" + header.get("X-Ca-Key") + "\n" + + "X-Ca-Stage:" + header.get("X-Ca-Stage") + "\n" + + "X-Ca-Timestamp:" + header.get("X-Ca-Timestamp") + "\n" + + "X-Ca-Version:" + header.get("X-Ca-Version") + "\n" + + url; + } + + private String postJson(String url, Map body, Map headers) { + String bodyStr = gson.toJson(body); + RequestBody requestBody = RequestBody.create(JSON, bodyStr); + if (!url.startsWith("http")) { + url = API_PREFIX + url; + } + HttpUrl.Builder urlBuilder = HttpUrl.parse(url).newBuilder(); + Request.Builder requestBuilder = new Request.Builder().post(requestBody).url(urlBuilder.build()); + + if (!CollectionUtils.isEmpty(headers)) { + headers.forEach(requestBuilder::addHeader); + } + + Request request = requestBuilder.build(); + + String msg = "url:" + url + ",header:" + gson.toJson(headers) + ", body:" + bodyStr; + return doHttpExecute(msg, request); + } + + private String doHttpExecute(String msg, Request request) { + try (Response resp = httpClient.newCall(request).execute()) { + if (!resp.isSuccessful() || resp.body() == null) { + L.trace("request_umeng_error", msg + ",resp:" + resp); + throw new PaganiException(PaganiExceptionCode.GENERAL_ERROR, "友盟请求失败"); + } + return Objects.requireNonNull(resp.body()).string(); + } catch (IOException ioe) { + L.trace("request_umeng_error", msg, ioe); + throw new PaganiException(PaganiExceptionCode.GENERAL_ERROR, ioe.getMessage(), ioe); + } + } + +} diff --git a/game-service/src/main/java/awesome/group/game/service/bo/citrus/AppBo.java b/game-service/src/main/java/awesome/group/game/service/bo/citrus/AppBo.java new file mode 100644 index 0000000..d70a2d0 --- /dev/null +++ b/game-service/src/main/java/awesome/group/game/service/bo/citrus/AppBo.java @@ -0,0 +1,40 @@ +package awesome.group.game.service.bo.citrus; + +import awesome.group.game.dao.bean.MatrixApp; +import com.google.gson.Gson; +import com.google.gson.reflect.TypeToken; +import org.springframework.util.StringUtils; + +import java.util.Arrays; +import java.util.List; + +public class AppBo { + public List moneyLadder;//提现梯度,单位分 + public Integer noAuditMoney;//不需审核的金额,单位分 + public String qqUrl;//qq客服链接 + public Integer dayLimit;//每日提现次数 + + public AppBo() { + } + + public AppBo(MatrixApp app) { + Gson gson = new Gson(); + if (StringUtils.hasText(app.getMoneyLadder())) { + this.moneyLadder = gson.fromJson(app.getMoneyLadder(), new TypeToken>() { + }.getType()); + } else { + moneyLadder = Arrays.asList(30, 50, 100, 10000, 30000, 50000); + } + if (app.getNoAuditMoney() != null) { + this.noAuditMoney = app.getNoAuditMoney(); + } else { + this.noAuditMoney = 30; + } + this.qqUrl = app.getQqUrl(); + if (app.getDayLimit() != null) { + this.dayLimit = app.getDayLimit(); + } else { + this.dayLimit = 3; + } + } +} diff --git a/game-service/src/main/java/awesome/group/game/service/bo/citrus/CashRecord.java b/game-service/src/main/java/awesome/group/game/service/bo/citrus/CashRecord.java new file mode 100644 index 0000000..6a545e1 --- /dev/null +++ b/game-service/src/main/java/awesome/group/game/service/bo/citrus/CashRecord.java @@ -0,0 +1,18 @@ +package awesome.group.game.service.bo.citrus; + +import awesome.group.game.dao.bean.MatrixMoneyRecord; + +public class CashRecord { + public Integer cent;//提现金额,分 + public Long createTime;//提现时间,时间戳, 毫秒 + public Integer status;//0发起申请,1审批成功,2转账中,3转账成功,-1转账失败 + + public CashRecord() { + } + + public CashRecord(MatrixMoneyRecord r) { + this.cent = r.getCent(); + this.createTime = r.getCreatedAt().getTime(); + this.status = r.getStatus(); + } +} diff --git a/game-service/src/main/java/awesome/group/game/service/bo/citrus/LoginReq.java b/game-service/src/main/java/awesome/group/game/service/bo/citrus/LoginReq.java index f6c8754..5df74fa 100644 --- a/game-service/src/main/java/awesome/group/game/service/bo/citrus/LoginReq.java +++ b/game-service/src/main/java/awesome/group/game/service/bo/citrus/LoginReq.java @@ -5,5 +5,6 @@ public class LoginReq { public String pwd; public String appCode; public String code;//验证码 + public String token;//友盟token } diff --git a/game-service/src/main/java/awesome/group/game/service/bo/citrus/UserBo.java b/game-service/src/main/java/awesome/group/game/service/bo/citrus/UserBo.java index 217f059..64a12c2 100644 --- a/game-service/src/main/java/awesome/group/game/service/bo/citrus/UserBo.java +++ b/game-service/src/main/java/awesome/group/game/service/bo/citrus/UserBo.java @@ -11,6 +11,7 @@ public class UserBo { public Integer money;//分,已提现金额 public String aliPayAccount; public Long income;//ecpm和,分 + public Long goldCoin;//金币 public String inviteCode; public String inviteUrl; @@ -28,5 +29,6 @@ public class UserBo { this.nickname = u.getNickname(); this.avatar = u.getAvatar(); this.money = u.getMoney(); + this.goldCoin = u.getIncome() - (u.getMoney() * 1000); } } diff --git a/game-service/src/main/java/awesome/group/game/service/bo/matrix/AliPayConfigBo.java b/game-service/src/main/java/awesome/group/game/service/bo/matrix/AliPayConfigBo.java new file mode 100644 index 0000000..434f5b0 --- /dev/null +++ b/game-service/src/main/java/awesome/group/game/service/bo/matrix/AliPayConfigBo.java @@ -0,0 +1,9 @@ +package awesome.group.game.service.bo.matrix; + +public class AliPayConfigBo { + public String aliPayPublicCert; + public String aliPayRootCert; + public String aliPayAppCert; + public String aliPayPrivateKey; + public String aliPayAppId; +} diff --git a/game-service/src/main/java/awesome/group/game/service/bo/matrix/UmengConfigBo.java b/game-service/src/main/java/awesome/group/game/service/bo/matrix/UmengConfigBo.java new file mode 100644 index 0000000..8a300b0 --- /dev/null +++ b/game-service/src/main/java/awesome/group/game/service/bo/matrix/UmengConfigBo.java @@ -0,0 +1,8 @@ +package awesome.group.game.service.bo.matrix; + +public class UmengConfigBo { + public String umengAppKeyAli; + public String umengAppSecret; + public String umengAppCode; + public String umengAppKey; +} diff --git a/game-service/src/main/java/awesome/group/game/service/bo/matrix/WxConfigBo.java b/game-service/src/main/java/awesome/group/game/service/bo/matrix/WxConfigBo.java new file mode 100644 index 0000000..84b7ff0 --- /dev/null +++ b/game-service/src/main/java/awesome/group/game/service/bo/matrix/WxConfigBo.java @@ -0,0 +1,6 @@ +package awesome.group.game.service.bo.matrix; + +public class WxConfigBo { + public String wxAppId; + public String wxAppSecret; +} diff --git a/game-service/src/main/java/awesome/group/game/service/citrus/CitrusAppService.java b/game-service/src/main/java/awesome/group/game/service/citrus/CitrusAppService.java new file mode 100644 index 0000000..4c7adda --- /dev/null +++ b/game-service/src/main/java/awesome/group/game/service/citrus/CitrusAppService.java @@ -0,0 +1,18 @@ +package awesome.group.game.service.citrus; + +import awesome.group.game.dao.bean.MatrixApp; +import awesome.group.game.dao.mapper.MatrixAppMapper; +import awesome.group.game.service.bo.citrus.AppBo; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; + +@Service +public class CitrusAppService { + @Autowired + private MatrixAppMapper appMapper; + + public AppBo getAppDetail(String appCode) { + MatrixApp app = appMapper.queryByCode(appCode); + return new AppBo(app); + } +} diff --git a/game-service/src/main/java/awesome/group/game/service/citrus/UserService.java b/game-service/src/main/java/awesome/group/game/service/citrus/UserService.java index 50d68b6..00fd51f 100644 --- a/game-service/src/main/java/awesome/group/game/service/citrus/UserService.java +++ b/game-service/src/main/java/awesome/group/game/service/citrus/UserService.java @@ -1,20 +1,32 @@ package awesome.group.game.service.citrus; import awesome.group.game.dao.bean.MatrixApp; +import awesome.group.game.dao.bean.MatrixMoneyRecord; import awesome.group.game.dao.bean.MatrixUser; import awesome.group.game.dao.mapper.MatrixAppMapper; +import awesome.group.game.dao.mapper.MatrixMoneyRecordMapper; import awesome.group.game.dao.mapper.MatrixUserMapper; import awesome.group.game.service.SmsService; +import awesome.group.game.service.bo.citrus.AppBo; +import awesome.group.game.service.bo.citrus.CashRecord; import awesome.group.game.service.bo.citrus.LoginReq; import awesome.group.game.service.bo.citrus.UserBo; import awesome.group.game.service.common.exception.PaganiException; import awesome.group.game.service.common.exception.PaganiExceptionCode; +import awesome.group.game.service.util.DateUtil; import awesome.group.game.service.util.EncryptUtil; +import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper; +import com.baomidou.mybatisplus.core.toolkit.Wrappers; import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.context.annotation.Lazy; import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Transactional; import org.springframework.util.Assert; import org.springframework.util.StringUtils; +import java.sql.Timestamp; +import java.util.List; + @Service public class UserService { @Autowired @@ -26,6 +38,22 @@ public class UserService { @Autowired private SmsService smsService; + @Autowired + private MatrixMoneyRecordMapper moneyRecordMapper; + + @Lazy + @Autowired + private UserService userService; + + public static final int STATUS_WAITING = 0;//等审核 + + public static final int STATUS_AUDIT_PASS = 1;//已审核通过 + + public static final int STATUS_TRANSFERRING = 2;//转账中 + public static final int TRANSFER_SUCCESS = 3; + public static final int TRANSFER_FAIL = -1; + + public MatrixUser login(LoginReq req) { Assert.isTrue(req != null, "非法请求"); Assert.isTrue(StringUtils.hasText(req.mobile), "非法请求"); @@ -56,8 +84,68 @@ public class UserService { return user; } + public MatrixUser loginByToken(String appCode, String token) { + Assert.isTrue(StringUtils.hasText(appCode), "非法请求"); + Assert.isTrue(StringUtils.hasText(token), "非法请求"); + MatrixApp app = appMapper.queryByCode(appCode); + Assert.isTrue(app != null, "非法请求"); + LambdaQueryWrapper wrapper = Wrappers.lambdaQuery(); + wrapper.eq(MatrixUser::getAppId, app.getId()); + return userMapper.selectOne(wrapper); + } + public UserBo getUser(Integer uid) { MatrixUser u = userMapper.selectById(uid); return new UserBo(u); } + + public void bindAliPay(Integer uid, String name, String aliPayAccount) { + Assert.isTrue(StringUtils.hasText(aliPayAccount), "支付宝账号不能为空"); + Assert.isTrue(StringUtils.hasText(name), "支付宝账号姓名不能为空"); + MatrixUser u = userMapper.selectById(uid); + Assert.isTrue(u != null, "非法请求"); + userMapper.updateAliPayAccount(uid, aliPayAccount, name); + } + + public List getCashRecord(Integer uid) { + List list = moneyRecordMapper.queryByUserId(uid); + return list.stream().map(CashRecord::new).toList(); + } + + public void applyMoney(Integer uid, Integer cent) { + Assert.isTrue(cent >= 10, "至少提0.1元"); + MatrixUser u = userMapper.selectById(uid); + Assert.isTrue(u != null, "非法请求"); + Assert.isTrue(u.getMoney() + cent <= u.getIncome(), "余额不足"); + String aliPayAccount = u.getAliPayAccount(); + Assert.isTrue(StringUtils.hasText(aliPayAccount), "请先绑定支付宝账号"); + Assert.isTrue(StringUtils.hasText(u.getName()), "请先填写支付宝实名姓名"); + + MatrixApp app = appMapper.selectById(u.getAppId()); + AppBo appBo = new AppBo(app); + Assert.isTrue(appBo.moneyLadder.contains(cent), "提现金额不合法"); + Timestamp todayBegin = new Timestamp(DateUtil.getDayBeginTimestamp(System.currentTimeMillis())); + int size = moneyRecordMapper.queryAfter(uid, todayBegin); + Assert.isTrue(size < appBo.dayLimit, "每天最多提现" + appBo.dayLimit + "次"); + + size = moneyRecordMapper.queryByAliPayAccount(aliPayAccount, todayBegin); + Assert.isTrue(size < appBo.dayLimit, "每天最多提现" + appBo.dayLimit + "次"); + userService.doApply(u, app.getNoAuditMoney(), cent); + } + + @Transactional + public void doApply(MatrixUser u, Integer noAuditMoney, Integer cent) { + int uid = u.getId(); + MatrixMoneyRecord record = new MatrixMoneyRecord(); + record.setUserId(uid); + record.setAppId(u.getAppId()); + record.setCent(cent); + record.setAliPayAccount(u.getAliPayAccount()); + record.setName(u.getName()); + record.setStatus(cent <= noAuditMoney ? STATUS_AUDIT_PASS : STATUS_WAITING); + userMapper.incMoney(uid, cent); + u = userMapper.selectById(uid); + Assert.isTrue(u.getMoney() <= u.getIncome(), "余额不足"); + moneyRecordMapper.insert(record); + } } diff --git a/game-service/src/main/java/awesome/group/game/service/pay/AlipayFundTransUniTransfer.java b/game-service/src/main/java/awesome/group/game/service/pay/AlipayFundTransUniTransfer.java new file mode 100644 index 0000000..7f034c4 --- /dev/null +++ b/game-service/src/main/java/awesome/group/game/service/pay/AlipayFundTransUniTransfer.java @@ -0,0 +1,114 @@ +package awesome.group.game.service.pay; + +import awesome.group.game.dao.bean.MatrixApp; +import awesome.group.game.dao.bean.MatrixMoneyRecord; +import awesome.group.game.dao.mapper.MatrixAppMapper; +import awesome.group.game.service.bo.matrix.AliPayConfigBo; +import awesome.group.game.service.citrus.UserService; +import awesome.group.game.service.common.log.L; +import awesome.group.game.service.util.DateUtil; +import com.alipay.api.AlipayApiException; +import com.alipay.api.AlipayClient; +import com.alipay.api.CertAlipayRequest; +import com.alipay.api.DefaultAlipayClient; +import com.alipay.api.domain.AlipayFundTransUniTransferModel; +import com.alipay.api.domain.Participant; +import com.alipay.api.request.AlipayFundTransUniTransferRequest; +import com.alipay.api.response.AlipayFundTransUniTransferResponse; +import com.google.gson.Gson; +import jakarta.annotation.PostConstruct; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; +import org.springframework.util.StringUtils; + +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +@Service +public class AlipayFundTransUniTransfer { + + @Autowired + private MatrixAppMapper appMapper; + + private Map appPayClientMap = new HashMap<>(); + + private Gson gson = new Gson(); + + @PostConstruct + public void init() { + List appList = appMapper.selectList(null); + for (MatrixApp app : appList) { + if (StringUtils.hasText(app.getAliPay())) { + AliPayConfigBo configBo = gson.fromJson(app.getAliPay(), AliPayConfigBo.class); + CertAlipayRequest alipayConfig = getAlipayConfig(configBo); + try { + AlipayClient alipayClient = new DefaultAlipayClient(alipayConfig); + appPayClientMap.put(app.getId(), alipayClient); + } catch (AlipayApiException e) { + L.trace("initAliPayClientError", "app:" + gson.toJson(app), e); + } + } + } + } + + //文档:https://opendocs.alipay.com/open/309/106236?pathHash=97724ae4#%E8%BD%AC%E8%B4%A6%E5%92%8C%E9%80%9A%E7%9F%A5 + public boolean transfer(MatrixMoneyRecord record) { + AlipayClient alipayClient = appPayClientMap.get(record.getAppId()); + if (alipayClient == null) { + L.trace("transferError", "app:" + record.getAppId() + "提现未开启或配置错误"); + return false; + } + MatrixApp app = appMapper.selectById(record.getAppId()); + try { + AlipayFundTransUniTransferRequest request = new AlipayFundTransUniTransferRequest(); + AlipayFundTransUniTransferModel model = new AlipayFundTransUniTransferModel(); + model.setOrderTitle(app.getName() + "-提现"); + model.setBizScene("DIRECT_TRANSFER"); + model.setBusinessParams("{\"payer_show_name_use_alias\":\"true\"}"); + model.setRemark(app.getName() + "-提现"); + String orderNo = String.format("%08d", record.getId()); + model.setOutBizNo(DateUtil.currentDate() + orderNo);//最小可传金额 0.1 元, + model.setTransAmount(String.format("%.2f", record.getCent() / 100.0)); + model.setProductCode("TRANS_ACCOUNT_NO_PWD"); + Participant payeeInfo = new Participant(); + payeeInfo.setIdentity(record.getAliPayAccount()); + payeeInfo.setName(record.getName()); + payeeInfo.setIdentityType("ALIPAY_LOGON_ID"); + model.setPayeeInfo(payeeInfo); + + request.setBizModel(model); + + AlipayFundTransUniTransferResponse response = alipayClient.certificateExecute(request); + if (response.isSuccess()) { + record.setStatus(UserService.TRANSFER_SUCCESS); + return true; + } else { + record.setStatus(UserService.TRANSFER_FAIL); + String reason = response.getCode() + "," + response.getMsg(); + record.setReason(reason); + return false; + } + } catch (AlipayApiException e) { + L.trace("transferError", "record:" + gson.toJson(record), e); + record.setReason("转账失败"); + record.setStatus(UserService.TRANSFER_FAIL); + return false; + } + } + + private static CertAlipayRequest getAlipayConfig(AliPayConfigBo bo) { + String privateKey = bo.aliPayPrivateKey; + CertAlipayRequest alipayConfig = new CertAlipayRequest(); + alipayConfig.setPrivateKey(privateKey); + alipayConfig.setServerUrl("https://openapi.alipay.com/gateway.do"); + alipayConfig.setAppId(bo.aliPayAppId); + alipayConfig.setCharset("UTF-8"); + alipayConfig.setSignType("RSA2"); + alipayConfig.setFormat("json"); + alipayConfig.setAlipayPublicCertContent(bo.aliPayPublicCert); + alipayConfig.setCertContent(bo.aliPayAppCert); + alipayConfig.setRootCertContent(bo.aliPayRootCert); + return alipayConfig; + } +} diff --git a/game-service/src/test/java/awesome/group/game/ServiceTestApplication.java b/game-service/src/test/java/awesome/group/game/ServiceTestApplication.java index 2b95fc8..51cd1bc 100644 --- a/game-service/src/test/java/awesome/group/game/ServiceTestApplication.java +++ b/game-service/src/test/java/awesome/group/game/ServiceTestApplication.java @@ -2,11 +2,13 @@ package awesome.group.game; import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.SpringBootApplication; +import org.springframework.scheduling.annotation.EnableScheduling; /** * @author nidaren */ @SpringBootApplication +@EnableScheduling public class ServiceTestApplication { public static void main(String[] args) throws Exception { diff --git a/game-service/src/test/java/awesome/group/game/service/UMengServiceTest.java b/game-service/src/test/java/awesome/group/game/service/UMengServiceTest.java new file mode 100644 index 0000000..3d0c6af --- /dev/null +++ b/game-service/src/test/java/awesome/group/game/service/UMengServiceTest.java @@ -0,0 +1,18 @@ +package awesome.group.game.service; + +import org.junit.jupiter.api.Test; +import org.springframework.beans.factory.annotation.Autowired; + +import static org.junit.jupiter.api.Assertions.*; + +class UMengServiceTest extends BaseTest{ + + @Autowired + private UMengService uMengService; + + @Test + void getMobile() { + String token = "eyJjIjoiNmk5amtxSVwvNXhXRElTRkNIeUpcL1RTemNjTEJsOEtiWndkT0NEYlhkUFJQREUzZ3g1bWx1bmNYdzRtclBWODVYOEludnJzS1pTOTRRXG53ejRudVlSaUs4cTFtRUdcL2FPQ0tIRktiUUtuS2Iya0ZFWjlyNWpPV044R0w3Q2I3V1g5dDA0ays2dmJwUXpaNGVTMklyOTJJcGtqaVxudm0rVG5vWVVVZWl4ZHhNNDArZ0hlaXBFRUpnUjlQNjhyZzY1VitrU1wvaWFQbXMxM3h4dEtGd2c3OVAwcVJ3VTZ1cFZcL2tUcXNvYTBOXG5jTDBtNThZc042RlwvcmZwcjJqbDVOZk1SdG1WdWFWTG1RVkVicHF3b2tUMWdiQk1UR0I4TDRIcHlhYUhyUXJUNnJQTG9kbDNWbjlNN1xudEFTZHRsU0JmMDYyVVVRSkZuZE9DeEZRN2diZ2JrRDNyYllBcXZ2cVZMUmFYWGlhNDNONGp6SnhTemJ0TnprM3ZTTmlrR0hHNFlaVlxuWXFJMlBcL3dlYlJucnlFRFlGQzhhaUVwdzB2R2UyRENcL3ZWNTdNMTlvN3VBVjFGaXFYUFpOSFFrdUVIcUFwRkpUUjBOODlRQ1Q0Qmw1XG5abmRsV2hyM1JWWTlRZWZSN3Nva0hjQjlHV1c0WlZWWXcyY0VFSDhIcHp5bmJlKzY2ZlwvbHpZZlJPUm5QUTNSdFpVV3dpNmFJNVd4M1xuY3F5ZVZjdEVCaTB6U1V5Y2tiVlRrXC90N0JaTlpMVkwyaHRKNzBXOXhXVnZRSU5LUloyOE1wc3M2bXNBNFlGa2gxdz09XG4iLCJrIjoiQ0ZZbm81SDNwSVJKK1FPMHhHZzZrU2FteGU2RXE5NDBxa0VoZXF1VHBiajlnSHl0UFwvNEdsQzh4R1lCYW04T093TVpoTElWSER5VVpvSThySFBOejRcL1ZKdm9XWXhwMEVNcWpyRkF0anV1cENDb1RKWUMzVWtXTmpMUkRLcG1za3Y2RHBjc2lBeHRvZnBPdVwvak04ZnR2dFhJOFBDQVwvU0Q4cHFENytKZDdqXC81Z0VQTUFndGgrdnZOYnp4VThrbU5cL01SVmRXK2FpUlFZSGswVFRZUnZ6eEJONDYwMCtDRjd2Vlh3djVcL1RUTmNBUmxCZkpkTFZnUnpnSFBjSE03Qk1NRzFRRW5PV3BGcjAyd29NS1dUdHZ6NndxYWdnQU9WeWFkdmgrRzg4eU9TRGNaTXBxbG5xOGtXQlFoY2QrampTZjRZaDdiOGNpdUZubWlzYmlXUmpmdz09IiwibyI6IkFuZHJvaWQifQ=="; + uMengService.getMobile(token); + } +} \ No newline at end of file diff --git a/game-service/src/test/java/awesome/group/game/service/pay/AlipayFundTransUniTransferTest.java b/game-service/src/test/java/awesome/group/game/service/pay/AlipayFundTransUniTransferTest.java new file mode 100644 index 0000000..68cab0b --- /dev/null +++ b/game-service/src/test/java/awesome/group/game/service/pay/AlipayFundTransUniTransferTest.java @@ -0,0 +1,198 @@ +package awesome.group.game.service.pay; + +import awesome.group.game.dao.bean.MatrixMoneyRecord; +import awesome.group.game.service.BaseTest; +import awesome.group.game.service.bo.matrix.AliPayConfigBo; +import awesome.group.game.service.citrus.UserService; +import com.alipay.api.AlipayApiException; +import com.google.gson.Gson; +import org.junit.jupiter.api.Test; +import org.springframework.beans.factory.annotation.Autowired; + +class AlipayFundTransUniTransferTest extends BaseTest { + @Autowired + private AlipayFundTransUniTransfer alipayFundTransUniTransfer; + + @Autowired + private UserService userService; + + @Test + void test1() throws AlipayApiException { + MatrixMoneyRecord matrixMoneyRecord = new MatrixMoneyRecord(); + matrixMoneyRecord.setAppId(6); + matrixMoneyRecord.setAliPayAccount("19181749767"); + matrixMoneyRecord.setName("倪丽"); + matrixMoneyRecord.setCent(10); + alipayFundTransUniTransfer.transfer(matrixMoneyRecord); + } + + @Test + public void testApply() { + userService.applyMoney(3, 10); + } + + @Test + public void genGson() { + AliPayConfigBo bo = new AliPayConfigBo(); + bo.aliPayAppId = "2021004143647533"; + bo.aliPayPrivateKey = "MIIEuwIBADANBgkqhkiG9w0BAQEFAASCBKUwggShAgEAAoIBAQCeU75wMTR1FUEbptIFgk9/aR+lPgMWVsONuj1JnRADqz/3AiNvDiXm20V75aZ/mUf+LaPx2su3wn2JoVr5reIOvx797Tb9JiUn/ucBx5p0lcEQbkMEh+PzXAZK6miRS4thgLEWbfrcVV7TTvGvlKiBVVPPfOfEmaqd/qX0aen9bOJ6/HH8EnTb19yckTK9xNO4WK4SqD66Xr649KyRteeeqx62ClbIU04ZMbywlmvkF1sjQbMI7MHMfHDHuI+3SuxQHY6INZwvG8Fua/6c4xCpAijjO0PnOlm5aZ7CxxwaxQva/jfHAQ7mq5xuvs1pyvtkhDF6md/RIqgFXM+w1VHDAgMBAAECggEBAJkz/7sgYdpJzs6rBd8+0R5A4tZKw0ICgwfJhzSMPsrOEv85moAD+LkCxKG2/v3JnNhf4ZxOU4JlOITNFfM0RuJuHdcoi2U6XAnvpikatGLL5h24FDF2LSV3jr8/RCAUMbMPjExf77b1BOUEJun3t3Yu0wKbosmiyG5J0txHAJywDS08+2udQSIvg4/BY67qCBbQeBx7sqMvnxatNAbjV7VdVDL2gl3MIS8MMlImBEsMWWcejEts8+XetxGVPJXhUr0yraWcnCCvReZxWhzdMNnmEWepsyj8ky6Q/L86i0s4OFPMfgk6lCTvGqqV2XJnr5k7KDVArCPUi80qHbHP6IECgYEA7ViPC+7zswwAvDoWOrIzZsCs9LQa7vZcPNzxnhjGg1OAx2W/h03u5x9kHETYiIAvZZh/cC3sj605r3JkvQstasO9xXG8qyWUpntEmnlFncgflkEW5Ou6dtbAEyMx+FMM+cl+tHMQsmnsL5hnhOkjP+R0XBATSU8iUCXRcJRoCTsCgYEAqsVQIxHVGyQovojkG0cIJRu94Mf6kWzenmHrslGzGm7MY7awEKnnXH/eepxHgJBwGHiLeb+cHgX+6prO58fM3RwYkHEVDAvnYabxATIFcmXQeXPiMBRmW0yzgtadlz4hJKdj/ZKOSvxMdSmYNih8cw8+0Q3/dhka/ORlo8k2kRkCgYBJiSOgzeMBeVmM9+5FN0sHrfCoTFj/6qJ/VPEjS4fNzoRawyKJOFMplqc8vvPbruOAdbQePIxLo574xdeCXsEukADu+KM834Lj5dNGjQZNsWBf/ECsooB+K2ENTN1Bk/G0PoKcQ/5LWNgNkwmXu2fpds26bFydXQBDlsQCPmjRWwKBgCdrVIxD2YViW2VgBAen5eFq/fGdN+HJ17mHsPiAk29OlC+QRCQUlCtt+NUkrfynWrjLWqbH7CmiCK3u/kPSgx+nFKSC9fDJ7qdD+e3ktg0qI21lqpienOIGWomhMM9wsAXd/d7SrbXxd1S0PUaDIfcNVdq7+HQyZ2Bo+G1OTSJBAn8QuGVOuCOUHYUSyOi+GJu9W3nJuqr1e6TuN3cY3/uGjTHkaBKgea6vT46jQC4yyM17sZz8F9FjJ1XN2jkUJnBMPFCQtmjSZqJBDSxl1UqLWtIEUKC4eKp6O9lc0msH/5dpO/klRVAonG2ksNn1/GxCzvJQOqwcGysikcSMBX2F"; + bo.aliPayRootCert = "-----BEGIN CERTIFICATE-----\n" + + "MIIBszCCAVegAwIBAgIIaeL+wBcKxnswDAYIKoEcz1UBg3UFADAuMQswCQYDVQQG\n" + + "EwJDTjEOMAwGA1UECgwFTlJDQUMxDzANBgNVBAMMBlJPT1RDQTAeFw0xMjA3MTQw\n" + + "MzExNTlaFw00MjA3MDcwMzExNTlaMC4xCzAJBgNVBAYTAkNOMQ4wDAYDVQQKDAVO\n" + + "UkNBQzEPMA0GA1UEAwwGUk9PVENBMFkwEwYHKoZIzj0CAQYIKoEcz1UBgi0DQgAE\n" + + "MPCca6pmgcchsTf2UnBeL9rtp4nw+itk1Kzrmbnqo05lUwkwlWK+4OIrtFdAqnRT\n" + + "V7Q9v1htkv42TsIutzd126NdMFswHwYDVR0jBBgwFoAUTDKxl9kzG8SmBcHG5Yti\n" + + "W/CXdlgwDAYDVR0TBAUwAwEB/zALBgNVHQ8EBAMCAQYwHQYDVR0OBBYEFEwysZfZ\n" + + "MxvEpgXBxuWLYlvwl3ZYMAwGCCqBHM9VAYN1BQADSAAwRQIgG1bSLeOXp3oB8H7b\n" + + "53W+CKOPl2PknmWEq/lMhtn25HkCIQDaHDgWxWFtnCrBjH16/W3Ezn7/U/Vjo5xI\n" + + "pDoiVhsLwg==\n" + + "-----END CERTIFICATE-----\n" + + "\n" + + "-----BEGIN CERTIFICATE-----\n" + + "MIIF0zCCA7ugAwIBAgIIH8+hjWpIDREwDQYJKoZIhvcNAQELBQAwejELMAkGA1UE\n" + + "BhMCQ04xFjAUBgNVBAoMDUFudCBGaW5hbmNpYWwxIDAeBgNVBAsMF0NlcnRpZmlj\n" + + "YXRpb24gQXV0aG9yaXR5MTEwLwYDVQQDDChBbnQgRmluYW5jaWFsIENlcnRpZmlj\n" + + "YXRpb24gQXV0aG9yaXR5IFIxMB4XDTE4MDMyMTEzNDg0MFoXDTM4MDIyODEzNDg0\n" + + "MFowejELMAkGA1UEBhMCQ04xFjAUBgNVBAoMDUFudCBGaW5hbmNpYWwxIDAeBgNV\n" + + "BAsMF0NlcnRpZmljYXRpb24gQXV0aG9yaXR5MTEwLwYDVQQDDChBbnQgRmluYW5j\n" + + "aWFsIENlcnRpZmljYXRpb24gQXV0aG9yaXR5IFIxMIICIjANBgkqhkiG9w0BAQEF\n" + + "AAOCAg8AMIICCgKCAgEAtytTRcBNuur5h8xuxnlKJetT65cHGemGi8oD+beHFPTk\n" + + "rUTlFt9Xn7fAVGo6QSsPb9uGLpUFGEdGmbsQ2q9cV4P89qkH04VzIPwT7AywJdt2\n" + + "xAvMs+MgHFJzOYfL1QkdOOVO7NwKxH8IvlQgFabWomWk2Ei9WfUyxFjVO1LVh0Bp\n" + + "dRBeWLMkdudx0tl3+21t1apnReFNQ5nfX29xeSxIhesaMHDZFViO/DXDNW2BcTs6\n" + + "vSWKyJ4YIIIzStumD8K1xMsoaZBMDxg4itjWFaKRgNuPiIn4kjDY3kC66Sl/6yTl\n" + + "YUz8AybbEsICZzssdZh7jcNb1VRfk79lgAprm/Ktl+mgrU1gaMGP1OE25JCbqli1\n" + + "Pbw/BpPynyP9+XulE+2mxFwTYhKAwpDIDKuYsFUXuo8t261pCovI1CXFzAQM2w7H\n" + + "DtA2nOXSW6q0jGDJ5+WauH+K8ZSvA6x4sFo4u0KNCx0ROTBpLif6GTngqo3sj+98\n" + + "SZiMNLFMQoQkjkdN5Q5g9N6CFZPVZ6QpO0JcIc7S1le/g9z5iBKnifrKxy0TQjtG\n" + + "PsDwc8ubPnRm/F82RReCoyNyx63indpgFfhN7+KxUIQ9cOwwTvemmor0A+ZQamRe\n" + + "9LMuiEfEaWUDK+6O0Gl8lO571uI5onYdN1VIgOmwFbe+D8TcuzVjIZ/zvHrAGUcC\n" + + "AwEAAaNdMFswCwYDVR0PBAQDAgEGMAwGA1UdEwQFMAMBAf8wHQYDVR0OBBYEFF90\n" + + "tATATwda6uWx2yKjh0GynOEBMB8GA1UdIwQYMBaAFF90tATATwda6uWx2yKjh0Gy\n" + + "nOEBMA0GCSqGSIb3DQEBCwUAA4ICAQCVYaOtqOLIpsrEikE5lb+UARNSFJg6tpkf\n" + + "tJ2U8QF/DejemEHx5IClQu6ajxjtu0Aie4/3UnIXop8nH/Q57l+Wyt9T7N2WPiNq\n" + + "JSlYKYbJpPF8LXbuKYG3BTFTdOVFIeRe2NUyYh/xs6bXGr4WKTXb3qBmzR02FSy3\n" + + "IODQw5Q6zpXj8prYqFHYsOvGCEc1CwJaSaYwRhTkFedJUxiyhyB5GQwoFfExCVHW\n" + + "05ZFCAVYFldCJvUzfzrWubN6wX0DD2dwultgmldOn/W/n8at52mpPNvIdbZb2F41\n" + + "T0YZeoWnCJrYXjq/32oc1cmifIHqySnyMnavi75DxPCdZsCOpSAT4j4lAQRGsfgI\n" + + "kkLPGQieMfNNkMCKh7qjwdXAVtdqhf0RVtFILH3OyEodlk1HYXqX5iE5wlaKzDop\n" + + "PKwf2Q3BErq1xChYGGVS+dEvyXc/2nIBlt7uLWKp4XFjqekKbaGaLJdjYP5b2s7N\n" + + "1dM0MXQ/f8XoXKBkJNzEiM3hfsU6DOREgMc1DIsFKxfuMwX3EkVQM1If8ghb6x5Y\n" + + "jXayv+NLbidOSzk4vl5QwngO/JYFMkoc6i9LNwEaEtR9PhnrdubxmrtM+RjfBm02\n" + + "77q3dSWFESFQ4QxYWew4pHE0DpWbWy/iMIKQ6UZ5RLvB8GEcgt8ON7BBJeMc+Dyi\n" + + "kT9qhqn+lw==\n" + + "-----END CERTIFICATE-----\n" + + "\n" + + "-----BEGIN CERTIFICATE-----\n" + + "MIICiDCCAgygAwIBAgIIQX76UsB/30owDAYIKoZIzj0EAwMFADB6MQswCQYDVQQG\n" + + "EwJDTjEWMBQGA1UECgwNQW50IEZpbmFuY2lhbDEgMB4GA1UECwwXQ2VydGlmaWNh\n" + + "dGlvbiBBdXRob3JpdHkxMTAvBgNVBAMMKEFudCBGaW5hbmNpYWwgQ2VydGlmaWNh\n" + + "dGlvbiBBdXRob3JpdHkgRTEwHhcNMTkwNDI4MTYyMDQ0WhcNNDkwNDIwMTYyMDQ0\n" + + "WjB6MQswCQYDVQQGEwJDTjEWMBQGA1UECgwNQW50IEZpbmFuY2lhbDEgMB4GA1UE\n" + + "CwwXQ2VydGlmaWNhdGlvbiBBdXRob3JpdHkxMTAvBgNVBAMMKEFudCBGaW5hbmNp\n" + + "YWwgQ2VydGlmaWNhdGlvbiBBdXRob3JpdHkgRTEwdjAQBgcqhkjOPQIBBgUrgQQA\n" + + "IgNiAASCCRa94QI0vR5Up9Yr9HEupz6hSoyjySYqo7v837KnmjveUIUNiuC9pWAU\n" + + "WP3jwLX3HkzeiNdeg22a0IZPoSUCpasufiLAnfXh6NInLiWBrjLJXDSGaY7vaokt\n" + + "rpZvAdmjXTBbMAsGA1UdDwQEAwIBBjAMBgNVHRMEBTADAQH/MB0GA1UdDgQWBBRZ\n" + + "4ZTgDpksHL2qcpkFkxD2zVd16TAfBgNVHSMEGDAWgBRZ4ZTgDpksHL2qcpkFkxD2\n" + + "zVd16TAMBggqhkjOPQQDAwUAA2gAMGUCMQD4IoqT2hTUn0jt7oXLdMJ8q4vLp6sg\n" + + "wHfPiOr9gxreb+e6Oidwd2LDnC4OUqCWiF8CMAzwKs4SnDJYcMLf2vpkbuVE4dTH\n" + + "Rglz+HGcTLWsFs4KxLsq7MuU+vJTBUeDJeDjdA==\n" + + "-----END CERTIFICATE-----\n" + + "\n" + + "-----BEGIN CERTIFICATE-----\n" + + "MIIDxTCCAq2gAwIBAgIUEMdk6dVgOEIS2cCP0Q43P90Ps5YwDQYJKoZIhvcNAQEF\n" + + "BQAwajELMAkGA1UEBhMCQ04xEzARBgNVBAoMCmlUcnVzQ2hpbmExHDAaBgNVBAsM\n" + + "E0NoaW5hIFRydXN0IE5ldHdvcmsxKDAmBgNVBAMMH2lUcnVzQ2hpbmEgQ2xhc3Mg\n" + + "MiBSb290IENBIC0gRzMwHhcNMTMwNDE4MDkzNjU2WhcNMzMwNDE4MDkzNjU2WjBq\n" + + "MQswCQYDVQQGEwJDTjETMBEGA1UECgwKaVRydXNDaGluYTEcMBoGA1UECwwTQ2hp\n" + + "bmEgVHJ1c3QgTmV0d29yazEoMCYGA1UEAwwfaVRydXNDaGluYSBDbGFzcyAyIFJv\n" + + "b3QgQ0EgLSBHMzCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBAOPPShpV\n" + + "nJbMqqCw6Bz1kehnoPst9pkr0V9idOwU2oyS47/HjJXk9Rd5a9xfwkPO88trUpz5\n" + + "4GmmwspDXjVFu9L0eFaRuH3KMha1Ak01citbF7cQLJlS7XI+tpkTGHEY5pt3EsQg\n" + + "wykfZl/A1jrnSkspMS997r2Gim54cwz+mTMgDRhZsKK/lbOeBPpWtcFizjXYCqhw\n" + + "WktvQfZBYi6o4sHCshnOswi4yV1p+LuFcQ2ciYdWvULh1eZhLxHbGXyznYHi0dGN\n" + + "z+I9H8aXxqAQfHVhbdHNzi77hCxFjOy+hHrGsyzjrd2swVQ2iUWP8BfEQqGLqM1g\n" + + "KgWKYfcTGdbPB1MCAwEAAaNjMGEwHQYDVR0OBBYEFG/oAMxTVe7y0+408CTAK8hA\n" + + "uTyRMB8GA1UdIwQYMBaAFG/oAMxTVe7y0+408CTAK8hAuTyRMA8GA1UdEwEB/wQF\n" + + "MAMBAf8wDgYDVR0PAQH/BAQDAgEGMA0GCSqGSIb3DQEBBQUAA4IBAQBLnUTfW7hp\n" + + "emMbuUGCk7RBswzOT83bDM6824EkUnf+X0iKS95SUNGeeSWK2o/3ALJo5hi7GZr3\n" + + "U8eLaWAcYizfO99UXMRBPw5PRR+gXGEronGUugLpxsjuynoLQu8GQAeysSXKbN1I\n" + + "UugDo9u8igJORYA+5ms0s5sCUySqbQ2R5z/GoceyI9LdxIVa1RjVX8pYOj8JFwtn\n" + + "DJN3ftSFvNMYwRuILKuqUYSHc2GPYiHVflDh5nDymCMOQFcFG3WsEuB+EYQPFgIU\n" + + "1DHmdZcz7Llx8UOZXX2JupWCYzK1XhJb+r4hK5ncf/w8qGtYlmyJpxk3hr1TfUJX\n" + + "Yf4Zr0fJsGuv\n" + + "-----END CERTIFICATE-----"; + bo.aliPayAppCert = "-----BEGIN CERTIFICATE-----\n" + + "MIIEoDCCA4igAwIBAgIQICQFCYw2I4Ya+pK5n28TCTANBgkqhkiG9w0BAQsFADCBgjELMAkGA1UE\n" + + "BhMCQ04xFjAUBgNVBAoMDUFudCBGaW5hbmNpYWwxIDAeBgNVBAsMF0NlcnRpZmljYXRpb24gQXV0\n" + + "aG9yaXR5MTkwNwYDVQQDDDBBbnQgRmluYW5jaWFsIENlcnRpZmljYXRpb24gQXV0aG9yaXR5IENs\n" + + "YXNzIDEgUjEwHhcNMjQwNTA5MDI0ODU2WhcNMjkwNTA4MDI0ODU2WjBoMQswCQYDVQQGEwJDTjEt\n" + + "MCsGA1UECgwk5oiQ6YO95aWH6L+555WF546p56eR5oqA5pyJ6ZmQ5YWs5Y+4MQ8wDQYDVQQLDAZB\n" + + "bGlwYXkxGTAXBgNVBAMMEDIwODg4NDEyODQ2NTg5ODEwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAw\n" + + "ggEKAoIBAQCeU75wMTR1FUEbptIFgk9/aR+lPgMWVsONuj1JnRADqz/3AiNvDiXm20V75aZ/mUf+\n" + + "LaPx2su3wn2JoVr5reIOvx797Tb9JiUn/ucBx5p0lcEQbkMEh+PzXAZK6miRS4thgLEWbfrcVV7T\n" + + "TvGvlKiBVVPPfOfEmaqd/qX0aen9bOJ6/HH8EnTb19yckTK9xNO4WK4SqD66Xr649KyRteeeqx62\n" + + "ClbIU04ZMbywlmvkF1sjQbMI7MHMfHDHuI+3SuxQHY6INZwvG8Fua/6c4xCpAijjO0PnOlm5aZ7C\n" + + "xxwaxQva/jfHAQ7mq5xuvs1pyvtkhDF6md/RIqgFXM+w1VHDAgMBAAGjggEpMIIBJTAfBgNVHSME\n" + + "GDAWgBRxB+IEYRbk5fJl6zEPyeD0PJrVkTAdBgNVHQ4EFgQUSFMQjFFZwHUPg8Punc9zle3FnR0w\n" + + "QAYDVR0gBDkwNzA1BgdggRwBbgEBMCowKAYIKwYBBQUHAgEWHGh0dHA6Ly9jYS5hbGlwYXkuY29t\n" + + "L2Nwcy5wZGYwDgYDVR0PAQH/BAQDAgbAMC8GA1UdHwQoMCYwJKAioCCGHmh0dHA6Ly9jYS5hbGlw\n" + + "YXkuY29tL2NybDg5LmNybDBgBggrBgEFBQcBAQRUMFIwKAYIKwYBBQUHMAKGHGh0dHA6Ly9jYS5h\n" + + "bGlwYXkuY29tL2NhNi5jZXIwJgYIKwYBBQUHMAGGGmh0dHA6Ly9jYS5hbGlwYXkuY29tOjgzNDAv\n" + + "MA0GCSqGSIb3DQEBCwUAA4IBAQAheCMGQ1iPZXjuh4oQaaQPXnHmeUvS4aASbW1PwcPPXvuRvEVi\n" + + "1m4PJaygX082A9bgRUqLbdTK0GQPDhSuGX6ap+8sz0mkm0ywM485hbjirRsAj2GKXi9UxUeuJ6OP\n" + + "6oIvwloOPqG1SDMScSDPPTtuaXRnu8QNEvRUjIVFrognqpVC+z8yXJENC24+uJWd1zmshvo2epHG\n" + + "iQD+L5+pIoTlzy/PwYlE14gBlLlOWuBHjz7TJXyA20Nk1GtQ3/dD+40D74vSatbmBAxoIIjAwAZD\n" + + "mjgDzHRtRAysLHBbyZh2GAWG5bXhATZSfUwAHhyNKu+E8AD/jRcyeiku9CFO/6NH\n" + + "-----END CERTIFICATE-----"; + bo.aliPayPublicCert = "-----BEGIN CERTIFICATE-----\n" + + "MIIDnTCCAoWgAwIBAgIQICQFCd/KXSqlPFRysYroGTANBgkqhkiG9w0BAQsFADCBgjELMAkGA1UE\n" + + "BhMCQ04xFjAUBgNVBAoMDUFudCBGaW5hbmNpYWwxIDAeBgNVBAsMF0NlcnRpZmljYXRpb24gQXV0\n" + + "aG9yaXR5MTkwNwYDVQQDDDBBbnQgRmluYW5jaWFsIENlcnRpZmljYXRpb24gQXV0aG9yaXR5IENs\n" + + "YXNzIDIgUjEwHhcNMjQwNTA5MDI0ODU3WhcNMjkwNTA4MDI0ODU3WjB+MQswCQYDVQQGEwJDTjEZ\n" + + "MBcGA1UECgwQMjA4ODg0MTI4NDY1ODk4MTEPMA0GA1UECwwGQWxpcGF5MUMwQQYDVQQDDDrmlK/k\n" + + "u5jlrp0o5Lit5Zu9Kee9kee7nOaKgOacr+aciemZkOWFrOWPuC0yMDg4ODQxMjg0NjU4OTgxMIIB\n" + + "IjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAmRfS59/z9uZCgainfQ7AWC3zNNrMxKOkU+Mr\n" + + "aZOI5wXR4nDrCk2xscd+84rd/DVQ13U7rXKDOAoWKrZNghDNyRM9j/bTBnkTceQGTbo2wOdeIOM1\n" + + "I90nmtQCfLE0sahcwiP32hyxL2s8C8RzEBNFWhwMuDvsWTZSBOjxDNz0B0rNG6ocfw8riNt1f0Ue\n" + + "5moRJ6MS1cWGOf8ngbOYgSccJn7E/K53iZj4EWhCeAA3wHTvRN2uX/hX5icbxc0tJ1eFFKisYhgZ\n" + + "VQCeYg0HJhmDV7G4R1uHL0EiHw5fQJFFjq+OWBrH1ro5he+kdU/adQC4fvT2DoVK/JamGjTN088A\n" + + "twIDAQABoxIwEDAOBgNVHQ8BAf8EBAMCA/gwDQYJKoZIhvcNAQELBQADggEBAEoVe17OXLCpO8l1\n" + + "6aED4aE4McQjeFeToxO4HtgQ0XC2sCur8ffSZDQZHCJN1eXyYedKH4dmGj3XhQqGGntqZgxTFymm\n" + + "zINRuBol8Z0OR7IAzP27R8Tml4+Ka8Q5sCHSFEBgmmv3YNOuL6LlNYZJ647FcSERvGZZmuOAnnV1\n" + + "Gis/hiwZ/0Rl7UM6KObKWO4eV2lyYOQqVJf6kI9NGDo2N6nTltgmJYag4PyFk+/70Y6arqCkIVjU\n" + + "qpajdaqMeZypFMwcMRnP1FDl5CrxL3NVBi3jXLGORe80dfg73ETZdiL0wM3wBSRT3J+dfFZT/sZ3\n" + + "Yfp28EoAG5Z1aF22j450Xhk=\n" + + "-----END CERTIFICATE-----\n" + + "-----BEGIN CERTIFICATE-----\n" + + "MIIE4jCCAsqgAwIBAgIIYsSr5bKAMl8wDQYJKoZIhvcNAQELBQAwejELMAkGA1UEBhMCQ04xFjAU\n" + + "BgNVBAoMDUFudCBGaW5hbmNpYWwxIDAeBgNVBAsMF0NlcnRpZmljYXRpb24gQXV0aG9yaXR5MTEw\n" + + "LwYDVQQDDChBbnQgRmluYW5jaWFsIENlcnRpZmljYXRpb24gQXV0aG9yaXR5IFIxMB4XDTE4MDMy\n" + + "MjE0MzQxNVoXDTM3MTEyNjE0MzQxNVowgYIxCzAJBgNVBAYTAkNOMRYwFAYDVQQKDA1BbnQgRmlu\n" + + "YW5jaWFsMSAwHgYDVQQLDBdDZXJ0aWZpY2F0aW9uIEF1dGhvcml0eTE5MDcGA1UEAwwwQW50IEZp\n" + + "bmFuY2lhbCBDZXJ0aWZpY2F0aW9uIEF1dGhvcml0eSBDbGFzcyAyIFIxMIIBIjANBgkqhkiG9w0B\n" + + "AQEFAAOCAQ8AMIIBCgKCAQEAsLMfYaoRoPRbmDcAfXPCmKf43pWRN5yTXa/KJWO0l+mrgQvs89bA\n" + + "NEvbDUxlkGwycwtwi5DgBuBgVhLliXu+R9CYgr2dXs8D8Hx/gsggDcyGPLmVrDOnL+dyeauheARZ\n" + + "fA3du60fwEwwbGcVIpIxPa/4n3IS/ElxQa6DNgqxh8J9Xwh7qMGl0JK9+bALuxf7B541Gr4p0WEN\n" + + "G8fhgjBV4w4ut9eQLOoa1eddOUSZcy46Z7allwowwgt7b5VFfx/P1iKJ3LzBMgkCK7GZ2kiLrL7R\n" + + "iqV+h482J7hkJD+ardoc6LnrHO/hIZymDxok+VH9fVeUdQa29IZKrIDVj65THQIDAQABo2MwYTAf\n" + + "BgNVHSMEGDAWgBRfdLQEwE8HWurlsdsio4dBspzhATAdBgNVHQ4EFgQUSqHkYINtUSAtDPnS8Xoy\n" + + "oP9p7qEwDwYDVR0TAQH/BAUwAwEB/zAOBgNVHQ8BAf8EBAMCAQYwDQYJKoZIhvcNAQELBQADggIB\n" + + "AIQ8TzFy4bVIVb8+WhHKCkKNPcJe2EZuIcqvRoi727lZTJOfYy/JzLtckyZYfEI8J0lasZ29wkTt\n" + + "a1IjSo+a6XdhudU4ONVBrL70U8Kzntplw/6TBNbLFpp7taRALjUgbCOk4EoBMbeCL0GiYYsTS0mw\n" + + "7xdySzmGQku4GTyqutIGPQwKxSj9iSFw1FCZqr4VP4tyXzMUgc52SzagA6i7AyLedd3tbS6lnR5B\n" + + "L+W9Kx9hwT8L7WANAxQzv/jGldeuSLN8bsTxlOYlsdjmIGu/C9OWblPYGpjQQIRyvs4Cc/mNhrh+\n" + + "14EQgwuemIIFDLOgcD+iISoN8CqegelNcJndFw1PDN6LkVoiHz9p7jzsge8RKay/QW6C03KNDpWZ\n" + + "EUCgCUdfHfo8xKeR+LL1cfn24HKJmZt8L/aeRZwZ1jwePXFRVtiXELvgJuM/tJDIFj2KD337iV64\n" + + "fWcKQ/ydDVGqfDZAdcU4hQdsrPWENwPTQPfVPq2NNLMyIH9+WKx9Ed6/WzeZmIy5ZWpX1TtTolo6\n" + + "OJXQFeItMAjHxW/ZSZTok5IS3FuRhExturaInnzjYpx50a6kS34c5+c8hYq7sAtZ/CNLZmBnBCFD\n" + + "aMQqT8xFZJ5uolUaSeXxg7JFY1QsYp5RKvj4SjFwCGKJ2+hPPe9UyyltxOidNtxjaknOCeBHytOr\n" + + "-----END CERTIFICATE-----\n"; + Gson gson = new Gson(); + String json = gson.toJson(bo); + System.out.println(json); + } + +} \ No newline at end of file diff --git a/game-web/src/main/java/awesome/group/game/web/filter/CitrusLoginFilter.java b/game-web/src/main/java/awesome/group/game/web/filter/CitrusLoginFilter.java index c0b9b1a..7ab078f 100644 --- a/game-web/src/main/java/awesome/group/game/web/filter/CitrusLoginFilter.java +++ b/game-web/src/main/java/awesome/group/game/web/filter/CitrusLoginFilter.java @@ -32,14 +32,7 @@ public class CitrusLoginFilter implements Filter { public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException { try { HttpServletRequest httpRequest = (HttpServletRequest) request; - String token = ""; - if(httpRequest.getCookies() != null) { - for (Cookie c : httpRequest.getCookies()) { - if (c.getName().equals("CitrusToken")) { - token = c.getValue(); - } - } - } + String token = httpRequest.getHeader("Authorization"); List openApi = List.of( "/api/citrus/register", "/api/citrus/login" diff --git a/game-web/src/main/java/awesome/group/game/web/rest/citrus/CitrusAppController.java b/game-web/src/main/java/awesome/group/game/web/rest/citrus/CitrusAppController.java new file mode 100644 index 0000000..a238ee8 --- /dev/null +++ b/game-web/src/main/java/awesome/group/game/web/rest/citrus/CitrusAppController.java @@ -0,0 +1,24 @@ +package awesome.group.game.web.rest.citrus; + +import awesome.group.game.service.bo.citrus.AppBo; +import awesome.group.game.service.citrus.CitrusAppService; +import awesome.group.game.service.common.response.R; +import awesome.group.game.web.aop.RestApi; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.web.bind.annotation.GetMapping; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestParam; +import org.springframework.web.bind.annotation.RestController; + +@RestController +@RequestMapping("/api/citrus/app") +public class CitrusAppController { + @Autowired + private CitrusAppService appService; + + @GetMapping("/getDetail") + @RestApi + public R getAppDetail(@RequestParam String appCode) { + return new R<>(appService.getAppDetail(appCode)); + } +} diff --git a/game-web/src/main/java/awesome/group/game/web/rest/citrus/OpenController.java b/game-web/src/main/java/awesome/group/game/web/rest/citrus/OpenController.java index 2fa0c15..96b0238 100644 --- a/game-web/src/main/java/awesome/group/game/web/rest/citrus/OpenController.java +++ b/game-web/src/main/java/awesome/group/game/web/rest/citrus/OpenController.java @@ -75,4 +75,12 @@ public class OpenController { return new R<>(R.CODE_SUCCESS, "ok", token); } + @PostMapping("/loginByToken") + @RestApi + public R loginByToken(@RequestBody LoginReq req) { + MatrixUser u = userService.loginByToken(req.appCode, req.token); + String token = JwtUtils.generatorToken(u.getId() + "", 15 * 86400); + return new R<>(R.CODE_SUCCESS, "ok", token); + } + } diff --git a/game-web/src/main/java/awesome/group/game/web/rest/citrus/UserController.java b/game-web/src/main/java/awesome/group/game/web/rest/citrus/UserController.java index 9ce0dd9..4f28310 100644 --- a/game-web/src/main/java/awesome/group/game/web/rest/citrus/UserController.java +++ b/game-web/src/main/java/awesome/group/game/web/rest/citrus/UserController.java @@ -1,14 +1,15 @@ package awesome.group.game.web.rest.citrus; +import awesome.group.game.service.bo.citrus.CashRecord; import awesome.group.game.service.bo.citrus.UserBo; import awesome.group.game.service.citrus.UserService; import awesome.group.game.service.common.response.R; import awesome.group.game.web.RequestContext; import awesome.group.game.web.aop.RestApi; import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.web.bind.annotation.GetMapping; -import org.springframework.web.bind.annotation.RequestMapping; -import org.springframework.web.bind.annotation.RestController; +import org.springframework.web.bind.annotation.*; + +import java.util.List; @RestController @RequestMapping("/api/citrus/user") @@ -22,4 +23,24 @@ public class UserController { public R currentUser() { return new R<>(userService.getUser(RequestContext.getCitrusUid())); } + + @PostMapping("/bindAliPay") + @RestApi + public R bindAliPay(@RequestBody UserBo userBo) { + userService.bindAliPay(RequestContext.getCitrusUid(), userBo.aliPayAccount, userBo.name); + return new R<>(null); + } + + @GetMapping("/cashRecords") + @RestApi + public R> getCashRecord() { + return new R<>(userService.getCashRecord(RequestContext.getCitrusUid())); + } + + @PostMapping("/applyCash") + @RestApi + public R applyCash(@RequestParam Integer money) { + userService.applyMoney(RequestContext.getCitrusUid(), money); + return new R<>(null); + } }