47 Commits

Author SHA1 Message Date
felord.cn
d95d9de0f1 Merge pull request #124 from dromara/1.0.20
1.0.20
2024-04-29 13:41:35 +08:00
xiafang
5b8850b980 enhance: 1.0.20 2024-04-29 13:41:07 +08:00
xiafang
85621edace Merge branch 'release' into 1.0.20
# Conflicts:
#	payment-spring-boot-autoconfigure/src/main/java/cn/felord/payment/wechat/v3/model/ecommerce/EcommerceContactInfo.java
2024-04-29 13:38:43 +08:00
xiafang
56995088d1 enhance: 发放代金券中制券商户号用户可自定义
Closes #122
2024-04-29 13:30:39 +08:00
xiafang
6e2b6decf4 enhance: 发起商家转账增加回调通知
Closes #123
2024-04-29 12:50:12 +08:00
xiafang
d068734422 enhance: 优化逻辑 2024-01-15 15:53:52 +08:00
xiafang
57e794280f fix: 微信支付分停车GET请求车牌号省份汉字encode问题
Closes  #113
2023-11-28 14:08:34 +08:00
xiafang
56bf43f04f #109 2023-11-28 13:50:53 +08:00
felord.cn
87257fc8b1 Merge pull request #109 from lgxisbb/20230703_media_api
20230703 ecommerce api
2023-11-28 13:37:23 +08:00
felord.cn
616ea0cede Merge pull request #110 from dromara/dependabot/maven/org.bouncycastle-bcprov-jdk15to18-1.74
build(deps): bump bcprov-jdk15to18 from 1.69 to 1.74
2023-11-28 13:36:57 +08:00
xiafang
f4615b02b3 修复时间序列化问题 2023-11-28 13:30:26 +08:00
dependabot[bot]
4e27958ace build(deps): bump bcprov-jdk15to18 from 1.69 to 1.74
Bumps [bcprov-jdk15to18](https://github.com/bcgit/bc-java) from 1.69 to 1.74.
- [Changelog](https://github.com/bcgit/bc-java/blob/main/docs/releasenotes.html)
- [Commits](https://github.com/bcgit/bc-java/commits)

---
updated-dependencies:
- dependency-name: org.bouncycastle:bcprov-jdk15to18
  dependency-type: direct:production
...

Signed-off-by: dependabot[bot] <support@github.com>
2023-07-06 15:41:12 +00:00
fourier
aaad20b78a feat: 电商收付通二级商户进件接口联系人手机号码加密 2023-07-04 10:33:41 +08:00
fourier
10b09ac4bb feat: 电商收付通二级商户进件接口联系人信息增加字段 2023-07-04 10:26:54 +08:00
xiafang
62ecc5b700 Merge remote-tracking branch 'origin/1.0.20' into 1.0.20 2023-07-01 09:27:04 +08:00
xiafang
8168097427 enhance: 电商收付通二级商户进件申请参数
Closes #108
2023-07-01 09:26:28 +08:00
xiafang
9645d20b33 enhance: 电商收付通二级商户进件申请参数 2023-07-01 09:25:12 +08:00
xiafang
c42f6d9d5e - 电商二级商户进件补充最终受益人列表 2023-06-27 14:02:07 +08:00
xiafang
0635d59666 1.0.19 2023-06-24 11:29:11 +08:00
xiafang
5941907d7c feat: 支付有礼-直连商户 2023-06-21 15:15:22 +08:00
xiafang
348fe9b5f1 enhance: 代金券商家券样式兼容 2023-06-20 09:34:20 +08:00
xiafang
fa0cc541de fix:服务商模式下预支付的签名问题
Closes #I7829T
2023-06-20 08:35:22 +08:00
xiafang
85fde9bb68 优化默认的证书加载,增加缓存 2023-05-22 14:07:24 +08:00
xiafang
da0fe928eb Merge README.md 2023-05-05 12:55:33 +08:00
felord.cn
1c27375d93 Merge pull request #99 from dromara/1.0.18
1.0.18
2023-05-05 12:44:37 +08:00
xiafang
4271491bc3 Merge README.md 2023-05-05 12:41:23 +08:00
xiafang
730c15b6b8 Update pom.xml 2023-05-05 12:33:21 +08:00
xiafang
dc6e48d538 enhance: 修改了支付配置加载机制,现在可以不停机维护微信支付参数了 2023-05-05 12:20:06 +08:00
xiafang
36259fc8ac 更新群信息 2023-04-25 11:00:18 +08:00
xiafang
e6e704cc28 docs: 修正文档描述错误 2023-03-24 13:43:34 +08:00
xiafang
8578300d1c docs: 修正文档描述错误 2023-03-24 13:40:32 +08:00
Fang
d7cdebc731 docs: 项目文档迁入dromara
Closes #96
2023-03-12 20:54:25 +08:00
felord.cn
97d87ce6f0 Delete 提问.md 2023-03-11 08:53:13 +08:00
felord.cn
99136f9bd6 Update issue templates 2023-03-11 08:52:15 +08:00
felord.cn
571bd2e563 Update issue templates 2023-03-11 08:49:32 +08:00
Fang
aef8ef9ac3 factor:移除过时的V2退款API 2023-03-10 22:32:52 +08:00
Fang
f630301bc3 docs:更新文档地址到dromara组织 2023-03-10 22:31:06 +08:00
xiafang
f7ba4dd306 1.0.18 2023-03-08 13:39:11 +08:00
Fang
997f004708 enhance: 增强资源加载器 2023-03-06 22:31:55 +08:00
xiafang
5e63779f36 1.0.18 2023-03-01 09:29:36 +08:00
xiafang
30613a2fdd enhance: 优化证书加载方式以支持Docker内读取
Closes #94
2023-03-01 09:24:51 +08:00
felord.cn
e9388f62c1 Update changelog.md 2023-02-26 14:33:38 +08:00
xiafang
685839089f README.md 2023-02-25 17:16:29 +08:00
xiafang
7b9bdd21f7 README.md 2023-02-25 16:56:37 +08:00
xiafang
8c4ecad809 README.md 2023-02-25 16:52:29 +08:00
xiafang
e24aa83ba0 README.md 2023-02-25 16:47:36 +08:00
felord.cn
d6d5e33dae Merge pull request #93 from NotFound403/1.0.17
1.0.17
2023-02-25 16:41:16 +08:00
50 changed files with 1270 additions and 182 deletions

27
.github/ISSUE_TEMPLATE/issues.md vendored Normal file
View File

@@ -0,0 +1,27 @@
---
name: issues
about: 向维护者提问以帮助改进
title: ''
labels: ''
assignees: ''
---
**提问前的思考**
1. 我是否已经认真阅读了文档和相关操作说明
2. 其它ISSUES是否已经有了解决方案
**描述问题**
提问时应该按照以下要点清晰地描述问题,才能得到可靠的答复
**环境版本信息**
问题发生的环境,不限于软件版本、运行时环境、操作系统等
**操作行为**
产生问题的操作行为
**期望的结果**
清晰地描述期望达成的结果
**代码与截图**
通常不建议使用代码截图这样不太方便维护者进行Preview。代码应该使用Markdown代码块进行格式化。因交互导致的问题才建议使用截图辅助排查。

View File

@@ -1,8 +1,8 @@
<div align="center" style="margin-bottom: 10px"><h1>最全最好用的微信支付V3 Spring Boot 组件</h1></div>
<p align="center">
<a target="_blank" href="https://github.com/NotFound403/payment-spring-boot/blob/release/LICENSE">
<img alt="" src="https://img.shields.io/github/license/NotFound403/payment-spring-boot"/>
<a target="_blank" href="https://github.com/dromara/payment-spring-boot/blob/release/LICENSE">
<img alt="" src="https://img.shields.io/github/license/dromara/payment-spring-boot"/>
</a>
<a target="_blank" href="https://felord.cn">
<img alt="" src="https://img.shields.io/badge/java-8-red"/>
@@ -13,17 +13,20 @@
<a target="_blank" href="https://mvnrepository.com/artifact/cn.felord/payment-spring-boot">
<img alt="" src="https://img.shields.io/maven-central/v/cn.felord/payment-spring-boot.svg?style=flat-square"/>
</a>
<a target="_blank" href="https://github.com/NotFound403/payment-spring-boot">
<img alt="" src="https://img.shields.io/github/stars/NotFound403/payment-spring-boot?style=social"/>
<a target="_blank" href="https://github.com/dromara/payment-spring-boot">
<img alt="" src="https://img.shields.io/github/stars/dromara/payment-spring-boot?style=social"/>
</a>
<a target="_blank" href="https://gitee.com/felord/payment-spring-boot/stargazers">
<a target="_blank" href="https://gitee.com/dromara/payment-spring-boot/stargazers">
<img alt="" src="https://gitee.com/felord/payment-spring-boot/badge/star.svg?theme=white"/>
</a>
<a target="_blank" href="https://work.weixin.qq.com/kfid/kfc9d9d759f27f087e1">
<img alt="点击立即微信咨询" src="https://img.shields.io/badge/%E7%82%B9%E5%87%BB-%E5%BE%AE%E4%BF%A1%E5%92%A8%E8%AF%A2-brightgreen"/>
</a>
<a target="_blank" href="https://jq.qq.com/?_wv=1027&k=qRTKHWY0">
<img alt="点击加入QQ交流" src="https://img.shields.io/badge/QQ%E4%BA%A4%E6%B5%81%E7%BE%A4-945342113-ff69b4"/>
<a target="_blank" href="#">
<img alt="点击加入QQ交流①群(满)" src="https://img.shields.io/badge/QQ%E4%BA%A4%E6%B5%81%E7%BE%A4-945342113(满)-ff69b4"/>
</a>
<a target="_blank" href="https://jq.qq.com/?_wv=1027&k=cCiv8Vlv">
<img alt="点击加入QQ交流②群" src="https://img.shields.io/badge/QQ%E4%BA%A4%E6%B5%81%E7%BE%A4-549174561-ff69b4"/>
</a>
</p>
@@ -42,46 +45,33 @@ Starter支持微信优惠券代金券、商家券、智慧商圈、商家
<dependency>
<groupId>cn.felord</groupId>
<artifactId>payment-spring-boot-starter</artifactId>
<version>1.0.17.RELEASE</version>
<version>1.0.20.RELEASE</version>
</dependency>
```
## JDK问题
**推荐使用Open JDK**,原因参见[FBI Warning](https://github.com/NotFound403/payment-spring-boot/issues/5)
**推荐使用Open JDK**,原因参见[FBI Warning](https://github.com/dromara/payment-spring-boot/issues/5)
## 文档地址
- [payment-spring-boot GitHub文档](https://notfound403.github.io/payment-spring-boot)
## 目前已经实现所有服务商和直连商户接口
- 实现微信支付多商户
- 集成支付宝SDK、快速接入Spring Boot
- 实现微信支付V3 基础支付
- 实现微信支付V3 合单支付
- 实现微信支付V3 代金券
- 实现微信支付V3 微信支付分
- 实现微信支付V3 先享卡
- 实现微信支付V3 商家券
- 实现微信支付V3 批量转账到零钱
更新日志参考[changelog](https://notfound403.github.io/payment-spring-boot/#/changelog)
- [payment-spring-boot GitHub文档](https://dromara.github.io/payment-spring-boot)
## API清单
API结构如下
![](https://asset.felord.cn/blog/20220613092244.png)
具体分为**直连商户**和**服务商**两个体系,请详细阅读文档说明
目前已经实现绝大部分微信支付直连商户和服务商的接口具体的API明细可查看[API清单](https://dromara.github.io/payment-spring-boot/#/wechat_v3_api)
> 随着版本迭代功能会增加也可通过API注册表类`WechatPayV3Type`进行API接口检索。
> 随着版本迭代功能会增加可通过API注册表类`WechatPayV3Type`进行API接口检索。
## CHANGELOG
更新日志[CHANGELOG](https://dromara.github.io/payment-spring-boot/#/changelog)
## 使用入门
### 集成配置
关于集成配置请详细阅读[payment-spring-boot GitHub文档](https://notfound403.github.io/payment-spring-boot)
中[快速接入](https://notfound403.github.io/payment-spring-boot/#/quick_start)章节
关于集成配置请详细阅读[payment-spring-boot GitHub文档](https://dromara.github.io/payment-spring-boot)
中[快速接入](https://dromara.github.io/payment-spring-boot/#/quick_start)章节
### 调用示例
@@ -360,11 +350,6 @@ public class CallbackController {
## 仓库地址
- [GitHub](https://github.com/NotFound403/payment-spring-boot)
- [Gitee](https://gitee.com/felord/payment-spring-boot)
## QQ交流群
为了交流解惑新建QQ群可通过扫码进入。
![QQ交流群](./docs/img/qqun.png)
- [GitHub](https://github.com/dromara/payment-spring-boot)
- [Gitee](https://gitee.com/dromara/payment-spring-boot)

View File

@@ -35,7 +35,7 @@
<dependency>
<groupId>cn.felord</groupId>
<artifactId>payment-spring-boot-starter</artifactId>
<version>1.0.17.RELEASE</version>
<version>1.0.20.RELEASE</version>
</dependency>
```
## 采用技术
@@ -51,4 +51,4 @@
## **免责声明**
**<span style="color:red;">本项目涉及到资金交易开发,开发者需要经严格测试后方能用于生产环境,本项目不对使用者的行为负责。</span>**
**<span style="color:red;">本项目涉及到资金交易开发,开发者需要经严格测试后方能用于生产环境,本项目不对使用者的行为负责。</span>**

View File

@@ -2,6 +2,6 @@
* [项目简介](README.md)
* [快速接入](quick_start.md)
* [JavaDoc](apidocs/index.html ':ignore')
* [微信支付V3接口文档](wechat_v3_api.md)
* [Payment微信支付V3接口文档](wechat_v3_api.md)
* [日常踩坑](stackoverflow.md)
* [更新日志](changelog.md)

View File

@@ -1,3 +1,20 @@
## 1.0.18.RELEASE
### 微信支付
- enhance: 使用`ResourceLoader`加载资源以改善Docker容器环境下的文件挂载问题
- enhance: 修改了微信支付配置加载机制,现在可以借助于`WechatTenantService`实现不停机维护微信支付参数的能力
- factor: 移除过时的V2退款API相关参数`RefundModel``RefundQueryModel`
- docs: 更新文档地址到[dromara.org](https://gitee.com/dromara),现在你可以通过[https://dromara.org/payment-spring-boot/](https://dromara.org/payment-spring-boot/)访问项目文档
- docs: 修正文档描述错误
## 1.0.17.RELEASE
### 微信支付
- feat: 直连商户合单支付增加查询单笔退款
- feat: 支付分增加退款独立的API
- factor: 营销图片上传API现在由WechatMediaApi#marketingImageUpload实现以代替WechatMarketingFavorApi#marketingImageUpload,旧实现已标记为过时
- factor:时间格式优化移除时区限制为东八区由LocalDateTime改为OffsetDateTime
- docs: 现在可以通过API清单检索API了
## 1.0.16.RELEASE
### 微信支付
- feat: 直连商户-委托营销相关API实现
@@ -186,4 +203,4 @@
- 多租户
- 支付宝
- 仅仅引入支付宝SDK后续维护以支付宝SDK变动为准
- 支付宝暂时不支持多租户
- 支付宝暂时不支持多租户

View File

@@ -4,7 +4,7 @@
<dependency>
<groupId>cn.felord</groupId>
<artifactId>payment-spring-boot-starter</artifactId>
<version>1.0.17.RELEASE</version>
<version>1.0.20.RELEASE</version>
</dependency>
```
> 基于 **Spring Boot 2.x**
@@ -174,4 +174,4 @@ public class PayConfig {
System.out.println("execute = " + execute.getBody());
}
```
```

View File

@@ -10,8 +10,8 @@
#### 基础支付
- [x] `WechatDirectPayApi` 基础支付,通过`WechatApiProvider#directPayApi`初始化
- [x] `jsPay` APP下单
- [x] `appPay` JSAPI/小程序下单
- [x] `jsPay` JSAPI/小程序下单
- [x] `appPay` APP下单
- [x] `h5Pay` H5下单
- [x] `nativePay` Native下单
- [x] 查询订单
@@ -25,8 +25,8 @@
- [x] `downloadTradeBill` 申请交易账单直接下载为gzip或者txt文件
- [x] `downloadFundFlowBill` 申请资金账单直接下载为gzip或者txt文件
- [x] `WechatCombinePayApi` 合单支付,通过`WechatApiProvider#combinePayApi`初始化
- [x] `jsPay` 合单APP下单
- [x] `appPay` 合单JSAPI/小程序下单
- [x] `jsPay` 合单JSAPI/小程序下单
- [x] `appPay` 合单APP下单
- [x] `h5Pay` 合单H5下单
- [x] `nativePay` 合单Native下单
- [x] `queryTransactionByOutTradeNo` 查询订单,**合单支付目前只支持商户订单号查询**
@@ -153,7 +153,15 @@
##### 支付有礼
- [ ] 功能实现中……
- [x] `WechatMarketingPayGiftActivityApi` 支付有礼,通过`WechatApiProvider#marketingPayGiftActivityApi`初始化
- [x] `create` 创建全场满额送活动
- [x] `details` 查询活动详情接口
- [x] `merchants` 查询活动发券商户号
- [x] `goods` 查询活动指定商品列表
- [x] `terminate` 终止活动
- [x] `addMches` 新增活动发券商户号
- [x] `page` 获取支付有礼活动列表
- [x] `deleteMch` 删除活动发券商户号
##### 图片上传(营销专用)
@@ -186,9 +194,6 @@
- [x] 申请转账明细电子回单
1. `transferElectronic` 受理转账明细电子回单
2. `queryTransferElectronicResult` 查询转账账单电子回单接口
- [x] 申请转账电子回单
1. `` 转账账单电子回单申请受理接口
2. `` 查询转账账单电子回单接口
##### 分账
@@ -224,4 +229,8 @@
- [x] `mediaVideoUpload` 视频上传
- [x] `marketingImageUpload` 营销图片上传
> 通过营销**图片上传API**上传图片后可获得图片url地址。图片url可在微信支付营销相关的API使用包括商家券、代金券、支付有礼等。
> 通过营销**图片上传API**上传图片后可获得图片url地址。图片url可在微信支付营销相关的API使用包括商家券、代金券、支付有礼等。
### 服务商
施工中……

View File

@@ -22,11 +22,11 @@
<parent>
<groupId>cn.felord</groupId>
<artifactId>payment-spring-boot</artifactId>
<version>1.0.17.RELEASE</version>
<version>1.0.20.RELEASE</version>
</parent>
<artifactId>payment-spring-boot-autoconfigure</artifactId>
<version>1.0.17.RELEASE</version>
<version>1.0.20.RELEASE</version>
<packaging>jar</packaging>
<modelVersion>4.0.0</modelVersion>
@@ -92,4 +92,4 @@
</plugin>
</plugins>
</build>
</project>
</project>

View File

@@ -20,10 +20,13 @@ package cn.felord.payment.wechat;
import cn.felord.payment.wechat.v3.KeyPairFactory;
import cn.felord.payment.wechat.v3.WechatMetaBean;
import lombok.AllArgsConstructor;
import org.springframework.core.io.ClassPathResource;
import org.springframework.core.io.FileSystemResource;
import org.springframework.core.io.Resource;
import org.springframework.core.io.ResourceLoader;
import org.springframework.util.CollectionUtils;
import org.springframework.util.ResourceUtils;
import java.util.HashSet;
import java.util.Map;
import java.util.Set;
import java.util.stream.Collectors;
@@ -31,32 +34,39 @@ import java.util.stream.Collectors;
/**
* 从配置文件中加载租户信息,默认实现,可被覆盖
*
* @author xiafang
* @author dax
* @since 2023/2/3 11:40
*/
@AllArgsConstructor
public class InMemoryWechatTenantService implements WechatTenantService {
private final WechatPayProperties wechatPayProperties;
private final ResourceLoader resourceLoader;
private final Set<WechatMetaBean> cache = new HashSet<>();
@Override
public Set<WechatMetaBean> loadTenants() {
Map<String, WechatPayProperties.V3> v3Map = wechatPayProperties.getV3();
KeyPairFactory keyPairFactory = new KeyPairFactory();
return v3Map.entrySet()
.stream()
.map(entry -> {
WechatPayProperties.V3 v3 = entry.getValue();
String tenantId = entry.getKey();
String certPath = v3.getCertPath();
String certAbsolutePath = v3.getCertAbsolutePath();
String mchId = v3.getMchId();
Resource resource = certAbsolutePath != null ? new FileSystemResource(certAbsolutePath) :
new ClassPathResource(certPath == null ? "wechat/apiclient_cert.p12" : certPath);
WechatMetaBean wechatMetaBean = keyPairFactory.initWechatMetaBean(resource, mchId);
wechatMetaBean.setV3(v3);
wechatMetaBean.setTenantId(tenantId);
return wechatMetaBean;
})
.collect(Collectors.toSet());
if (CollectionUtils.isEmpty(cache)) {
Map<String, WechatPayProperties.V3> v3Map = wechatPayProperties.getV3();
KeyPairFactory keyPairFactory = new KeyPairFactory();
Set<WechatMetaBean> beans = v3Map.entrySet()
.stream()
.map(entry -> {
WechatPayProperties.V3 v3 = entry.getValue();
String tenantId = entry.getKey();
String certPath = v3.getCertPath();
String certAbsolutePath = v3.getCertAbsolutePath();
String mchId = v3.getMchId();
Resource resource = certAbsolutePath != null ? new FileSystemResource(certAbsolutePath) :
resourceLoader.getResource(certPath == null ? "classpath:wechat/apiclient_cert.p12" :
certPath.startsWith(ResourceUtils.CLASSPATH_URL_PREFIX) ? certPath : ResourceUtils.CLASSPATH_URL_PREFIX + certPath);
WechatMetaBean wechatMetaBean = keyPairFactory.initWechatMetaBean(resource, mchId);
wechatMetaBean.setV3(v3);
wechatMetaBean.setTenantId(tenantId);
return wechatMetaBean;
})
.collect(Collectors.toSet());
cache.addAll(beans);
}
return cache;
}
}

View File

@@ -43,9 +43,7 @@ public class WechatPayConfiguration {
@Bean
@ConditionalOnMissingBean
WechatMetaContainer wechatMetaContainer(WechatTenantService wechatTenantService) {
WechatMetaContainer container = new WechatMetaContainer();
container.addWechatMetas(wechatTenantService.loadTenants());
return container;
return new WechatMetaContainer(wechatTenantService);
}
/**

View File

@@ -22,6 +22,7 @@ import org.springframework.boot.context.properties.EnableConfigurationProperties
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Conditional;
import org.springframework.context.annotation.Configuration;
import org.springframework.core.io.ResourceLoader;
/**
* The type Wechat tenant service configuration.
@@ -42,7 +43,7 @@ public class WechatTenantServiceConfiguration {
*/
@Bean
@ConditionalOnMissingBean
public WechatTenantService wechatTenantService(WechatPayProperties wechatPayProperties) {
return new InMemoryWechatTenantService(wechatPayProperties);
public WechatTenantService wechatTenantService(WechatPayProperties wechatPayProperties, ResourceLoader resourceLoader) {
return new InMemoryWechatTenantService(wechatPayProperties, resourceLoader);
}
}

View File

@@ -0,0 +1,58 @@
/*
* Copyright 2019-2022 felord.cn
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* https://www.apache.org/licenses/LICENSE-2.0
* Website:
* https://felord.cn
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package cn.felord.payment.wechat.enumeration;
/**
* The enum Activity status.
*
* @author dax
* @since 1.0.19.RELEASE
*/
public enum ActivityStatus {
/**
* 状态未知
*/
ACT_STATUS_UNKNOWN,
/**
* 已创建
*/
CREATE_ACT_STATUS,
/**
* 运行中
*/
ONGOING_ACT_STATUS,
/**
* 已终止
*/
TERMINATE_ACT_STATUS,
/**
* 已暂停
*/
STOP_ACT_STATUS,
/**
* 已过期
*/
OVER_TIME_ACT_STATUS,
/**
* 创建活动失败
*/
CREATE_ACT_FAILED
}

View File

@@ -15,11 +15,17 @@
* limitations under the License.
*/
package cn.felord.payment.wechat.v2.model;
package cn.felord.payment.wechat.enumeration;
/**
* @author felord.cn
* @since 1.0.4.RELEASE
* The enum Award type.
*
* @author dax
* @since 1.0.19.RELEASE
*/
public class RefundQueryModel {
public enum AwardType {
/**
* 商家券
*/
BUSIFAVOR
}

View File

@@ -0,0 +1,71 @@
/*
* Copyright 2019-2022 felord.cn
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* https://www.apache.org/licenses/LICENSE-2.0
* Website:
* https://felord.cn
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package cn.felord.payment.wechat.enumeration;
/**
* The enum Business cert type.
*
* @author dax
* @since 2023 /7/1 8:34
*/
public enum BusinessCertType {
/**
* 事业单位法人证书
*/
CERTIFICATE_TYPE_2388,
/**
* 统一社会信用代码证书
*/
CERTIFICATE_TYPE_2389,
/**
* 社会团体法人登记证书
*/
CERTIFICATE_TYPE_2394,
/**
* 民办非企业单位登记证书
*/
CERTIFICATE_TYPE_2395,
/**
* 基金会法人登记证书
*/
CERTIFICATE_TYPE_2396,
/**
* 宗教活动场所登记证
*/
CERTIFICATE_TYPE_2399,
/**
* 政府部门下发的其他有效证明文件
*/
CERTIFICATE_TYPE_2400,
/**
* 执业许可证/执业证
*/
CERTIFICATE_TYPE_2520,
/**
* 基层群众性自治组织特别法人统一社会信用代码证
*/
CERTIFICATE_TYPE_2521,
/**
* 农村集体经济组织登记证
*/
CERTIFICATE_TYPE_2522
}

View File

@@ -28,41 +28,57 @@ public enum CouponBgColor {
/**
* Color 010 coupon bg color.
*/
COLOR010,
COLOR010("Color010"),
/**
* COLOR 020 coupon bg color.
*/
COLOR020,
COLOR020("Color010"),
/**
* COLOR 030 coupon bg color.
*/
COLOR030,
COLOR030("Color010"),
/**
* COLOR 040 coupon bg color.
*/
COLOR040,
COLOR040("Color010"),
/**
* COLOR 050 coupon bg color.
*/
COLOR050,
COLOR050("Color010"),
/**
* COLOR 060 coupon bg color.
*/
COLOR060,
COLOR060("Color010"),
/**
* COLOR 070 coupon bg color.
*/
COLOR070,
COLOR070("Color010"),
/**
* COLOR 080 coupon bg color.
*/
COLOR080,
COLOR080("Color010"),
/**
* COLOR 090 coupon bg color.
*/
COLOR090,
COLOR090("Color010"),
/**
* COLOR 100 coupon bg color.
*/
COLOR100
COLOR100("Color010");
private final String value;
CouponBgColor(String value) {
this.value = value;
}
/**
* Gets value.
*
* @return the value
*/
public String getValue() {
return value;
}
}

View File

@@ -0,0 +1,35 @@
/*
* Copyright 2019-2022 felord.cn
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* https://www.apache.org/licenses/LICENSE-2.0
* Website:
* https://felord.cn
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package cn.felord.payment.wechat.enumeration;
/**
* The enum Delivery purpose.
*
* @author felord.cn
* @since 1.0.19.RELEASE
*/
public enum DeliveryPurpose {
/**
* 拉用户回店消费
*/
OFF_LINE_PAY,
/**
* 引导用户前往小程序消费
*/
JUMP_MINI_APP
}

View File

@@ -0,0 +1,33 @@
/*
* Copyright 2019-2022 felord.cn
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* https://www.apache.org/licenses/LICENSE-2.0
* Website:
* https://felord.cn
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package cn.felord.payment.wechat.enumeration;
/**
* @author dax
* @since 1.0.19.RELEASE
*/
public enum DeliveryUserCategory {
/**
* 所有用户
*/
DELIVERY_ALL_PERSON,
/**
* 会员用户
*/
DELIVERY_MEMBER_PERSON
}

View File

@@ -0,0 +1,35 @@
/*
* Copyright 2019-2022 felord.cn
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* https://www.apache.org/licenses/LICENSE-2.0
* Website:
* https://felord.cn
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package cn.felord.payment.wechat.enumeration;
/**
* The enum Send content.
*
* @author dax
* @since 1.0.19.RELEASE
*/
public enum SendContent {
/**
* 单张券
*/
SINGLE_COUPON,
/**
* 礼包
*/
GIFT_PACKAGE
}

View File

@@ -20,7 +20,7 @@ package cn.felord.payment.wechat.enumeration;
import lombok.Getter;
/**
* @author xiafang
* @author dax
* @since 2023/2/1 8:59
*/
@Getter

View File

@@ -507,6 +507,55 @@ public enum WechatPayV3Type {
*/
MARKETING_PARTNERSHIPS_GET(HttpMethod.GET, "%s/v3/marketing/partnerships"),
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
/**
* 创建全场满额送活动API
*
* @since 1.0.19.RELEASES
*/
MARKETING_PAYGIFTACTIVITY(HttpMethod.POST, "%s/v3/marketing/paygiftactivity/unique-threshold-activity"),
/**
* 查询活动详情接口API
*
* @since 1.0.19.RELEASES
*/
MARKETING_PAYGIFTACTIVITY_DETAIL(HttpMethod.GET, "%s/v3/marketing/paygiftactivity/activities/{activity_id}"),
/**
* 查询活动发券商户号API
*
* @since 1.0.19.RELEASES
*/
MARKETING_PAYGIFTACTIVITY_MCH(HttpMethod.GET, "%s/v3/marketing/paygiftactivity/activities/{activity_id}/merchants"),
/**
* 查询活动指定商品列表API
*
* @since 1.0.19.RELEASES
*/
MARKETING_PAYGIFTACTIVITY_GOODS(HttpMethod.GET, "%s/v3/marketing/paygiftactivity/activities/{activity_id}/goods"),
/**
* 终止活动API
*
* @since 1.0.19.RELEASES
*/
MARKETING_PAYGIFTACTIVITY_TERMINATE(HttpMethod.POST, "%s/v3/marketing/paygiftactivity/activities/{activity_id}/terminate"),
/**
* 新增活动发券商户号API
*
* @since 1.0.19.RELEASES
*/
MARKETING_PAYGIFTACTIVITY_MCH_ADD(HttpMethod.POST, "%s/v3/marketing/paygiftactivity/activities/{activity_id}/merchants/add"),
/**
* 获取支付有礼活动列表API
*
* @since 1.0.19.RELEASES
*/
MARKETING_PAYGIFTACTIVITY_ACTIVITIES(HttpMethod.GET, "%s/v3/marketing/paygiftactivity/activities"),
/**
* 删除活动发券商户号API
*
* @since 1.0.19.RELEASES
*/
MARKETING_PAYGIFTACTIVITY_MCH_DEL(HttpMethod.POST, "%s/v3/marketing/paygiftactivity/activities/{activity_id}/merchants/delete"),
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
/**
* 发起批量转账API.

View File

@@ -31,6 +31,9 @@ import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.PropertyNamingStrategy;
import com.fasterxml.jackson.databind.node.ObjectNode;
import com.fasterxml.jackson.datatype.jsr310.JavaTimeModule;
import com.fasterxml.jackson.datatype.jsr310.ser.LocalDateSerializer;
import com.fasterxml.jackson.datatype.jsr310.ser.LocalDateTimeSerializer;
import com.fasterxml.jackson.datatype.jsr310.ser.LocalTimeSerializer;
import org.springframework.core.io.Resource;
import org.springframework.http.ContentDisposition;
import org.springframework.http.HttpHeaders;
@@ -44,6 +47,8 @@ import org.springframework.web.util.UriComponentsBuilder;
import java.net.URI;
import java.time.LocalDate;
import java.time.LocalDateTime;
import java.time.LocalTime;
import java.time.format.DateTimeFormatter;
import java.util.Objects;
import java.util.Optional;
@@ -92,12 +97,16 @@ public abstract class AbstractApi {
* @param mapper the mapper
*/
private void applyObjectMapper(ObjectMapper mapper) {
JavaTimeModule javaTimeModule = new JavaTimeModule();
javaTimeModule.addSerializer(LocalDate.class, new LocalDateSerializer(DateTimeFormatter.ISO_LOCAL_DATE));
javaTimeModule.addSerializer(LocalDateTime.class, new LocalDateTimeSerializer(DateTimeFormatter.ISO_LOCAL_DATE_TIME));
javaTimeModule.addSerializer(LocalTime.class, new LocalTimeSerializer(DateTimeFormatter.ISO_LOCAL_TIME));
mapper.setPropertyNamingStrategy(PropertyNamingStrategy.SNAKE_CASE)
.configure(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES, false)
// empty string error
.configure(DeserializationFeature.ACCEPT_EMPTY_STRING_AS_NULL_OBJECT, true)
.setSerializationInclusion(JsonInclude.Include.NON_NULL)
.registerModule(new JavaTimeModule());
.registerModule(javaTimeModule);
}

View File

@@ -27,11 +27,7 @@ import com.fasterxml.jackson.databind.node.ObjectNode;
import lombok.SneakyThrows;
import lombok.extern.slf4j.Slf4j;
import org.bouncycastle.jce.provider.BouncyCastleProvider;
import org.springframework.http.HttpHeaders;
import org.springframework.http.HttpMethod;
import org.springframework.http.MediaType;
import org.springframework.http.RequestEntity;
import org.springframework.http.ResponseEntity;
import org.springframework.http.*;
import org.springframework.http.converter.HttpMessageConverter;
import org.springframework.http.converter.xml.MappingJackson2XmlHttpMessageConverter;
import org.springframework.util.AlternativeJdkIdGenerator;
@@ -54,8 +50,7 @@ import java.security.cert.Certificate;
import java.security.cert.CertificateException;
import java.security.cert.CertificateFactory;
import java.security.cert.X509Certificate;
import java.time.LocalDateTime;
import java.time.ZoneOffset;
import java.time.Instant;
import java.util.*;
import java.util.stream.Collectors;
@@ -135,7 +130,7 @@ public class SignatureProvider {
@SneakyThrows
public String requestSign(String tenantId, String method, String canonicalUrl, String body) {
long timestamp = LocalDateTime.now().toEpochSecond(ZoneOffset.of("+8"));
long timestamp = Instant.now().getEpochSecond();
String nonceStr = nonceStrGenerator.generateId()
.toString()
.replaceAll("-", "");
@@ -175,7 +170,6 @@ public class SignatureProvider {
* @param params the params
* @return the boolean
*/
@SneakyThrows
public boolean responseSignVerify(ResponseSignVerifyParams params) {
String wechatpaySerial = params.getWechatpaySerial();
@@ -190,13 +184,15 @@ public class SignatureProvider {
.orElseThrow(() -> new PayException("cannot obtain the certificate"));
});
final String signatureStr = createSign(params.getWechatpayTimestamp(), params.getWechatpayNonce(), params.getBody());
Signature signer = Signature.getInstance("SHA256withRSA", BC_PROVIDER);
signer.initVerify(certificate.getX509Certificate());
signer.update(signatureStr.getBytes(StandardCharsets.UTF_8));
return signer.verify(Base64Utils.decodeFromString(params.getWechatpaySignature()));
try {
final String signatureStr = createSign(params.getWechatpayTimestamp(), params.getWechatpayNonce(), params.getBody());
Signature signer = Signature.getInstance("SHA256withRSA", BC_PROVIDER);
signer.initVerify(certificate.getX509Certificate());
signer.update(signatureStr.getBytes(StandardCharsets.UTF_8));
return signer.verify(Base64Utils.decodeFromString(params.getWechatpaySignature()));
} catch (Exception e) {
throw new PayException("An exception occurred during the response verification, the cause: " + e.getMessage());
}
}
@@ -234,12 +230,9 @@ public class SignatureProvider {
throw new PayException("cant obtain the response body");
}
ArrayNode certificates = bodyObjectNode.withArray("data");
if (certificates.isArray() && certificates.size() > 0) {
CERTIFICATE_SET.forEach(x509WechatCertificateInfo -> {
if (Objects.equals(tenantId, x509WechatCertificateInfo.getTenantId())) {
CERTIFICATE_SET.remove(x509WechatCertificateInfo);
}
});
if (certificates.isArray() && !certificates.isEmpty()) {
CERTIFICATE_SET.removeIf(x509WechatCertificateInfo ->
Objects.equals(tenantId, x509WechatCertificateInfo.getTenantId()));
final CertificateFactory certificateFactory = CertificateFactory.getInstance("X509", BC_PROVIDER);
certificates.forEach(objectNode -> {
JsonNode encryptCertificate = objectNode.get("encrypt_certificate");

View File

@@ -140,6 +140,17 @@ public class WechatApiProvider {
return new WechatMarketingPartnershipApi(this.wechatPayClient, tenantId);
}
/**
* 支付有礼-直连商户
*
* @param tenantId the tenant id
* @return the wechat marketing pay gift activity api
* @since 1.0.19.RELEASE
*/
public WechatMarketingPayGiftActivityApi marketingPayGiftActivityApi(String tenantId) {
return new WechatMarketingPayGiftActivityApi(this.wechatPayClient, tenantId);
}
/**
* 批量转账到零钱.
* <p>

View File

@@ -158,7 +158,9 @@ public class WechatMarketingFavorApi extends AbstractApi {
WechatPayProperties.V3 v3 = this.wechatMetaBean().getV3();
params.setAppid(v3.getAppId());
params.setStockCreatorMchid(v3.getMchId());
if (StringUtils.hasText(params.getStockCreatorMchid())){
params.setStockCreatorMchid(v3.getMchId());
}
URI uri = UriComponentsBuilder.fromHttpUrl(type.uri(WeChatServer.CHINA))
.build()
.expand(params.getOpenid())

View File

@@ -0,0 +1,232 @@
/*
* Copyright 2019-2022 felord.cn
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* https://www.apache.org/licenses/LICENSE-2.0
* Website:
* https://felord.cn
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package cn.felord.payment.wechat.v3;
import cn.felord.payment.wechat.enumeration.WeChatServer;
import cn.felord.payment.wechat.enumeration.WechatPayV3Type;
import cn.felord.payment.wechat.v3.model.paygiftactivity.ActivitiesListPageRequest;
import cn.felord.payment.wechat.v3.model.paygiftactivity.ActivitiesPageRequest;
import cn.felord.payment.wechat.v3.model.paygiftactivity.DeleteActivityMchRequest;
import cn.felord.payment.wechat.v3.model.paygiftactivity.GiftActivityParams;
import cn.felord.payment.wechat.v3.model.paygiftactivity.NewActivityMchRequest;
import com.fasterxml.jackson.databind.node.ObjectNode;
import org.springframework.web.util.UriComponentsBuilder;
import java.net.URI;
import java.util.Collections;
import java.util.HashMap;
import java.util.Map;
/**
* 支付有礼
*
* @author dax
* @since 1.0.19.RELEASE
*/
public class WechatMarketingPayGiftActivityApi extends AbstractApi {
/**
* Instantiates a new Abstract api.
*
* @param wechatPayClient the wechat pay client
* @param tenantId the tenant id
*/
public WechatMarketingPayGiftActivityApi(WechatPayClient wechatPayClient, String tenantId) {
super(wechatPayClient, tenantId);
}
/**
* 创建全场满额送活动API
*
* @param params the params
* @return the wechat response entity
*/
public WechatResponseEntity<ObjectNode> create(GiftActivityParams params) {
WechatResponseEntity<ObjectNode> wechatResponseEntity = new WechatResponseEntity<>();
this.client().withType(WechatPayV3Type.MARKETING_PAYGIFTACTIVITY, params)
.function((type, activityParams) -> {
URI uri = UriComponentsBuilder.fromHttpUrl(type.uri(WeChatServer.CHINA))
.build()
.toUri();
return Post(uri, activityParams);
})
.consumer(wechatResponseEntity::convert)
.request();
return wechatResponseEntity;
}
/**
* 查询活动详情接口API
*
* @param activityId the activity id
* @return the wechat response entity
*/
public WechatResponseEntity<ObjectNode> details(String activityId) {
WechatResponseEntity<ObjectNode> wechatResponseEntity = new WechatResponseEntity<>();
this.client().withType(WechatPayV3Type.MARKETING_PAYGIFTACTIVITY_DETAIL, activityId)
.function((type, param) -> {
URI uri = UriComponentsBuilder.fromHttpUrl(type.uri(WeChatServer.CHINA))
.build()
.expand(param)
.toUri();
return Get(uri);
})
.consumer(wechatResponseEntity::convert)
.request();
return wechatResponseEntity;
}
/**
* 查询活动发券商户号API
*
* @param request the request
* @return the wechat response entity
*/
public WechatResponseEntity<ObjectNode> merchants(ActivitiesPageRequest request) {
WechatResponseEntity<ObjectNode> wechatResponseEntity = new WechatResponseEntity<>();
this.client().withType(WechatPayV3Type.MARKETING_PAYGIFTACTIVITY_MCH, request)
.function((type, params) -> {
URI uri = UriComponentsBuilder.fromHttpUrl(type.uri(WeChatServer.CHINA))
.queryParam("offset", params.getOffset())
.queryParam("limit", params.getLimit())
.build()
.expand(params.getActivityId())
.toUri();
return Get(uri);
})
.consumer(wechatResponseEntity::convert)
.request();
return wechatResponseEntity;
}
/**
* 查询活动指定商品列表API
*
* @param request the request
* @return the wechat response entity
*/
public WechatResponseEntity<ObjectNode> goods(ActivitiesPageRequest request) {
WechatResponseEntity<ObjectNode> wechatResponseEntity = new WechatResponseEntity<>();
this.client().withType(WechatPayV3Type.MARKETING_PAYGIFTACTIVITY_GOODS, request)
.function((type, params) -> {
URI uri = UriComponentsBuilder.fromHttpUrl(type.uri(WeChatServer.CHINA))
.queryParam("offset", params.getOffset())
.queryParam("limit", params.getLimit())
.build()
.expand(params.getActivityId())
.toUri();
return Get(uri);
})
.consumer(wechatResponseEntity::convert)
.request();
return wechatResponseEntity;
}
/**
* 终止活动API
*
* @param activityId the activity id
* @return the wechat response entity
*/
public WechatResponseEntity<ObjectNode> terminate(String activityId) {
WechatResponseEntity<ObjectNode> wechatResponseEntity = new WechatResponseEntity<>();
this.client().withType(WechatPayV3Type.MARKETING_PAYGIFTACTIVITY_TERMINATE, activityId)
.function((type, param) -> {
URI uri = UriComponentsBuilder.fromHttpUrl(type.uri(WeChatServer.CHINA))
.build()
.expand(param)
.toUri();
return Post(uri, Collections.emptyMap());
})
.consumer(wechatResponseEntity::convert)
.request();
return wechatResponseEntity;
}
/**
* 新增活动发券商户号API
*
* @param request the request
* @return the wechat response entity
*/
public WechatResponseEntity<ObjectNode> addMches(NewActivityMchRequest request) {
WechatResponseEntity<ObjectNode> wechatResponseEntity = new WechatResponseEntity<>();
this.client().withType(WechatPayV3Type.MARKETING_PAYGIFTACTIVITY_MCH_ADD, request)
.function((type, params) -> {
URI uri = UriComponentsBuilder.fromHttpUrl(type.uri(WeChatServer.CHINA))
.build()
.expand(params.getActivityId())
.toUri();
Map<String, Object> body = new HashMap<>();
body.put("merchant_id_list", params.getMerchantIdList());
body.put("add_request_no", params.getAddRequestNo());
return Post(uri, body);
})
.consumer(wechatResponseEntity::convert)
.request();
return wechatResponseEntity;
}
/**
* 获取支付有礼活动列表API
*
* @param request the request
* @return the wechat response entity
*/
public WechatResponseEntity<ObjectNode> page(ActivitiesListPageRequest request) {
WechatResponseEntity<ObjectNode> wechatResponseEntity = new WechatResponseEntity<>();
this.client().withType(WechatPayV3Type.MARKETING_PAYGIFTACTIVITY_ACTIVITIES, request)
.function((type, params) -> {
URI uri = UriComponentsBuilder.fromHttpUrl(type.uri(WeChatServer.CHINA))
.queryParam("offset", params.getOffset())
.queryParam("limit", params.getLimit())
.queryParam("activity_name", params.getActivityName())
.queryParam("activity_status", params.getActivityStatus())
.queryParam("award_type", params.getAwardType())
.build()
.toUri();
return Get(uri);
})
.consumer(wechatResponseEntity::convert)
.request();
return wechatResponseEntity;
}
/**
* 删除活动发券商户号API
*
* @param request the request
* @return the wechat response entity
*/
public WechatResponseEntity<ObjectNode> deleteMch(DeleteActivityMchRequest request) {
WechatResponseEntity<ObjectNode> wechatResponseEntity = new WechatResponseEntity<>();
this.client().withType(WechatPayV3Type.MARKETING_PAYGIFTACTIVITY_MCH_DEL, request)
.function((type, params) -> {
URI uri = UriComponentsBuilder.fromHttpUrl(type.uri(WeChatServer.CHINA))
.build()
.expand(params.getActivityId())
.toUri();
Map<String, Object> body = new HashMap<>();
body.put("merchant_id_list", params.getMerchantIdList());
body.put("delete_request_no", params.getDeleteRequestNo());
return Post(uri, body);
})
.consumer(wechatResponseEntity::convert)
.request();
return wechatResponseEntity;
}
}

View File

@@ -17,9 +17,15 @@
package cn.felord.payment.wechat.v3;
import java.util.*;
import cn.felord.payment.wechat.WechatTenantService;
import lombok.AllArgsConstructor;
import java.util.Collection;
import java.util.Map;
import java.util.Objects;
import java.util.Set;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.ConcurrentSkipListSet;
import java.util.stream.Collectors;
/**
* 配置容器
@@ -27,10 +33,10 @@ import java.util.concurrent.ConcurrentSkipListSet;
* @author felord.cn
* @since 1.0.0.RELEASE
*/
@AllArgsConstructor
public class WechatMetaContainer {
private final Map<String, WechatMetaBean> wechatMetaBeanMap = new ConcurrentHashMap<>();
private final Set<String> tenantIds = new ConcurrentSkipListSet<>();
private final WechatTenantService wechatTenantService;
/**
* Add wechat metas.
@@ -43,22 +49,9 @@ public class WechatMetaContainer {
private void addMeta(WechatMetaBean wechatMetaBean) {
String tenantId = wechatMetaBean.getTenantId();
tenantIds.add(tenantId);
wechatMetaBeanMap.put(tenantId, wechatMetaBean);
}
/**
* Remove wechat meta wechat meta bean.
*
* @param tenantId the tenantId
* @return the wechat meta bean
*/
public WechatMetaBean removeWechatMeta(String tenantId) {
tenantIds.remove(tenantId);
return this.wechatMetaBeanMap.remove(tenantId);
}
/**
* Gets wechat meta.
*
@@ -66,7 +59,14 @@ public class WechatMetaContainer {
* @return the wechat meta
*/
public WechatMetaBean getWechatMeta(String tenantId) {
return Objects.requireNonNull(this.wechatMetaBeanMap.get(tenantId));
WechatMetaBean wechatMetaBean = this.wechatMetaBeanMap.get(tenantId);
if (Objects.nonNull(wechatMetaBean)) {
return wechatMetaBean;
} else {
this.addWechatMetas(wechatTenantService.loadTenants());
return Objects.requireNonNull(this.wechatMetaBeanMap.get(tenantId),
"cant obtain the config with tenant: "+tenantId);
}
}
/**
@@ -75,6 +75,9 @@ public class WechatMetaContainer {
* @return the properties keys
*/
public Set<String> getTenantIds() {
return tenantIds;
return wechatTenantService.loadTenants()
.stream()
.map(WechatMetaBean::getTenantId)
.collect(Collectors.toSet());
}
}

View File

@@ -80,7 +80,7 @@ public class WechatPartnerPayApi extends AbstractApi {
WechatMetaBean wechatMetaBean = wechatMetaContainer.getWechatMeta(tenantId());
PrivateKey privateKey = wechatMetaBean.getKeyPair().getPrivate();
String subAppid = partnerPayParams.getSubAppid();
String spAppid = partnerPayParams.getSpAppid();
long epochSecond = LocalDateTime.now()
.toEpochSecond(ZoneOffset.of("+8"));
String timestamp = String.valueOf(epochSecond);
@@ -89,9 +89,8 @@ public class WechatPartnerPayApi extends AbstractApi {
.toString()
.replaceAll("-", "");
String prepayId = body.get("prepay_id").asText();
String paySign = signatureProvider.doRequestSign(privateKey, subAppid, timestamp, nonceStr, prepayId);
body.put("appid", subAppid);
String paySign = signatureProvider.doRequestSign(privateKey, spAppid, timestamp, nonceStr, prepayId);
body.put("appid", spAppid);
body.put("partnerid", partnerPayParams.getSubMchid());
body.put("prepayid", prepayId);
body.put("package", "Sign=WXPay");
@@ -129,7 +128,7 @@ public class WechatPartnerPayApi extends AbstractApi {
WechatMetaBean wechatMetaBean = wechatMetaContainer.getWechatMeta(tenantId());
PrivateKey privateKey = wechatMetaBean.getKeyPair().getPrivate();
String subAppid = partnerPayParams.getSubAppid();
String spAppid = partnerPayParams.getSpAppid();
long epochSecond = LocalDateTime.now()
.toEpochSecond(ZoneOffset.of("+8"));
String timestamp = String.valueOf(epochSecond);
@@ -138,9 +137,8 @@ public class WechatPartnerPayApi extends AbstractApi {
.toString()
.replaceAll("-", "");
String packageStr = "prepay_id=" + body.get("prepay_id").asText();
String paySign = signatureProvider.doRequestSign(privateKey, subAppid, timestamp, nonceStr, packageStr);
body.put("appId", subAppid);
String paySign = signatureProvider.doRequestSign(privateKey, spAppid, timestamp, nonceStr, packageStr);
body.put("appid", spAppid);
body.put("timeStamp", timestamp);
body.put("nonceStr", nonceStr);
body.put("package", packageStr);

View File

@@ -76,6 +76,7 @@ public class WechatPayScoreParkingApi extends AbstractApi {
URI uri = UriComponentsBuilder.fromHttpUrl(wechatPayV3Type.uri(WeChatServer.CHINA))
.queryParams(queryParams)
.encode()
.build()
.toUri();
return Get(uri);

View File

@@ -178,6 +178,7 @@ public class ApplymentApi extends AbstractApi {
EcommerceContactInfo contactInfo = applymentParams.getContactInfo();
contactInfo.setContactName(signatureProvider.encryptRequestMessage(contactInfo.getContactName(), x509Certificate));
contactInfo.setContactIdCardNumber(signatureProvider.encryptRequestMessage(contactInfo.getContactIdCardNumber(), x509Certificate));
contactInfo.setMobilePhone(signatureProvider.encryptRequestMessage(contactInfo.getMobilePhone(), x509Certificate));
String contactEmail = contactInfo.getContactEmail();
if (contactEmail != null) {
contactInfo.setContactEmail(signatureProvider.encryptRequestMessage(contactEmail, x509Certificate));

View File

@@ -31,7 +31,7 @@ public class PatternInfo {
/**
* 背景色
*/
private CouponBgColor backgroundColor;
private String backgroundColor;
/**
* 券详情图片
*/
@@ -49,4 +49,16 @@ public class PatternInfo {
*/
private String merchantName;
/**
* Sets background color.
*
* @param backgroundColor the background color
*/
public void setBackgroundColor(CouponBgColor backgroundColor) {
this.backgroundColor = backgroundColor.name();
}
private void setBackgroundColor(String backgroundColor) {
this.backgroundColor = backgroundColor;
}
}

View File

@@ -61,6 +61,11 @@ public class CreateBatchTransferParams {
* 指定该笔转账使用的转账场景ID
*/
private String transferSceneId;
/**
* 回调通知
* @since 1.0.20
*/
private String notifyUrl;
/**
* 转账明细.
@@ -96,4 +101,4 @@ public class CreateBatchTransferParams {
*/
private String userIdCard;
}
}
}

View File

@@ -17,7 +17,7 @@
package cn.felord.payment.wechat.v3.model.busifavor;
import cn.felord.payment.wechat.enumeration.CouponBgColor;
import cn.felord.payment.wechat.v3.WechatMarketingFavorApi;
import cn.felord.payment.wechat.v3.WechatMediaApi;
import lombok.Data;
import org.springframework.web.multipart.MultipartFile;
@@ -33,7 +33,7 @@ public class DisplayPatternInfo {
/**
* 背景颜色
*/
private CouponBgColor backgroundColor;
private String backgroundColor;
/**
* 商户logo
* <ol>
@@ -42,7 +42,7 @@ public class DisplayPatternInfo {
* </ol>
* 仅支持通过 <a target= "_blank" href= "https://pay.weixin.qq.com/wiki/doc/apiv3/wxpay/marketing/chapter3_1.shtml">图片上传API</a> 接口获取的图片URL地址。
*
* @see WechatMarketingFavorApi#marketingImageUpload(MultipartFile)
* @see WechatMediaApi#marketingImageUpload(MultipartFile)
*/
private String merchantLogoUrl;
/**
@@ -54,7 +54,7 @@ public class DisplayPatternInfo {
* </ol>
* 仅支持通过 <a target= "_blank" href= "https://pay.weixin.qq.com/wiki/doc/apiv3/wxpay/marketing/chapter3_1.shtml">图片上传API</a> 接口获取的图片URL地址。
*
* @see WechatMarketingFavorApi#marketingImageUpload(MultipartFile)
* @see WechatMediaApi#marketingImageUpload(MultipartFile)
*/
private String couponImageUrl;
/**
@@ -69,4 +69,17 @@ public class DisplayPatternInfo {
* 商户名称,字数上限为16个
*/
private String merchantName;
/**
* Sets background color.
*
* @param backgroundColor the background color
*/
public void setBackgroundColor(CouponBgColor backgroundColor) {
this.backgroundColor = backgroundColor.getValue();
}
private void setBackgroundColor(String backgroundColor) {
this.backgroundColor = backgroundColor;
}
}

View File

@@ -17,6 +17,7 @@
package cn.felord.payment.wechat.v3.model.ecommerce;
import cn.felord.payment.wechat.enumeration.BusinessCertType;
import lombok.Data;
/**
@@ -25,6 +26,7 @@ import lombok.Data;
*/
@Data
public class EcommerceBusinessLicenseInfo {
private BusinessCertType certType;
private String businessLicenseCopy;
private String businessLicenseNumber;
private String merchantName;

View File

@@ -17,13 +17,20 @@
package cn.felord.payment.wechat.v3.model.ecommerce;
import cn.felord.payment.wechat.enumeration.IdDocType;
import lombok.Data;
@Data
public class EcommerceContactInfo {
private String contactType;
private String contactName;
private IdDocType contactIdDocType;
private String contactIdCardNumber;
private String contactIdDocCopy;
private String contactIdDocCopyBack;
private String contactIdDocPeriodEnd;
private String businessAuthorizationLetter;
private String contactIdDocPeriodBegin;
private String mobilePhone;
private String contactEmail;
}
}

View File

@@ -0,0 +1,35 @@
/*
* Copyright 2019-2022 felord.cn
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* https://www.apache.org/licenses/LICENSE-2.0
* Website:
* https://felord.cn
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package cn.felord.payment.wechat.v3.model.ecommerce;
import cn.felord.payment.wechat.enumeration.IdDocType;
import lombok.Data;
import java.time.LocalDate;
@Data
public class UboInfoListItem {
private IdDocType uboIdDocType;
private String uboIdDocCopy;
private String uboIdDocCopyBack;
private String uboIdDocName;
private String uboIdDocNumber;
private String uboIdDocAddress;
private LocalDate uboIdDocPeriodBegin;
private String uboIdDocPeriodEnd;
}

View File

@@ -0,0 +1,35 @@
/*
* Copyright 2019-2022 felord.cn
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* https://www.apache.org/licenses/LICENSE-2.0
* Website:
* https://felord.cn
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package cn.felord.payment.wechat.v3.model.paygiftactivity;
import cn.felord.payment.wechat.enumeration.ActivityStatus;
import cn.felord.payment.wechat.enumeration.AwardType;
import lombok.Data;
/**
* @author dax
* @since 1.0.19.RELEASE
*/
@Data
public class ActivitiesListPageRequest {
private final long offset;
private final long limit;
private String activityName;
private ActivityStatus activityStatus;
private AwardType awardType;
}

View File

@@ -0,0 +1,31 @@
/*
* Copyright 2019-2022 felord.cn
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* https://www.apache.org/licenses/LICENSE-2.0
* Website:
* https://felord.cn
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package cn.felord.payment.wechat.v3.model.paygiftactivity;
import lombok.Data;
/**
* @author dax
* @since 1.0.19.RELEASE
*/
@Data
public class ActivitiesPageRequest {
private final String activityId;
private Long offset;
private Long limit;
}

View File

@@ -0,0 +1,66 @@
/*
* Copyright 2019-2022 felord.cn
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* https://www.apache.org/licenses/LICENSE-2.0
* Website:
* https://felord.cn
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package cn.felord.payment.wechat.v3.model.paygiftactivity;
import cn.felord.payment.wechat.enumeration.CouponBgColor;
import cn.felord.payment.wechat.enumeration.DeliveryPurpose;
import com.fasterxml.jackson.annotation.JsonFormat;
import lombok.Data;
import java.time.OffsetDateTime;
/**
* The type Activity base info.
*
* @author dax
* @since 1.0.19.RELEASE
*/
@Data
public class ActivityBaseInfo {
private String activityName;
private String activitySecondTitle;
private String merchantLogoUrl;
private String backgroundColor;
@JsonFormat(pattern = "yyyy-MM-dd'T'HH:mm:ssXXX")
private OffsetDateTime beginTime;
@JsonFormat(pattern = "yyyy-MM-dd'T'HH:mm:ssXXX")
private OffsetDateTime endTime;
private AvailablePeriods availablePeriods;
private String outRequestNo;
private DeliveryPurpose deliveryPurpose;
private String miniProgramsPath;
/**
* Sets background color.
*
* @param backgroundColor the background color
*/
void setBackgroundColor(String backgroundColor) {
this.backgroundColor = backgroundColor;
}
/**
* Sets background color.
*
* @param backgroundColor the background color
*/
public void setBackgroundColor(CouponBgColor backgroundColor) {
this.backgroundColor = backgroundColor.getValue();
}
}

View File

@@ -14,30 +14,21 @@
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package cn.felord.payment.wechat.v2.model;
package cn.felord.payment.wechat.v3.model.paygiftactivity;
import cn.felord.payment.wechat.enumeration.DeliveryUserCategory;
import lombok.Data;
import lombok.EqualsAndHashCode;
import java.util.Set;
/**
* @author felord.cn
* @since 1.0.4.RELEASE
* @author dax
* @since 1.0.19.RELEASE
*/
@EqualsAndHashCode(callSuper = true)
@Data
public class RefundModel extends BaseModel {
private String appid;
private String mchId;
private String signType="MD5";
private String transactionId;
private String outTradeNo;
private String outRefundNo;
private Integer totalFee;
private Integer refundFee;
private String refundFeeType="CNY";
private String refundDesc;
private String refundAccount;
private String notifyUrl;
public class AdvancedSetting {
private DeliveryUserCategory deliveryUserCategory;
private String merchantMemberAppid;
private Set<String> goodsTags;
}

View File

@@ -0,0 +1,34 @@
/*
* Copyright 2019-2022 felord.cn
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* https://www.apache.org/licenses/LICENSE-2.0
* Website:
* https://felord.cn
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package cn.felord.payment.wechat.v3.model.paygiftactivity;
import lombok.Data;
import java.util.List;
/**
* The type Available periods.
*
* @author dax
* @since 1.0.19.RELEASE
*/
@Data
public class AvailablePeriods {
private List<OffsetDateTimePeriods> availableTime;
private List<LocalTimePeriods> availableDayTime;
}

View File

@@ -0,0 +1,31 @@
/*
* Copyright 2019-2022 felord.cn
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* https://www.apache.org/licenses/LICENSE-2.0
* Website:
* https://felord.cn
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package cn.felord.payment.wechat.v3.model.paygiftactivity;
import lombok.Data;
/**
* @author dax
* @since 1.0.19.RELEASE
*/
@Data
public class AwardItem {
private final String stock_id;
private final String original_image_url;
private String thumbnail_url;
}

View File

@@ -0,0 +1,40 @@
/*
* Copyright 2019-2022 felord.cn
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* https://www.apache.org/licenses/LICENSE-2.0
* Website:
* https://felord.cn
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package cn.felord.payment.wechat.v3.model.paygiftactivity;
import cn.felord.payment.wechat.enumeration.AwardType;
import cn.felord.payment.wechat.enumeration.SendContent;
import lombok.Data;
import java.util.List;
/**
* 满送活动规则
*
* @author dax
* @since 1.0.19.RELEASE
*/
@Data
public class AwardSendRule {
private final int transactionAmountMinimum;
private final SendContent sendContent;
private final AwardType awardType;
private final List<AwardItem> awardList;
private final String merchantOption;
private final List<String> merchantIdList;
}

View File

@@ -0,0 +1,33 @@
/*
* Copyright 2019-2022 felord.cn
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* https://www.apache.org/licenses/LICENSE-2.0
* Website:
* https://felord.cn
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package cn.felord.payment.wechat.v3.model.paygiftactivity;
import lombok.Data;
import java.util.List;
/**
* @author dax
* @since 1.0.19.RELEASE
*/
@Data
public class DeleteActivityMchRequest {
private final String activityId;
private String deleteRequestNo;
private List<String> merchantIdList;
}

View File

@@ -0,0 +1,31 @@
/*
* Copyright 2019-2022 felord.cn
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* https://www.apache.org/licenses/LICENSE-2.0
* Website:
* https://felord.cn
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package cn.felord.payment.wechat.v3.model.paygiftactivity;
import lombok.Data;
/**
* @author dax
* @since 1.0.19.RELEASE
*/
@Data
public class GiftActivityParams {
private final ActivityBaseInfo activityBaseInfo;
private final AwardSendRule awardSendRule;
private AdvancedSetting advancedSetting;
}

View File

@@ -0,0 +1,35 @@
/*
* Copyright 2019-2022 felord.cn
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* https://www.apache.org/licenses/LICENSE-2.0
* Website:
* https://felord.cn
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package cn.felord.payment.wechat.v3.model.paygiftactivity;
import com.fasterxml.jackson.annotation.JsonFormat;
import lombok.Data;
import java.time.OffsetDateTime;
/**
* @author dax
* @since 1.0.19.RELEASE
*/
@Data
public class LocalTimePeriods {
@JsonFormat(pattern = "HHmmss")
private final OffsetDateTime beginDayTime;
@JsonFormat(pattern = "HHmmss")
private final OffsetDateTime endDayTime;
}

View File

@@ -0,0 +1,33 @@
/*
* Copyright 2019-2022 felord.cn
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* https://www.apache.org/licenses/LICENSE-2.0
* Website:
* https://felord.cn
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package cn.felord.payment.wechat.v3.model.paygiftactivity;
import lombok.Data;
import java.util.List;
/**
* @author dax
* @since 1.0.19.RELEASE
*/
@Data
public class NewActivityMchRequest {
private final String activityId;
private final String addRequestNo;
private List<String> merchantIdList;
}

View File

@@ -0,0 +1,37 @@
/*
* Copyright 2019-2022 felord.cn
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* https://www.apache.org/licenses/LICENSE-2.0
* Website:
* https://felord.cn
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package cn.felord.payment.wechat.v3.model.paygiftactivity;
import com.fasterxml.jackson.annotation.JsonFormat;
import lombok.Data;
import java.time.OffsetDateTime;
/**
* The type Time periods.
*
* @author dax
* @since 1.0.19.RELEASE
*/
@Data
public class OffsetDateTimePeriods {
@JsonFormat(pattern = "yyyy-MM-dd'T'HH:mm:ssXXX")
private final OffsetDateTime beginTime;
@JsonFormat(pattern = "yyyy-MM-dd'T'HH:mm:ssXXX")
private final OffsetDateTime endTime;
}

View File

@@ -1,3 +1,20 @@
/*
* Copyright 2019-2022 felord.cn
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* https://www.apache.org/licenses/LICENSE-2.0
* Website:
* https://felord.cn
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package cn.felord.payment.wechat.v3.model.profitsharing;
import lombok.Data;
@@ -5,7 +22,7 @@ import lombok.Data;
import java.util.List;
/**
* @author xiafang
* @author dax
* @since 2023/1/3 10:27
*/
@Data

View File

@@ -22,11 +22,11 @@
<parent>
<groupId>cn.felord</groupId>
<artifactId>payment-spring-boot</artifactId>
<version>1.0.17.RELEASE</version>
<version>1.0.20.RELEASE</version>
</parent>
<artifactId>payment-spring-boot-starter</artifactId>
<version>1.0.17.RELEASE</version>
<version>1.0.20.RELEASE</version>
<packaging>jar</packaging>
<modelVersion>4.0.0</modelVersion>
@@ -62,4 +62,4 @@
</dependency>
</dependencies>
</project>
</project>

View File

@@ -21,7 +21,7 @@
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<groupId>cn.felord</groupId>
<artifactId>payment-spring-boot</artifactId>
<version>1.0.17.RELEASE</version>
<version>1.0.20.RELEASE</version>
<packaging>pom</packaging>
<modelVersion>4.0.0</modelVersion>
@@ -47,7 +47,7 @@
</developers>
<scm>
<tag>payment-spring-boot-1.0.14.RELEASE</tag>
<tag>payment-spring-boot-1.0.18.RELEASE</tag>
<url>https://github.com/NotFound403/payment-spring-boot</url>
<connection>scm:git:https://github.com/NotFound403/payment-spring-boot.git</connection>
<developerConnection>scm:git:https://github.com/NotFound403/payment-spring-boot.git</developerConnection>
@@ -90,7 +90,7 @@
<java.version>1.8</java.version>
<spring-boot.version>2.7.7</spring-boot.version>
<alipay-sdk.version>4.31.7.ALL</alipay-sdk.version>
<bcprov.version>1.69</bcprov.version>
<bcprov.version>1.74</bcprov.version>
</properties>
<distributionManagement>
@@ -212,4 +212,4 @@
</plugin>
</plugins>
</build>
</project>
</project>