44import org .testng .annotations .*;
55
66import static org .assertj .core .api .Assertions .assertThat ;
7+ import static org .assertj .core .api .Assertions .assertThatThrownBy ;
78
89/**
910 * <pre>
1415 * @author <a href="https://github.com/binarywang">Binary Wang</a>
1516 */
1617public class WxMaCryptUtilsTest {
18+ // 模拟来自 getUserEncryptKey 接口返回的 encrypt_key(Base64,解码后 16 字节)
19+ // 和 iv(Hex,32 位十六进制字符,解码后 16 字节,AES-128-CBC 要求)
20+ private static final String ENCRYPT_KEY = "VI6BpyrK9XH4i4AIGe86tg==" ;
21+ private static final String HEX_IV = "6003f73ec441c3866003f73ec441c386" ;
22+
1723 @ Test
1824 public void testDecrypt () {
1925 String sessionKey = "7MG7jbTToVVRWRXVA885rg==" ;
@@ -32,4 +38,98 @@ public void testDecryptAnotherWay() {
3238 assertThat (WxMaCryptUtils .decrypt (sessionKey , encryptedData , ivStr ))
3339 .isEqualTo (WxMaCryptUtils .decryptAnotherWay (sessionKey , encryptedData , ivStr ));
3440 }
41+
42+ /**
43+ * 测试使用用户加密 key(来自小程序加密网络通道)进行加密和解密的对称性.
44+ * encrypt_key 为 Base64 编码的 16 字节 AES-128 密钥,iv 为 Hex 编码的 16 字节初始向量。
45+ */
46+ @ Test
47+ public void testEncryptAndDecryptWithEncryptKey () {
48+ String plainText = "{\" userId\" :\" 12345\" ,\" amount\" :100}" ;
49+
50+ String encrypted = WxMaCryptUtils .encryptWithEncryptKey (ENCRYPT_KEY , HEX_IV , plainText );
51+ assertThat (encrypted ).isNotNull ().isNotEmpty ();
52+
53+ String decrypted = WxMaCryptUtils .decryptWithEncryptKey (ENCRYPT_KEY , HEX_IV , encrypted );
54+ assertThat (decrypted ).isEqualTo (plainText );
55+ }
56+
57+ /**
58+ * 测试加密网络通道的加解密对称性(不同明文).
59+ */
60+ @ Test
61+ public void testEncryptDecryptSymmetryWithEncryptKey () {
62+ String plainText = "hello miniprogram" ;
63+
64+ String encrypted = WxMaCryptUtils .encryptWithEncryptKey (ENCRYPT_KEY , HEX_IV , plainText );
65+ String decrypted = WxMaCryptUtils .decryptWithEncryptKey (ENCRYPT_KEY , HEX_IV , encrypted );
66+ assertThat (decrypted ).isEqualTo (plainText );
67+ }
68+
69+ /**
70+ * 测试 hexIv 为奇数长度时,应抛出 IllegalArgumentException.
71+ */
72+ @ Test
73+ public void testEncryptWithEncryptKeyInvalidHexIvOddLength () {
74+ assertThatThrownBy (() -> WxMaCryptUtils .encryptWithEncryptKey (ENCRYPT_KEY , "abc" , "data" ))
75+ .isInstanceOf (IllegalArgumentException .class )
76+ .hasMessageContaining ("长度必须为偶数" );
77+ }
78+
79+ /**
80+ * 测试 hexIv 包含非十六进制字符时,应抛出 IllegalArgumentException.
81+ */
82+ @ Test
83+ public void testEncryptWithEncryptKeyInvalidHexIvNonHexChar () {
84+ // 32 位但含非法字符 'z'
85+ assertThatThrownBy (() -> WxMaCryptUtils .encryptWithEncryptKey (
86+ ENCRYPT_KEY , "6003f73ec441c3866003f73ec441z386" , "data" ))
87+ .isInstanceOf (IllegalArgumentException .class )
88+ .hasMessageContaining ("非法字符" );
89+ }
90+
91+ /**
92+ * 测试 hexIv 解码后不足 16 字节(如仅 16 位 hex = 8 字节)时,应抛出 IllegalArgumentException.
93+ */
94+ @ Test
95+ public void testEncryptWithEncryptKeyShortHexIv () {
96+ // 16 位 hex = 8 字节,不满足 AES-CBC 要求的 16 字节
97+ assertThatThrownBy (() -> WxMaCryptUtils .encryptWithEncryptKey (
98+ ENCRYPT_KEY , "6003f73ec441c386" , "data" ))
99+ .isInstanceOf (IllegalArgumentException .class )
100+ .hasMessageContaining ("hexIv 解码后必须为 16 字节" );
101+ }
102+
103+ /**
104+ * 测试 encryptKey 解码后不足 16 字节时,应抛出 IllegalArgumentException.
105+ */
106+ @ Test
107+ public void testEncryptWithEncryptKeyShortKey () {
108+ // Base64 编码的 8 字节 key(不符合 AES-128 要求)
109+ String shortKey = java .util .Base64 .getEncoder ().encodeToString (new byte [8 ]);
110+ assertThatThrownBy (() -> WxMaCryptUtils .encryptWithEncryptKey (shortKey , HEX_IV , "data" ))
111+ .isInstanceOf (IllegalArgumentException .class )
112+ .hasMessageContaining ("encryptKey 解码后必须为 16 字节" );
113+ }
114+
115+ /**
116+ * 测试 decryptWithEncryptKey 使用非法 hexIv 时,应抛出 IllegalArgumentException.
117+ */
118+ @ Test
119+ public void testDecryptWithEncryptKeyInvalidHexIv () {
120+ assertThatThrownBy (() -> WxMaCryptUtils .decryptWithEncryptKey (ENCRYPT_KEY , "abc" , "data" ))
121+ .isInstanceOf (IllegalArgumentException .class )
122+ .hasMessageContaining ("长度必须为偶数" );
123+ }
124+
125+ /**
126+ * 测试 decryptWithEncryptKey encryptKey 长度不合法时,应抛出 IllegalArgumentException.
127+ */
128+ @ Test
129+ public void testDecryptWithEncryptKeyShortKey () {
130+ String shortKey = java .util .Base64 .getEncoder ().encodeToString (new byte [8 ]);
131+ assertThatThrownBy (() -> WxMaCryptUtils .decryptWithEncryptKey (shortKey , HEX_IV , "data" ))
132+ .isInstanceOf (IllegalArgumentException .class )
133+ .hasMessageContaining ("encryptKey 解码后必须为 16 字节" );
134+ }
35135}
0 commit comments