Skip to content

Commit dceeaf3

Browse files
authored
🎨 消除旧通知头空值重载歧义
1 parent 509bce5 commit dceeaf3

3 files changed

Lines changed: 173 additions & 18 deletions

File tree

Lines changed: 109 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,9 @@
11
package com.github.binarywang.wxpay.bean.ecommerce;
22

3-
import lombok.AllArgsConstructor;
4-
import lombok.Builder;
5-
import lombok.Data;
6-
import lombok.NoArgsConstructor;
3+
import lombok.EqualsAndHashCode;
4+
import lombok.Getter;
5+
import lombok.Setter;
6+
import lombok.ToString;
77

88
import java.io.Serializable;
99

@@ -13,30 +13,124 @@
1313
*
1414
* @author cloudX
1515
*/
16-
@Data
17-
@Builder
18-
@NoArgsConstructor
19-
@AllArgsConstructor
2016
@Deprecated
21-
public class SignatureHeader implements Serializable {
17+
@Getter
18+
@Setter
19+
@EqualsAndHashCode(callSuper = false)
20+
@ToString(callSuper = false)
21+
public class SignatureHeader extends com.github.binarywang.wxpay.bean.notify.SignatureHeader implements Serializable {
2222
private static final long serialVersionUID = -6958015499416059949L;
23+
24+
/**
25+
* 已签名字符串
26+
*/
27+
private String signed;
28+
29+
/**
30+
* 证书序列号
31+
*/
32+
private String serialNo;
33+
2334
/**
24-
* 时间戳
35+
* 保留在旧类中的序列化字段,避免升级后反序列化旧数据时丢失。
2536
*/
2637
private String timeStamp;
2738

2839
/**
29-
* 随机串
40+
* 保留在旧类中的序列化字段,避免升级后反序列化旧数据时丢失。
3041
*/
3142
private String nonce;
3243

44+
public SignatureHeader() {
45+
super();
46+
}
47+
3348
/**
34-
* 已签名字符串
49+
* 保留 4.8.4 及以前版本的构造器签名。
3550
*/
36-
private String signed;
51+
public SignatureHeader(String timeStamp, String nonce, String signed, String serialNo) {
52+
setTimeStamp(timeStamp);
53+
setNonce(nonce);
54+
this.signed = signed;
55+
this.serialNo = serialNo;
56+
}
57+
58+
private SignatureHeader(SignatureHeaderBuilder builder) {
59+
super(builder);
60+
this.timeStamp = builder.timeStamp;
61+
this.nonce = builder.nonce;
62+
this.signed = builder.signed;
63+
this.serialNo = builder.serialNo;
64+
}
65+
66+
@Override
67+
public String getTimeStamp() {
68+
return this.timeStamp;
69+
}
70+
71+
@Override
72+
public void setTimeStamp(String timeStamp) {
73+
super.setTimeStamp(timeStamp);
74+
this.timeStamp = timeStamp;
75+
}
76+
77+
@Override
78+
public String getNonce() {
79+
return this.nonce;
80+
}
81+
82+
@Override
83+
public void setNonce(String nonce) {
84+
super.setNonce(nonce);
85+
this.nonce = nonce;
86+
}
3787

3888
/**
39-
* 证书序列号
89+
* 保留旧版 builder 的类型和方法返回值描述符。
4090
*/
41-
private String serialNo;
91+
public static SignatureHeaderBuilder builder() {
92+
return new SignatureHeaderBuilder();
93+
}
94+
95+
public static class SignatureHeaderBuilder extends com.github.binarywang.wxpay.bean.notify.SignatureHeader
96+
.SignatureHeaderBuilder<SignatureHeader, SignatureHeaderBuilder> {
97+
private String timeStamp;
98+
private String nonce;
99+
private String signed;
100+
private String serialNo;
101+
102+
@Override
103+
public SignatureHeaderBuilder timeStamp(String timeStamp) {
104+
super.timeStamp(timeStamp);
105+
this.timeStamp = timeStamp;
106+
return this;
107+
}
108+
109+
@Override
110+
public SignatureHeaderBuilder nonce(String nonce) {
111+
super.nonce(nonce);
112+
this.nonce = nonce;
113+
return this;
114+
}
115+
116+
public SignatureHeaderBuilder signed(String signed) {
117+
this.signed = signed;
118+
return this;
119+
}
120+
121+
public SignatureHeaderBuilder serialNo(String serialNo) {
122+
this.serialNo = serialNo;
123+
return this;
124+
}
125+
126+
@Override
127+
protected SignatureHeaderBuilder self() {
128+
return this;
129+
}
130+
131+
@Override
132+
public SignatureHeader build() {
133+
return new SignatureHeader(this);
134+
}
135+
}
42136
}

weixin-java-pay/src/main/java/com/github/binarywang/wxpay/bean/notify/SignatureHeader.java

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,9 @@
11
package com.github.binarywang.wxpay.bean.notify;
22

33
import lombok.AllArgsConstructor;
4-
import lombok.Builder;
54
import lombok.Data;
65
import lombok.NoArgsConstructor;
6+
import lombok.experimental.SuperBuilder;
77

88
import java.io.Serializable;
99

@@ -14,7 +14,7 @@
1414
* @author thinstar
1515
*/
1616
@Data
17-
@Builder
17+
@SuperBuilder
1818
@NoArgsConstructor
1919
@AllArgsConstructor
2020
public class SignatureHeader implements Serializable {

weixin-java-pay/src/test/java/com/github/binarywang/wxpay/service/LegacyEcommerceApiCompatibilityTest.java

Lines changed: 62 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,8 +5,12 @@
55
import org.testng.Assert;
66
import org.testng.annotations.Test;
77

8+
import java.io.ByteArrayInputStream;
9+
import java.io.ObjectInputStream;
10+
import java.util.Base64;
11+
812
/**
9-
* Compile-time compatibility checks for the pre-#4014 e-commerce API.
13+
* Compatibility checks for the pre-#4014 e-commerce API.
1014
*/
1115
public class LegacyEcommerceApiCompatibilityTest {
1216

@@ -25,4 +29,61 @@ public void shouldKeepLegacyRefundAndWithdrawNotificationSignatures() throws Exc
2529
Assert.assertNotNull(EcommerceService.class.getMethod("parseRefundNotifyResult", String.class, legacyHeader));
2630
Assert.assertNotNull(EcommerceService.class.getMethod("parseWithdrawNotifyResult", String.class, legacyHeader));
2731
}
32+
33+
@Test
34+
public void shouldKeepLegacySignatureHeaderConstructorAndBuilderAbi() throws Exception {
35+
com.github.binarywang.wxpay.bean.ecommerce.SignatureHeader legacyHeader =
36+
com.github.binarywang.wxpay.bean.ecommerce.SignatureHeader.builder()
37+
.timeStamp("timestamp")
38+
.nonce("nonce")
39+
.signed("signed")
40+
.serialNo("serial-no")
41+
.build();
42+
43+
Assert.assertNotNull(com.github.binarywang.wxpay.bean.ecommerce.SignatureHeader.class.getConstructor(
44+
String.class, String.class, String.class, String.class));
45+
Assert.assertEquals(com.github.binarywang.wxpay.bean.ecommerce.SignatureHeader.SignatureHeaderBuilder.class,
46+
com.github.binarywang.wxpay.bean.ecommerce.SignatureHeader.SignatureHeaderBuilder.class
47+
.getMethod("timeStamp", String.class).getReturnType());
48+
Assert.assertEquals(com.github.binarywang.wxpay.bean.ecommerce.SignatureHeader.SignatureHeaderBuilder.class,
49+
com.github.binarywang.wxpay.bean.ecommerce.SignatureHeader.SignatureHeaderBuilder.class
50+
.getMethod("nonce", String.class).getReturnType());
51+
Assert.assertTrue(com.github.binarywang.wxpay.bean.notify.SignatureHeader.class
52+
.isAssignableFrom(legacyHeader.getClass()));
53+
com.github.binarywang.wxpay.bean.notify.SignatureHeader unifiedHeader =
54+
EcommerceService.toUnifiedSignatureHeader(legacyHeader);
55+
Assert.assertEquals(unifiedHeader.getTimeStamp(), "timestamp");
56+
Assert.assertEquals(unifiedHeader.getNonce(), "nonce");
57+
Assert.assertEquals(unifiedHeader.getSignature(), "signed");
58+
Assert.assertEquals(unifiedHeader.getSerial(), "serial-no");
59+
}
60+
61+
@Test
62+
public void shouldIncludeTimestampAndNonceInLegacyHeaderEquality() {
63+
com.github.binarywang.wxpay.bean.ecommerce.SignatureHeader first =
64+
new com.github.binarywang.wxpay.bean.ecommerce.SignatureHeader("timestamp-1", "nonce", "signed", "serial-no");
65+
com.github.binarywang.wxpay.bean.ecommerce.SignatureHeader second =
66+
new com.github.binarywang.wxpay.bean.ecommerce.SignatureHeader("timestamp-2", "nonce", "signed", "serial-no");
67+
68+
Assert.assertNotEquals(first, second);
69+
}
70+
71+
@Test
72+
public void shouldReadLegacySerializedHeaderFields() throws Exception {
73+
String legacySerializedHeader = "rO0ABXNyADpjb20uZ2l0aHViLmJpbmFyeXdhbmcud3hwYXkuYmVhbi5lY29tbWVyY2UuU2lnbmF0dXJlSGVhZGVyn3ApxLekv9MCAARMAAVub25jZXQAEkxqYXZhL2xhbmcvU3RyaW5nO0wACHNlcmlhbE5vcQB+AAFMAAZzaWduZWRxAH4AAUwACXRpbWVTdGFtcHEAfgABeHB0AAVub25jZXQACXNlcmlhbC1ub3QABnNpZ25lZHQACXRpbWVzdGFtcA==";
74+
ObjectInputStream input = new ObjectInputStream(new ByteArrayInputStream(
75+
Base64.getDecoder().decode(legacySerializedHeader)));
76+
com.github.binarywang.wxpay.bean.ecommerce.SignatureHeader header =
77+
(com.github.binarywang.wxpay.bean.ecommerce.SignatureHeader) input.readObject();
78+
79+
Assert.assertEquals(header.getTimeStamp(), "timestamp");
80+
Assert.assertEquals(header.getNonce(), "nonce");
81+
Assert.assertEquals(header.getSigned(), "signed");
82+
Assert.assertEquals(header.getSerialNo(), "serial-no");
83+
}
84+
85+
private void shouldCompileNullNotificationHeaderCalls(EcommerceService ecommerceService) throws Exception {
86+
ecommerceService.parseRefundNotifyResult("notify-data", null);
87+
ecommerceService.parseWithdrawNotifyResult("notify-data", null);
88+
}
2889
}

0 commit comments

Comments
 (0)