# authapi-sdk **Repository Path**: ufudig/authapi-sdk ## Basic Information - **Project Name**: authapi-sdk - **Description**: 公开服务用RSA签名/加密开发库 - **Primary Language**: Java - **License**: Not specified - **Default Branch**: master - **Homepage**: None - **GVP Project**: No ## Statistics - **Stars**: 0 - **Forks**: 0 - **Created**: 2025-09-07 - **Last Updated**: 2026-02-04 ## Categories & Tags **Categories**: Uncategorized **Tags**: None ## README # Auth Api SDK 公共服务RSA签名/加密开发库 ## 添加依赖 ```xml com.touscm authapi-sdk 1.0-SNAPSHOT ``` ## 签名算法 ### 获取签名 签名使用基于非对称密钥的SHA256-RSA的数字签名算法, 具体处理如下: 原始字符 = 请求方法 + "\n" + 请求路由 + "\n" + 时间戳 + "\n" + 随机字符 + "\n" + 请求体 + "\n"
签名字符 = 使用 `SHA256withRSA` 算法签名原始字符
认证类型 = 如果配置了 `auth-api.auth-type`, 认证类型的值为配置的值, 如果未配置认证类型为 `OPEN-SHA256-RSA2048`
认证标识字段名 = 如果配置了 `auth-api.cert-identity`, 认证标识字段名为配置的值, 如果未配置则值为 `merchant_id`
认证信息 = 认证类型 + " " + 认证标识字段名 + "=" + 认证标识值 + ",nonce_str=" + 随机字符 + ",signature=" + 签名 + ",timestamp=" + 时间戳 + ",serial_no=" + 证书序号 ### 加密算法 加密算法使用SM4(ECB模式, 填充格式为PKCS5Padding)加密请求体内容 ## 示例代码 ### 配置信息 ```yaml auth-api: auth-type: 签名/验签标识类型(默认:OPEN-SHA256-RSA2048) cert-identity: 认证标识字段名(例如:app-id或者merchant-id) cert-root-path: 私钥/证书的根目录 cert-prefix: 私钥/证书文件名前缀 ``` ### 调用服务 #### SM4加密/解密 ```java public void testSm4() throws NoSuchAlgorithmException, NoSuchProviderException, IllegalBlockSizeException, NoSuchPaddingException, BadPaddingException, InvalidKeyException { var key = Sm4Utils.generateKey(); System.out.println("Key: " + key); var body = """ { "app_id": "app_dc8643cf-bae6-4713-8511-75723e88095c", "business_mode": "00", "created_time": "20250605095528", "end_time": "20250605095533", "fee_amt": "0.00", "freeze_stat": "UNFREEZE", "id": "002212025060509552710776517720207020032", "notifyToWxLiteFlag": "01", "order_no": "P1930443317366820866", "party_order_id": "02242506053572761009492", "pay_amt": "1020.00", "pay_channel": "wx_lite", "real_amt": "1020.00", "share_eq": "Y", "status": "succeeded" } """; // SM4加密 var encryptBody = Sm4Utils.encryptEcb(key, body); System.out.println("encryptBody: " + encryptBody); // SM4解密 var decryptBody = Sm4Utils.decryptEcb(key, encryptBody); System.out.println("decryptBody: " + decryptBody); assertEquals(body, decryptBody); } ``` #### 生成私钥/证书 ```java @Bean public CommandLineRunner testSdk(SignAuthService signAuthService) { return args -> { // 认证标识值, 例如:商户ID/应用ID var certIdentity = "APP-ID-000000"; // 证书序号 var certSerialNo = 2025; // 请求方法 var method = "POST"; // 请求路由 var openApiUri = "/open/api/v1"; // 请求体 var body = """ { "app_id": "app_dc8643cf-bae6-4713-8511-75723e88095c", "business_mode": "00", "created_time": "20250605095528", "end_time": "20250605095533", "fee_amt": "0.00", "freeze_stat": "UNFREEZE", "id": "002212025060509552710776517720207020032", "notifyToWxLiteFlag": "01", "order_no": "P1930443317366820866", "party_order_id": "02242506053572761009492", "pay_amt": "1020.00", "pay_channel": "wx_lite", "real_amt": "1020.00", "share_eq": "Y", "status": "succeeded" } """; // RSA加密, 可根据需要加密敏感字段(注意, 犹豫RSA算法长度限制, 2048位的RSA密钥加密原始字符长度上限为214位) // 由于RSA的限制, 使用SM4对请求体进行整体加密 var json = JSONObject.parseObject(body); var originValue = json.getString("id"); var encryptValue = signAuthService.rsaEncrypt(certIdentity, originValue); System.out.println("encrypt"); System.out.println("originValue=" + originValue + ",encryptValue=" + encryptValue); json.replace("id", encryptValue); var requestBody = json.toJSONString(); // gen cert signAuthService.generateCert(certIdentity, certSerialNo); // RSA签名 var authContent = signAuthService.getAuthorization(certIdentity, certSerialNo, openApiUri, method, requestBody); System.out.println("sign"); System.out.println(EntryUtils.toString(authContent)); // RSA验签 var verifyResult = signAuthService.authCheck(method, openApiUri, authContent, requestBody, new HashMap<>()); System.out.println("verify sign"); System.out.println(EntryUtils.toString(verifyResult)); // RSA字段解密, 实际使用可替换为SM4 var requestJson = JSONObject.parseObject(requestBody); var requestEncryptValue = requestJson.getString("id"); var decryptResult = signAuthService.rsaDecrypt(certIdentity, requestEncryptValue); System.out.println("decrypt"); System.out.println(EntryUtils.toString(decryptResult)); }; } ```