From d18985f260c8ab54f60439421801c47f199edae4 Mon Sep 17 00:00:00 2001 From: Fu Diwei Date: Sun, 13 Nov 2022 23:17:18 +0800 Subject: [PATCH] =?UTF-8?q?feat(tenpayv3):=20=E9=80=82=E9=85=8D=E5=9B=BD?= =?UTF-8?q?=E5=AF=86=E6=8E=A5=E5=85=A5=E6=A8=A1=E5=BC=8F?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- docs/WechatTenpayV3/Advanced_Extensions.md | 4 +- ...yCertificateRefreshingBackgroundService.cs | 11 +- ...enpayCertificateRefreshingBackgroundJob.cs | 11 +- .../WechatTenpaySensitivePropertyAttribute.cs | 9 +- .../Constants/EncryptionAlgorithms.cs | 6 +- .../Constants/SignSchemes.cs | 11 +- .../WechatTenpayClientSignExtensions.cs | 118 +++++---- ...atTenpayClientEventDecryptionExtensions.cs | 70 ++++-- ...TenpayClientEventVerificationExtensions.cs | 84 ++++++- .../WechatTenpayClientParameterExtensions.cs | 4 +- ...TenpayClientRequestEncryptionExtensions.cs | 223 ++++++++++++------ ...enpayClientResponseDecryptionExtensions.cs | 214 ++++++++++++----- ...payClientResponseVerificationExtensions.cs | 96 +++++++- ...WechatTenpayRequestSignatureInterceptor.cs | 23 +- ...eateApplyForSubMerchantApplymentRequest.cs | 45 ++-- ...ifyApplyForSubMerchantSettlementRequest.cs | 5 +- .../CreateApplyForSubjectApplymentRequest.cs | 29 ++- .../GetBillSubMerchantFundflowBillResponse.cs | 5 +- .../CreateBrandProfitSharingOrderRequest.cs | 5 +- .../QueryCapitalBanksByBankAccountRequest.cs | 5 +- .../Certificates/QueryCertificatesResponse.cs | 5 +- .../CreateEcommerceApplymentRequest.cs | 47 ++-- ...erceApplymentByOutRequestNumberResponse.cs | 8 +- .../GetEcommerceBillFundflowBillResponse.cs | 5 +- ...reateEcommerceProfitSharingOrderRequest.cs | 5 +- ...ddEcommerceProfitSharingReceiverRequest.cs | 5 +- .../VerifyHKCustomsCertificateRequest.cs | 8 +- .../HKMerchants/AddHKSubMerchantRequest.cs | 11 +- .../HKMerchants/GetHKSubMerchantResponse.cs | 11 +- ...MarketingMemberCardOpenCardPhoneRequest.cs | 5 +- ...ntServiceComplaintByComplaintIdResponse.cs | 3 +- .../QueryMerchantServiceComplaintsResponse.cs | 5 +- ...ferBatchDetailByOutDetailNumberResponse.cs | 5 +- .../GetPayScoreMerchantBillResponse.cs | 5 +- .../CreateProfitSharingOrderRequest.cs | 5 +- .../AddProfitSharingReceiverRequest.cs | 5 +- .../AddProfitSharingReceiverResponse.cs | 5 +- .../SmartGuide/CreateSmartGuideRequest.cs | 8 +- .../SmartGuide/QuerySmartGuidesRequest.cs | 5 +- .../SmartGuide/QuerySmartGuidesResponse.cs | 8 +- .../SmartGuide/UpdateSmartGuideRequest.cs | 8 +- .../Batches/CreateTransferBatchRequest.cs | 5 +- ...ferBatchDetailByOutDetailNumberResponse.cs | 5 +- .../README.md | 4 +- .../Settings/CertificateEntry.cs | 118 +++++++-- .../Settings/Credentials.cs | 8 +- .../Utilities/SM2Utility.cs | 41 ++-- .../WechatTenpayClient.cs | 15 +- .../WechatTenpayClientOptions.cs | 4 +- .../WechatTenpayResponse.cs | 7 + .../TestCase_CertificateManagerTests.cs | 6 +- .../TestCase_RequestEncryptionTests.cs | 13 +- .../TestCase_ResponseVerificationTests.cs | 8 +- 53 files changed, 995 insertions(+), 389 deletions(-) diff --git a/docs/WechatTenpayV3/Advanced_Extensions.md b/docs/WechatTenpayV3/Advanced_Extensions.md index 56d24c5b..578f3569 100644 --- a/docs/WechatTenpayV3/Advanced_Extensions.md +++ b/docs/WechatTenpayV3/Advanced_Extensions.md @@ -62,7 +62,7 @@ public class MyFakeRequest : WechatTenpayRequest { [Newtonsoft.Json.JsonProperty("my_fake_props")] [System.Text.Json.Serialization.JsonPropertyName("my_fake_props")] - [WechatTenpaySensitiveProperty("my_alg")] + [WechatTenpaySensitiveProperty("my_scheme", "my_alg")] public string MyFakeProps { get; set; } } @@ -71,7 +71,7 @@ public class MyFakeResponse : WechatTenpayResponse { [Newtonsoft.Json.JsonProperty("my_fake_props")] [System.Text.Json.Serialization.JsonPropertyName("my_fake_props")] - [WechatTenpaySensitiveProperty("my_alg")] + [WechatTenpaySensitiveProperty("my_scheme", "my_alg")] public string MyFakeProps { get; set; } } ``` diff --git a/samples/SKIT.FlurlHttpClient.Wechat.TenpayV3.Sample_Net6/Services/BackgroundServices/TenpayCertificateRefreshingBackgroundService.cs b/samples/SKIT.FlurlHttpClient.Wechat.TenpayV3.Sample_Net6/Services/BackgroundServices/TenpayCertificateRefreshingBackgroundService.cs index ec1f744e..0c8665c5 100644 --- a/samples/SKIT.FlurlHttpClient.Wechat.TenpayV3.Sample_Net6/Services/BackgroundServices/TenpayCertificateRefreshingBackgroundService.cs +++ b/samples/SKIT.FlurlHttpClient.Wechat.TenpayV3.Sample_Net6/Services/BackgroundServices/TenpayCertificateRefreshingBackgroundService.cs @@ -1,4 +1,4 @@ -using System; +using System; using System.Threading; using System.Threading.Tasks; using Microsoft.Extensions.Hosting; @@ -34,18 +34,19 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Sample.Services.BackgroundService { try { + const string ALGORITHM_TYPE = "RSA"; var client = _tenpayHttpClientFactory.Create(tenpayMerchantOptions.MerchantId); - var request = new QueryCertificatesRequest(); + var request = new QueryCertificatesRequest() { AlgorithmType = ALGORITHM_TYPE }; var response = await client.ExecuteQueryCertificatesAsync(request, cancellationToken: stoppingToken); if (response.IsSuccessful()) { // NOTICE: - // 如果启用了 `AutoDecryptResponseSensitiveProperty` 配置项,则无需再手动执行下面被注释的解密方法: + // 如果构造 Client 时启用了 `AutoDecryptResponseSensitiveProperty` 配置项,则无需再手动执行下面被注释的解密方法: // response = client.DecryptResponseSensitiveProperty(response); - foreach (var certificateModel in response.CertificateList) + foreach (var certificate in response.CertificateList) { - client.PlatformCertificateManager.AddEntry(new CertificateEntry(certificateModel)); + client.PlatformCertificateManager.AddEntry(new CertificateEntry(ALGORITHM_TYPE, certificate)); } _logger.LogInformation("刷新微信商户平台证书成功。"); diff --git a/samples/SKIT.FlurlHttpClient.Wechat.TenpayV3.Sample_NetFramework47/Services/BackgroundJobs/TenpayCertificateRefreshingBackgroundJob.cs b/samples/SKIT.FlurlHttpClient.Wechat.TenpayV3.Sample_NetFramework47/Services/BackgroundJobs/TenpayCertificateRefreshingBackgroundJob.cs index 367ed5d9..3c609b68 100644 --- a/samples/SKIT.FlurlHttpClient.Wechat.TenpayV3.Sample_NetFramework47/Services/BackgroundJobs/TenpayCertificateRefreshingBackgroundJob.cs +++ b/samples/SKIT.FlurlHttpClient.Wechat.TenpayV3.Sample_NetFramework47/Services/BackgroundJobs/TenpayCertificateRefreshingBackgroundJob.cs @@ -1,4 +1,4 @@ -namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Sample.Services.BackgroundJobs +namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Sample.Services.BackgroundJobs { internal class TenpayCertificateRefreshingBackgroundJob { @@ -16,18 +16,19 @@ { try { + const string ALGORITHM_TYPE = "RSA"; var client = _tenpayHttpClientFactory.Create(tenpayMerchantOptions.MerchantId); - var request = new QueryCertificatesRequest(); + var request = new QueryCertificatesRequest() { AlgorithmType = ALGORITHM_TYPE }; var response = await client.ExecuteQueryCertificatesAsync(request); if (response.IsSuccessful()) { // NOTICE: - // 如果启用了 `AutoDecryptResponseSensitiveProperty` 配置项,则无需再手动执行下面被注释的解密方法: + // 如果构造 Client 时启用了 `AutoDecryptResponseSensitiveProperty` 配置项,则无需再手动执行下面被注释的解密方法: // response = client.DecryptResponseSensitiveProperty(response); - foreach (var certificateModel in response.CertificateList) + foreach (var certificate in response.CertificateList) { - client.CertificateManager.AddEntry(new CertificateEntry(certificateModel)); + client.CertificateManager.AddEntry(new CertificateEntry(ALGORITHM_TYPE, certificate)); } Debug.WriteLine("刷新微信商户平台证书成功。"); diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Attributes/WechatTenpaySensitivePropertyAttribute.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Attributes/WechatTenpaySensitivePropertyAttribute.cs index 6f304890..76237d70 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Attributes/WechatTenpaySensitivePropertyAttribute.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Attributes/WechatTenpaySensitivePropertyAttribute.cs @@ -1,14 +1,17 @@ -using System; +using System; namespace SKIT.FlurlHttpClient.Wechat.TenpayV3 { - [AttributeUsage(AttributeTargets.Property, AllowMultiple = false, Inherited = true)] + [AttributeUsage(AttributeTargets.Property, AllowMultiple = true, Inherited = true)] public sealed class WechatTenpaySensitivePropertyAttribute : Attribute { + public string Scheme { get; } + public string Algorithm { get; } - public WechatTenpaySensitivePropertyAttribute(string algorithm) + public WechatTenpaySensitivePropertyAttribute(string scheme, string algorithm) { + Scheme = scheme; Algorithm = algorithm; } } diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Constants/EncryptionAlgorithms.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Constants/EncryptionAlgorithms.cs index 441e7d91..c0ecb79d 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Constants/EncryptionAlgorithms.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Constants/EncryptionAlgorithms.cs @@ -1,11 +1,15 @@ -namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Constants +namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Constants { public static class EncryptionAlgorithms { public const string AEAD_AES_256_GCM = "AEAD_AES_256_GCM"; + public const string AEAD_SM4_128_GCM = "AEAD_SM4_GCM"; + public const string RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1 = "RSA_2048_ECB_PKCS8_OAEPWithSHA-1AndMGF1"; public const string RSA_2048_ECB_PKCS1 = "RSA_2048_ECB_PKCS1"; + + public const string SM2_C1C3C2_ASN1 = "SM2_C1C3C2_ASN1"; } } diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Constants/SignSchemes.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Constants/SignSchemes.cs index b249888c..cfbbf496 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Constants/SignSchemes.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Constants/SignSchemes.cs @@ -1,10 +1,15 @@ -namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Constants +namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Constants { public static class SignSchemes { /// - /// WECHATPAY2-SHA256-RSA2048。 + /// RSA 算法:RSA2048 Sign with SHA256。 /// - public const string WECHATPAY2_SHA256_RSA2048 = "WECHATPAY2-SHA256-RSA2048"; + public const string WECHATPAY2_RSA_2048_WITH_SHA256 = "WECHATPAY2-SHA256-RSA2048"; + + /// + /// 国密算法:SM2 Sign with SM3。 + /// + public const string WECHATPAY2_SM2_WITH_SM3 = "WECHATPAY2-SM2-WITH-SM3"; } } diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Extensions/Internal/WechatTenpayClientSignExtensions.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Extensions/Internal/WechatTenpayClientSignExtensions.cs index 3bd456c7..376e8421 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Extensions/Internal/WechatTenpayClientSignExtensions.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Extensions/Internal/WechatTenpayClientSignExtensions.cs @@ -1,70 +1,98 @@ -using System; +using System; namespace SKIT.FlurlHttpClient.Wechat.TenpayV3 { internal static class WechatTenpayClientSignExtensions { - public static bool VerifySignature(this WechatTenpayClient client, string strTimestamp, string strNonce, string strBody, string strSignature, string strSerialNumber) - { - return VerifySignature(client, strTimestamp, strNonce, strBody, strSignature, strSerialNumber, Constants.SignSchemes.WECHATPAY2_SHA256_RSA2048, out _); - } - - public static bool VerifySignature(this WechatTenpayClient client, string strTimestamp, string strNonce, string strBody, string strSignature, string strSerialNumber, string strSignScheme) - { - return VerifySignature(client, strTimestamp, strNonce, strBody, strSignature, strSerialNumber, strSignScheme, out _); - } - - public static bool VerifySignature(this WechatTenpayClient client, string strTimestamp, string strNonce, string strBody, string strSignature, string strSerialNumber, out Exception? error) - { - return VerifySignature(client, strTimestamp, strNonce, strBody, strSignature, strSerialNumber, Constants.SignSchemes.WECHATPAY2_SHA256_RSA2048, out error); - } - - public static bool VerifySignature(this WechatTenpayClient client, string strTimestamp, string strNonce, string strBody, string strSignature, string strSerialNumber, string strSignScheme, out Exception? error) + public static bool VerifySignature(this WechatTenpayClient client, string strTimestamp, string strNonce, string strContent, string strSignature, string strSignatureScheme, string strSerialNumber, out Exception? error) { if (client == null) throw new ArgumentNullException(nameof(client)); - switch (strSignScheme) + switch (strSignatureScheme) { - case Constants.SignSchemes.WECHATPAY2_SHA256_RSA2048: + case Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256: { - if (client.PlatformCertificateManager != null) + if (client.PlatformCertificateManager == null) { - try - { - var cert = client.PlatformCertificateManager.GetEntry(strSerialNumber); - if (!cert.HasValue) - { - error = new Exceptions.WechatTenpayEventVerificationException("There is no platform certificate matched the serial number."); - return false; - } - - error = null; - return Utilities.RSAUtility.VerifyWithSHA256ByCertificate( - certificate: cert.Value.Certificate, - plainText: GetPlainTextForSignature(timestamp: strTimestamp, nonce: strNonce, body: strBody), - signature: strSignature - ); - } - catch (Exception ex) - { - error = ex; - return false; - } + error = new Exception("The platform certificate manager is not initialized."); + return false; } - error = new Exception("There is no platform certificate in the certificate manager."); - return false; + var entry = client.PlatformCertificateManager.GetEntry(strSerialNumber); + if (!entry.HasValue) + { + error = new Exception($"There is no platform certificate matched the serial number: \"{strSerialNumber}\", please make sure you have downloaded platform certificates first."); + return false; + } + + if (!Settings.CertificateEntry.ALGORITHM_TYPE_RSA.Equals(entry.Value.AlgorithmType)) + { + error = new Exception($"The platform certificate with serial number: \"{strSerialNumber}\" is not for RSA."); + return false; + } + + error = null; + try + { + return Utilities.RSAUtility.VerifyWithSHA256ByCertificate( + certificate: entry.Value.Certificate, + message: GenerateMessageForSignature(timestamp: strTimestamp, nonce: strNonce, body: strContent), + signature: strSignature + ); + } + catch (Exception ex) + { + error = ex; + return false; + } + } + + case Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3: + { + if (client.PlatformCertificateManager == null) + { + error = new Exception("The platform certificate manager is not initialized."); + return false; + } + + var entry = client.PlatformCertificateManager.GetEntry(strSerialNumber); + if (!entry.HasValue) + { + error = new Exception($"There is no platform certificate matched the serial number: \"{strSerialNumber}\", please make sure you have downloaded platform certificates first."); + return false; + } + + if (!Settings.CertificateEntry.ALGORITHM_TYPE_SM2.Equals(entry.Value.AlgorithmType)) + { + error = new Exception($"The platform certificate with serial number: \"{strSerialNumber}\" is not for SM2."); + return false; + } + + error = null; + try + { + return Utilities.SM2Utility.VerifyWithSM3ByCertificate( + certificate: entry.Value.Certificate, + message: GenerateMessageForSignature(timestamp: strTimestamp, nonce: strNonce, body: strContent), + signature: strSignature + ); + } + catch (Exception ex) + { + error = ex; + return false; + } } default: { - error = new Exception("Unsupported sign scheme."); + error = new Exception($"Unsupported signature scheme: \"{strSignatureScheme}\"."); return false; } } } - private static string GetPlainTextForSignature(string timestamp, string nonce, string body) + private static string GenerateMessageForSignature(string timestamp, string nonce, string body) { return $"{timestamp}\n{nonce}\n{body}\n"; } diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Extensions/WechatTenpayClientEventDecryptionExtensions.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Extensions/WechatTenpayClientEventDecryptionExtensions.cs index 880c6abe..befbc239 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Extensions/WechatTenpayClientEventDecryptionExtensions.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Extensions/WechatTenpayClientEventDecryptionExtensions.cs @@ -1,4 +1,5 @@ -using System; +using System; +using System.Text; namespace SKIT.FlurlHttpClient.Wechat.TenpayV3 { @@ -51,26 +52,55 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3 if (resource == null) throw new ArgumentNullException(nameof(resource)); string plainJson; + switch (resource.Algorithm) + { + case Constants.EncryptionAlgorithms.AEAD_AES_256_GCM: + { + try + { + plainJson = Utilities.AESUtility.DecryptWithGCM( + key: client.Credentials.MerchantV3Secret, + nonce: resource.Nonce, + aad: resource.AssociatedData, + cipherText: resource.CipherText + ); + } + catch (Exception ex) + { + throw new Exceptions.WechatTenpayEventDecryptionException("Decrypt event resource failed. Please see the `InnerException` for more details.", ex); + } + } + break; - if (Constants.EncryptionAlgorithms.AEAD_AES_256_GCM.Equals(resource.Algorithm)) - { - try - { - plainJson = Utilities.AESUtility.DecryptWithGCM( - key: client.Credentials.MerchantV3Secret, - iv: resource.Nonce, - aad: resource.AssociatedData, - cipherText: resource.CipherText - ); - } - catch (Exception ex) - { - throw new Exceptions.WechatTenpayEventDecryptionException("Decrypt event resource failed. Please see the `InnerException` for more details.", ex); - } - } - else - { - throw new Exceptions.WechatTenpayEventDecryptionException("Unsupported encrypt algorithm of the resource."); + case Constants.EncryptionAlgorithms.AEAD_SM4_128_GCM: + { + try + { + // REF: https://pay.weixin.qq.com/docs/merchant/development/shangmi/guide.html + // 由于 SM4 密钥长度的限制,密钥由 APIv3 密钥通过国密 SM3 Hash 计算生成。SM4 密钥取其摘要(256bit)的前 128bit。 + byte[] secretBytes = Utilities.SM3Utility.Hash(Encoding.UTF8.GetBytes(client.Credentials.MerchantV3Secret)); + byte[] keyBytes = new byte[16]; + Array.Copy(secretBytes, keyBytes, keyBytes.Length); + + byte[] plainBytes = Utilities.SM4Utility.DecryptWithGCM( + keyBytes: keyBytes, + nonceBytes: Encoding.UTF8.GetBytes(resource.Nonce), + aadBytes: Encoding.UTF8.GetBytes(resource.AssociatedData), + cipherBytes: Convert.FromBase64String(resource.CipherText) + ); + plainJson = Encoding.UTF8.GetString(plainBytes); + } + catch (Exception ex) + { + throw new Exceptions.WechatTenpayEventDecryptionException("Decrypt event resource failed. Please see the `InnerException` for more details.", ex); + } + } + break; + + default: + { + throw new Exceptions.WechatTenpayEventDecryptionException($"Unsupported encryption algorithm: \"{resource.Algorithm}\"."); + } } return client.JsonSerializer.Deserialize(plainJson); diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Extensions/WechatTenpayClientEventVerificationExtensions.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Extensions/WechatTenpayClientEventVerificationExtensions.cs index 5f815f87..1727fa0b 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Extensions/WechatTenpayClientEventVerificationExtensions.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Extensions/WechatTenpayClientEventVerificationExtensions.cs @@ -1,4 +1,4 @@ -using System; +using System; namespace SKIT.FlurlHttpClient.Wechat.TenpayV3 { @@ -21,7 +21,42 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3 /// public static bool VerifyEventSignature(this WechatTenpayClient client, string callbackTimestamp, string callbackNonce, string callbackBody, string callbackSignature, string callbackSerialNumber) { - return VerifyEventSignature(client, callbackTimestamp, callbackNonce, callbackBody, callbackSignature, callbackSerialNumber, out _); + return VerifyEventSignature( + client, + callbackTimestamp: callbackTimestamp, + callbackNonce: callbackNonce, + callbackBody: callbackBody, + callbackSignature: callbackSignature, + callbackSignatureType: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, + callbackSerialNumber: callbackSerialNumber + ); + } + + /// + /// 验证回调通知事件签名。 + /// REF: https://pay.weixin.qq.com/wiki/doc/apiv3/wechatpay/wechatpay4_1.shtml + /// REF: https://pay.weixin.qq.com/wiki/doc/apiv3_partner/wechatpay/wechatpay4_1.shtml + /// + /// + /// 微信回调通知中的 Wechatpay-Timestamp 字段。 + /// 微信回调通知中的 Wechatpay-Nonce 字段。 + /// 微信回调通知中请求正文。 + /// 微信回调通知中的 Wechatpay-Signature 字段。 + /// 微信回调通知中的 Wechatpay-Signature-Type 字段。 + /// 微信回调通知中的 Wechatpay-Serial 字段。 + /// + public static bool VerifyEventSignature(this WechatTenpayClient client, string callbackTimestamp, string callbackNonce, string callbackBody, string callbackSignature, string callbackSignatureType, string callbackSerialNumber) + { + return VerifyEventSignature( + client, + callbackTimestamp: callbackTimestamp, + callbackNonce: callbackNonce, + callbackBody: callbackBody, + callbackSignature: callbackSignature, + callbackSignatureType: callbackSignatureType, + callbackSerialNumber: callbackSerialNumber, + out _ + ); } /// @@ -39,17 +74,60 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3 /// /// public static bool VerifyEventSignature(this WechatTenpayClient client, string callbackTimestamp, string callbackNonce, string callbackBody, string callbackSignature, string callbackSerialNumber, out Exception? error) + { + return VerifyEventSignature( + client, + callbackTimestamp: callbackTimestamp, + callbackNonce: callbackNonce, + callbackBody: callbackBody, + callbackSignature: callbackSignature, + callbackSignatureType: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, + callbackSerialNumber: callbackSerialNumber, + out error + ); + } + + /// + /// 验证回调通知事件签名。 + /// REF: https://pay.weixin.qq.com/wiki/doc/apiv3/wechatpay/wechatpay4_1.shtml + /// REF: https://pay.weixin.qq.com/wiki/doc/apiv3_partner/wechatpay/wechatpay4_1.shtml + /// + /// + /// 微信回调通知中的 Wechatpay-Timestamp 字段。 + /// 微信回调通知中的 Wechatpay-Nonce 字段。 + /// 微信回调通知中请求正文。 + /// 微信回调通知中的 Wechatpay-Signature 字段。 + /// 微信回调通知中的 Wechatpay-Signature-Type 字段。 + /// 微信回调通知中的 Wechatpay-Serial 字段。 + /// + /// + /// + public static bool VerifyEventSignature(this WechatTenpayClient client, string callbackTimestamp, string callbackNonce, string callbackBody, string callbackSignature, string callbackSignatureType, string callbackSerialNumber, out Exception? error) { if (client == null) throw new ArgumentNullException(nameof(client)); if (callbackTimestamp == null) throw new ArgumentNullException(nameof(callbackTimestamp)); if (callbackNonce == null) throw new ArgumentNullException(nameof(callbackNonce)); if (callbackBody == null) throw new ArgumentNullException(nameof(callbackBody)); if (callbackSignature == null) throw new ArgumentNullException(nameof(callbackSignature)); + if (callbackSignatureType == null) throw new ArgumentNullException(nameof(callbackSignatureType)); if (callbackSerialNumber == null) throw new ArgumentNullException(nameof(callbackSerialNumber)); - bool ret = WechatTenpayClientSignExtensions.VerifySignature(client, callbackTimestamp, callbackNonce, callbackBody, callbackSignature, callbackSerialNumber, out error); + bool ret = WechatTenpayClientSignExtensions.VerifySignature( + client, + strTimestamp: callbackTimestamp, + strNonce: callbackNonce, + strContent: callbackBody, + strSignature: callbackSignature, + strSignatureScheme: callbackSignatureType, + strSerialNumber: callbackSerialNumber, + out error + ); + if (error != null) + { error = new Exceptions.WechatTenpayEventVerificationException("Verify signature of event failed. Please see the `InnerException` for more details.", error); + } + return ret; } } diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Extensions/WechatTenpayClientParameterExtensions.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Extensions/WechatTenpayClientParameterExtensions.cs index 08b89954..30285f29 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Extensions/WechatTenpayClientParameterExtensions.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Extensions/WechatTenpayClientParameterExtensions.cs @@ -37,7 +37,7 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3 string package = $"prepay_id={prepayId}"; string sign = Utilities.RSAUtility.SignWithSHA256( privateKey: client.Credentials.MerchantCertificatePrivateKey, - plainText: $"{appId}\n{timestamp}\n{nonce}\n{package}\n" + message: $"{appId}\n{timestamp}\n{nonce}\n{package}\n" ); return new ReadOnlyDictionary(new Dictionary() @@ -92,7 +92,7 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3 string nonce = Guid.NewGuid().ToString("N"); string sign = Utilities.RSAUtility.SignWithSHA256( privateKey: client.Credentials.MerchantCertificatePrivateKey, - plainText: $"{appId}\n{timestamp}\n{nonce}\n{prepayId}\n" + message: $"{appId}\n{timestamp}\n{nonce}\n{prepayId}\n" ); return new ReadOnlyDictionary(new Dictionary() diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Extensions/WechatTenpayClientRequestEncryptionExtensions.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Extensions/WechatTenpayClientRequestEncryptionExtensions.cs index 0f685451..42e8c64a 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Extensions/WechatTenpayClientRequestEncryptionExtensions.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Extensions/WechatTenpayClientRequestEncryptionExtensions.cs @@ -1,6 +1,7 @@ -using System; +using System; using System.Linq; using System.Reflection; +using System.Text; namespace SKIT.FlurlHttpClient.Wechat.TenpayV3 { @@ -9,6 +10,147 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3 /// public static class WechatTenpayClientRequestEncryptionExtensions { + private static TRequest InnerEncryptRequestSensitivePropertyByRSA(WechatTenpayClient client, TRequest request) + where TRequest : WechatTenpayRequest + { + Utilities.ReflectionUtility.ReplacePropertyStringValue(ref request, (target, currentProp, oldValue) => + { + var attribute = currentProp + .GetCustomAttributes() + .FirstOrDefault(attr => Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256.Equals(attr.Scheme)); + if (attribute == null) + return (false, oldValue); + + if (client.PlatformCertificateManager == null) + throw new Exceptions.WechatTenpayRequestEncryptionException("Encrypt request failed, because the platform certificate manager is not initialized."); + + string certificate; + if (string.IsNullOrEmpty(request.WechatpayCertificateSerialNumber)) + { + // 如果未在请求中指定特定的平台证书序列号,从管理器中取过期时间最远的 + var entries = client.PlatformCertificateManager.AllEntries() + .Where(e => Settings.CertificateEntry.ALGORITHM_TYPE_RSA.Equals(e.AlgorithmType)) + .OrderByDescending(e => e.ExpireTime); + if (!entries.Any()) + { + throw new Exceptions.WechatTenpayEventVerificationException("Encrypt request failed, because there is no platform certificate in the manager, please make sure you have downloaded platform certificates first."); + } + + var entry = entries.First(); + certificate = entry.Certificate; + request.WechatpayCertificateSerialNumber = entry.SerialNumber; + } + else + { + // 如果已在请求中指定特定的平台证书序列号,直接从管理器中取值 + var entry = client.PlatformCertificateManager.GetEntry(request.WechatpayCertificateSerialNumber!); + if (!entry.HasValue) + { + throw new Exceptions.WechatTenpayEventVerificationException($"Encrypt request failed, because there is no platform certificate matched the serial number: \"{request.WechatpayCertificateSerialNumber}\", please make sure you have downloaded platform certificates first."); + } + + certificate = entry.Value.Certificate; + } + + string newValue; + switch (attribute.Algorithm) + { + case Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1: + { + newValue = Utilities.RSAUtility.EncryptWithECBByCertificate( + certificate: certificate, + plainText: oldValue + ); + } + break; + + case Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS1: + { + newValue = Utilities.RSAUtility.EncryptWithECBByCertificate( + certificate: certificate, + plainText: oldValue, + paddingMode: "PKCS1PADDING" + ); + } + break; + + default: + { + throw new Exceptions.WechatTenpayRequestEncryptionException($"Unsupported encryption algorithm: \"{attribute.Algorithm}\"."); + } + } + + return (true, newValue); + }); + return request; + } + + private static TRequest InnerEncryptRequestSensitivePropertyBySM(WechatTenpayClient client, TRequest request) + where TRequest : WechatTenpayRequest + { + Utilities.ReflectionUtility.ReplacePropertyStringValue(ref request, (target, currentProp, oldValue) => + { + var attribute = currentProp + .GetCustomAttributes() + .FirstOrDefault(attr => Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3.Equals(attr.Scheme)); + if (attribute == null) + return (false, oldValue); + + if (client.PlatformCertificateManager == null) + throw new Exceptions.WechatTenpayRequestEncryptionException("Encrypt request failed, because the platform certificate manager is not initialized."); + + string certificate; + if (string.IsNullOrEmpty(request.WechatpayCertificateSerialNumber)) + { + // 如果未在请求中指定特定的平台证书序列号,从管理器中取过期时间最远的 + var entries = client.PlatformCertificateManager.AllEntries() + .Where(e => Settings.CertificateEntry.ALGORITHM_TYPE_SM2.Equals(e.AlgorithmType)) + .OrderByDescending(e => e.ExpireTime); + if (!entries.Any()) + { + throw new Exceptions.WechatTenpayEventVerificationException("Encrypt request failed, because there is no platform certificate in the manager, please make sure you have downloaded platform certificates first."); + } + + var entry = entries.First(); + certificate = entry.Certificate; + request.WechatpayCertificateSerialNumber = entry.SerialNumber; + } + else + { + // 如果已在请求中指定特定的平台证书序列号,直接从管理器中取值 + var entry = client.PlatformCertificateManager.GetEntry(request.WechatpayCertificateSerialNumber!); + if (!entry.HasValue) + { + throw new Exceptions.WechatTenpayEventVerificationException($"Encrypt request failed, because there is no platform certificate matched the serial number: \"{request.WechatpayCertificateSerialNumber}\", please make sure you have downloaded platform certificates first."); + } + + certificate = entry.Value.Certificate; + } + + string newValue; + switch (attribute.Algorithm) + { + case Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1: + { + newValue = Utilities.SM2Utility.EncryptByCertificate( + certificate: certificate, + plainText: oldValue, + asn1Encoding: true + ); + } + break; + + default: + { + throw new Exceptions.WechatTenpayRequestEncryptionException($"Unsupported encryption algorithm: \"{attribute.Algorithm}\"."); + } + } + + return (true, newValue); + }); + return request; + } + /// /// 加密请求中传入的敏感数据。该方法会改变传入的请求模型对象。 /// @@ -23,81 +165,30 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3 try { + // 遍历并加密被标记为敏感数据的字段 bool requireEncrypt = Attribute.IsDefined(request.GetType(), typeof(WechatTenpaySensitiveAttribute)); if (requireEncrypt) { - // 遍历并加密被标记为敏感数据的字段 - Utilities.ReflectionUtility.ReplacePropertyStringValue(ref request, (target, currentProp, oldValue) => + switch (client.Credentials.SignScheme) { - var attr = currentProp.GetCustomAttribute(); - if (attr == null) - return (false, oldValue); + case Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256: + return InnerEncryptRequestSensitivePropertyByRSA(client, request); - if (Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1.Equals(attr.Algorithm) || - Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS1.Equals(attr.Algorithm)) - { - if (client.PlatformCertificateManager == null) - throw new Exceptions.WechatTenpayRequestEncryptionException("Encrypt request failed, because there is no platform certificate in the manager."); - - string certificate; - - if (!string.IsNullOrEmpty(request.WechatpayCertificateSerialNumber)) - { - // 如果已在请求中指定特定的平台证书序列号,直接从管理器中取值 - var cert = client.PlatformCertificateManager.GetEntry(request.WechatpayCertificateSerialNumber!); - if (!cert.HasValue) - { - throw new Exceptions.WechatTenpayEventVerificationException("Encrypt request failed, because there is no platform certificate matched the serial number."); - } - - certificate = cert.Value.Certificate; - } - else - { - // 如果未在请求中指定特定的平台证书序列号,从管理器中取过期时间最远的 - var certs = client.PlatformCertificateManager.AllEntries().OrderByDescending(e => e.ExpireTime); - if (!certs.Any()) - { - throw new Exceptions.WechatTenpayEventVerificationException("Encrypt request failed, because there is no platform certificate in the manager."); - } - - var cert = certs.First(); - certificate = cert.Certificate; - request.WechatpayCertificateSerialNumber = cert.SerialNumber; - } - - string newValue = oldValue; - if (Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1.Equals(attr.Algorithm)) - { - newValue = Utilities.RSAUtility.EncryptWithECBByCertificate( - certificate: certificate, - plainText: oldValue - ); - } - else if (Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS1.Equals(attr.Algorithm)) - { - newValue = Utilities.RSAUtility.EncryptWithECBByCertificate( - certificate: certificate, - plainText: oldValue, - paddingMode: "PKCS1PADDING" - ); - } - - return (true, newValue); - } - else - { - throw new Exceptions.WechatTenpayRequestEncryptionException("Unsupported encryption algorithm."); - } - }); + case Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3: + return InnerEncryptRequestSensitivePropertyBySM(client, request); + } } + + return request; } - catch (Exception ex) when (!(ex is Exceptions.WechatTenpayRequestEncryptionException)) + catch (WechatTenpayException) + { + throw; + } + catch (Exception ex) { throw new Exceptions.WechatTenpayRequestEncryptionException("Encrypt request failed. Please see the `InnerException` for more details.", ex); } - - return request; } } } diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Extensions/WechatTenpayClientResponseDecryptionExtensions.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Extensions/WechatTenpayClientResponseDecryptionExtensions.cs index ce63f9a6..54d64b99 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Extensions/WechatTenpayClientResponseDecryptionExtensions.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Extensions/WechatTenpayClientResponseDecryptionExtensions.cs @@ -1,6 +1,7 @@ -using System; +using System; using System.Linq; using System.Reflection; +using System.Text; namespace SKIT.FlurlHttpClient.Wechat.TenpayV3 { @@ -9,6 +10,143 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3 /// public static class WechatTenpayClientResponseDecryptionExtensions { + private static TResponse InnerDecryptResponseSensitiveProperty(WechatTenpayClient client, TResponse response) + where TResponse : Models.QueryCertificatesResponse + { + if (response.CertificateList == null) + return response; + + foreach (var certificate in response.CertificateList) + { + if (certificate.EncryptCertificate == null) + continue; + + switch (certificate.EncryptCertificate.Algorithm) + { + case Constants.EncryptionAlgorithms.AEAD_AES_256_GCM: + { + if (string.IsNullOrEmpty(client.Credentials.MerchantCertificatePrivateKey)) + throw new Exceptions.WechatTenpayResponseDecryptionException("Decrypt response failed, because there is no merchant private key."); + + certificate.EncryptCertificate.CipherText = Utilities.AESUtility.DecryptWithGCM( + key: client.Credentials.MerchantV3Secret, + nonce: certificate.EncryptCertificate.Nonce, + aad: certificate.EncryptCertificate.AssociatedData, + cipherText: certificate.EncryptCertificate.CipherText + ); + } + break; + + case Constants.EncryptionAlgorithms.AEAD_SM4_128_GCM: + { + if (string.IsNullOrEmpty(client.Credentials.MerchantV3Secret)) + throw new Exceptions.WechatTenpayResponseDecryptionException("Decrypt response failed, because there is no merchant APIv3 secret."); + + // REF: https://pay.weixin.qq.com/docs/merchant/development/shangmi/guide.html + // 由于 SM4 密钥长度的限制,密钥由 APIv3 密钥通过国密 SM3 Hash 计算生成。SM4 密钥取其摘要(256bit)的前 128bit。 + byte[] secretBytes = Utilities.SM3Utility.Hash(Encoding.UTF8.GetBytes(client.Credentials.MerchantV3Secret)); + byte[] keyBytes = new byte[16]; + Array.Copy(secretBytes, keyBytes, keyBytes.Length); + + byte[] plainBytes = Utilities.SM4Utility.DecryptWithGCM( + keyBytes: keyBytes, + nonceBytes: Encoding.UTF8.GetBytes(certificate.EncryptCertificate.Nonce), + aadBytes: Encoding.UTF8.GetBytes(certificate.EncryptCertificate.AssociatedData ?? string.Empty), + cipherBytes: Convert.FromBase64String(certificate.EncryptCertificate.CipherText) + ); + certificate.EncryptCertificate.CipherText = Encoding.UTF8.GetString(plainBytes); + } + break; + + default: + { + throw new Exceptions.WechatTenpayResponseDecryptionException($"Unsupported encryption algorithm: \"{certificate.EncryptCertificate.Algorithm}\"."); + } + } + } + + return response; + } + + private static TResponse InnerDecryptResponseSensitivePropertyByRSA(WechatTenpayClient client, TResponse response) + where TResponse : WechatTenpayResponse + { + Utilities.ReflectionUtility.ReplacePropertyStringValue(ref response, (target, currentProp, oldValue) => + { + var attribute = currentProp + .GetCustomAttributes() + .FirstOrDefault(attr => Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256.Equals(attr.Scheme)); + if (attribute == null) + return (false, oldValue); + + string newValue; + switch (attribute.Algorithm) + { + case Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1: + { + newValue = Utilities.RSAUtility.DecryptWithECB( + privateKey: client.Credentials.MerchantCertificatePrivateKey, + cipherText: oldValue + ); + } + break; + + case Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS1: + { + newValue = Utilities.RSAUtility.DecryptWithECB( + privateKey: client.Credentials.MerchantCertificatePrivateKey, + cipherText: oldValue, + paddingMode: "PKCS1PADDING" + ); + } + break; + + default: + { + throw new Exceptions.WechatTenpayResponseDecryptionException($"Unsupported encryption algorithm: \"{attribute.Algorithm}\"."); + } + } + + return (true, newValue); + }); + return response; + } + + private static TResponse InnerDecryptResponseSensitivePropertyBySM(WechatTenpayClient client, TResponse response) + where TResponse : WechatTenpayResponse + { + Utilities.ReflectionUtility.ReplacePropertyStringValue(ref response, (target, currentProp, oldValue) => + { + var attribute = currentProp + .GetCustomAttributes() + .FirstOrDefault(attr => Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3.Equals(attr.Scheme)); + if (attribute == null) + return (false, oldValue); + + string newValue; + switch (attribute.Algorithm) + { + case Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1: + { + newValue = Utilities.SM2Utility.Decrypt( + privateKey: client.Credentials.MerchantCertificatePrivateKey, + cipherText: oldValue, + asn1Encoding: true + ); + } + break; + + default: + { + throw new Exceptions.WechatTenpayResponseDecryptionException($"Unsupported encryption algorithm: \"{attribute.Algorithm}\"."); + } + } + + return (true, newValue); + }); + return response; + } + /// /// 解密响应中返回的敏感数据。该方法会改变传入的响应模型对象。 /// @@ -29,77 +167,33 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3 // [GET] /certificates 接口的响应模型需特殊处理 if (response is Models.QueryCertificatesResponse queryCertificatesResponse) { - if (queryCertificatesResponse.CertificateList == null) - return response; - - foreach (var certificateModel in queryCertificatesResponse.CertificateList) - { - if (Constants.EncryptionAlgorithms.AEAD_AES_256_GCM.Equals(certificateModel.EncryptCertificate?.Algorithm)) - { - if (string.IsNullOrEmpty(client.Credentials.MerchantCertificatePrivateKey)) - throw new Exceptions.WechatTenpayResponseDecryptionException("Decrypt response failed, because there is no merchant private key."); - - certificateModel.EncryptCertificate.CipherText = Utilities.AESUtility.DecryptWithGCM( - key: client.Credentials.MerchantV3Secret, - iv: certificateModel.EncryptCertificate.Nonce, - aad: certificateModel.EncryptCertificate.AssociatedData, - cipherText: certificateModel.EncryptCertificate.CipherText - ); - } - else - { - throw new Exceptions.WechatTenpayResponseDecryptionException("Unsupported decryption algorithm."); - } - } - - return response; + return (InnerDecryptResponseSensitiveProperty(client, queryCertificatesResponse) as TResponse)!; } + // 遍历并解密被标记为敏感数据的字段 bool requireDecrypt = Attribute.IsDefined(response.GetType(), typeof(WechatTenpaySensitiveAttribute)); if (requireDecrypt) { - // 遍历并解密被标记为敏感数据的字段 - Utilities.ReflectionUtility.ReplacePropertyStringValue(ref response, (target, currentProp, oldValue) => + switch (client.Credentials.SignScheme) { - var attr = currentProp.GetCustomAttribute(); - if (attr == null) - return (false, oldValue); + case Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256: + return InnerDecryptResponseSensitivePropertyByRSA(client, response); - if (Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1.Equals(attr.Algorithm) || - Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS1.Equals(attr.Algorithm)) - { - string newValue = oldValue; - if (Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1.Equals(attr.Algorithm)) - { - newValue = Utilities.RSAUtility.DecryptWithECB( - privateKey: client.Credentials.MerchantCertificatePrivateKey, - cipherText: oldValue - ); - } - else if (Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS1.Equals(attr.Algorithm)) - { - newValue = Utilities.RSAUtility.DecryptWithECB( - privateKey: client.Credentials.MerchantCertificatePrivateKey, - cipherText: oldValue, - paddingMode: "PKCS1PADDING" - ); - } - - return (true, newValue); - } - else - { - throw new Exceptions.WechatTenpayResponseDecryptionException("Unsupported decryption algorithm."); - } - }); + case Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3: + return InnerDecryptResponseSensitivePropertyBySM(client, response); + } } + + return response; } - catch (Exception ex) when (!(ex is Exceptions.WechatTenpayResponseDecryptionException)) + catch (WechatTenpayException) + { + throw; + } + catch (Exception ex) { throw new Exceptions.WechatTenpayResponseDecryptionException("Decrypt response failed. Please see the `InnerException` for more details.", ex); } - - return response; } } } diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Extensions/WechatTenpayClientResponseVerificationExtensions.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Extensions/WechatTenpayClientResponseVerificationExtensions.cs index 8b915a51..19745676 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Extensions/WechatTenpayClientResponseVerificationExtensions.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Extensions/WechatTenpayClientResponseVerificationExtensions.cs @@ -1,4 +1,4 @@ -using System; +using System; using System.Text; namespace SKIT.FlurlHttpClient.Wechat.TenpayV3 @@ -40,7 +40,16 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3 if (client == null) throw new ArgumentNullException(nameof(client)); if (response == null) throw new ArgumentNullException(nameof(response)); - return VerifyResponseSignature(client, response.WechatpayTimestamp, response.WechatpayNonce, Encoding.UTF8.GetString(response.RawBytes), response.WechatpaySignature, response.WechatpayCertificateSerialNumber, out error); + return VerifyResponseSignature( + client, + responseTimestamp: response.WechatpayTimestamp, + responseNonce: response.WechatpayNonce, + responseBody: Encoding.UTF8.GetString(response.RawBytes), + responseSignature: response.WechatpaySignature, + responseSignatureType: response.WechatpaySignatureType, + responseSerialNumber: response.WechatpayCertificateSerialNumber, + out error + ); } /// @@ -57,7 +66,42 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3 /// public static bool VerifyResponseSignature(this WechatTenpayClient client, string responseTimestamp, string responseNonce, string responseBody, string responseSignature, string responseSerialNumber) { - return VerifyResponseSignature(client, responseTimestamp, responseNonce, responseBody, responseSignature, responseSerialNumber, out _); + return VerifyResponseSignature( + client, + responseTimestamp: responseTimestamp, + responseNonce: responseNonce, + responseBody: responseBody, + responseSignature: responseSignature, + responseSignatureType: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, + responseSerialNumber: responseSerialNumber + ); + } + + /// + /// 验证响应签名。 + /// REF: https://pay.weixin.qq.com/wiki/doc/apiv3/wechatpay/wechatpay4_1.shtml + /// REF: https://pay.weixin.qq.com/wiki/doc/apiv3_partner/wechatpay/wechatpay4_1.shtml + /// + /// + /// + /// 。 + /// + /// + /// + /// + /// + public static bool VerifyResponseSignature(this WechatTenpayClient client, string responseTimestamp, string responseNonce, string responseBody, string responseSignature, string responseSignatureType, string responseSerialNumber) + { + return VerifyResponseSignature( + client, + responseTimestamp: responseTimestamp, + responseNonce: responseNonce, + responseBody: responseBody, + responseSignature: responseSignature, + responseSignatureType: responseSignatureType, + responseSerialNumber, + out _ + ); } /// @@ -76,17 +120,61 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3 /// /// public static bool VerifyResponseSignature(this WechatTenpayClient client, string responseTimestamp, string responseNonce, string responseBody, string responseSignature, string responseSerialNumber, out Exception? error) + { + return VerifyResponseSignature( + client, + responseTimestamp: responseTimestamp, + responseNonce: responseNonce, + responseBody: responseBody, + responseSignature: responseSignature, + responseSignatureType: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, + responseSerialNumber, + out error + ); + } + + /// + /// 验证响应签名。 + /// REF: https://pay.weixin.qq.com/wiki/doc/apiv3/wechatpay/wechatpay4_1.shtml + /// REF: https://pay.weixin.qq.com/wiki/doc/apiv3_partner/wechatpay/wechatpay4_1.shtml + /// + /// + /// + /// + /// 。 + /// + /// + /// + /// + /// + /// + /// + public static bool VerifyResponseSignature(this WechatTenpayClient client, string responseTimestamp, string responseNonce, string responseBody, string responseSignature, string responseSignatureType, string responseSerialNumber, out Exception? error) { if (client == null) throw new ArgumentNullException(nameof(client)); if (responseTimestamp == null) throw new ArgumentNullException(nameof(responseTimestamp)); if (responseNonce == null) throw new ArgumentNullException(nameof(responseNonce)); if (responseBody == null) throw new ArgumentNullException(nameof(responseBody)); if (responseSignature == null) throw new ArgumentNullException(nameof(responseSignature)); + if (responseSignatureType == null) throw new ArgumentNullException(nameof(responseSignatureType)); if (responseSerialNumber == null) throw new ArgumentNullException(nameof(responseSerialNumber)); - bool ret = WechatTenpayClientSignExtensions.VerifySignature(client, responseTimestamp, responseNonce, responseBody, responseSignature, responseSerialNumber, out error); + bool ret = WechatTenpayClientSignExtensions.VerifySignature( + client, + strTimestamp: responseTimestamp, + strNonce: responseNonce, + strContent: responseBody, + strSignature: responseSignature, + strSignatureScheme: responseSignatureType, + strSerialNumber: responseSerialNumber, + out error + ); + if (error != null) + { error = new Exceptions.WechatTenpayEventVerificationException("Verify signature of response failed. Please see the `InnerException` for more details.", error); + } + return ret; } } diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Interceptors/WechatTenpayRequestSignatureInterceptor.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Interceptors/WechatTenpayRequestSignatureInterceptor.cs index ca2232f9..8e34ffbe 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Interceptors/WechatTenpayRequestSignatureInterceptor.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Interceptors/WechatTenpayRequestSignatureInterceptor.cs @@ -1,4 +1,4 @@ -using System; +using System; using System.Linq; using System.Net.Http; using System.Threading.Tasks; @@ -46,16 +46,29 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Interceptors body = flurlCall.RequestBody ?? string.Empty; } - string plainText = $"{method}\n{url}\n{timestamp}\n{nonce}\n{body}\n"; + string msgText = $"{method}\n{url}\n{timestamp}\n{nonce}\n{body}\n"; string signText; switch (_scheme) { - case Constants.SignSchemes.WECHATPAY2_SHA256_RSA2048: + case Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256: { try { - signText = Utilities.RSAUtility.SignWithSHA256(_mchCertPk, plainText); + signText = Utilities.RSAUtility.SignWithSHA256(_mchCertPk, msgText); + } + catch (Exception ex) + { + throw new Exceptions.WechatTenpayRequestSignatureException("Generate signature of request failed. Please see the `InnerException` for more details.", ex); + } + } + break; + + case Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3: + { + try + { + signText = Utilities.SM2Utility.SignWithSM3(_mchCertPk, msgText); } catch (Exception ex) { @@ -65,7 +78,7 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Interceptors break; default: - throw new Exceptions.WechatTenpayRequestSignatureException("Unsupported authorization scheme."); + throw new Exceptions.WechatTenpayRequestSignatureException($"Unsupported signature scheme: \"{_scheme}\"."); } string auth = $"mchid=\"{_mchId}\",nonce_str=\"{nonce}\",signature=\"{signText}\",timestamp=\"{timestamp}\",serial_no=\"{_mchCertSn}\""; diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/Apply4SubMerchant/CreateApplyForSubMerchantApplymentRequest.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/Apply4SubMerchant/CreateApplyForSubMerchantApplymentRequest.cs index f20c7db3..fc0642d6 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/Apply4SubMerchant/CreateApplyForSubMerchantApplymentRequest.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/Apply4SubMerchant/CreateApplyForSubMerchantApplymentRequest.cs @@ -24,7 +24,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("contact_name")] [System.Text.Json.Serialization.JsonPropertyName("contact_name")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string ContactName { get; set; } = string.Empty; /// @@ -39,7 +40,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("contact_id_number")] [System.Text.Json.Serialization.JsonPropertyName("contact_id_number")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string? IdNumber { get; set; } /// @@ -89,7 +91,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("mobile_phone")] [System.Text.Json.Serialization.JsonPropertyName("mobile_phone")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string MobileNumber { get; set; } = string.Empty; /// @@ -97,7 +100,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("contact_email")] [System.Text.Json.Serialization.JsonPropertyName("contact_email")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string Email { get; set; } = string.Empty; } @@ -414,7 +418,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("id_card_name")] [System.Text.Json.Serialization.JsonPropertyName("id_card_name")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string IdCardName { get; set; } = string.Empty; /// @@ -422,7 +427,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("id_card_number")] [System.Text.Json.Serialization.JsonPropertyName("id_card_number")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string IdCardNumber { get; set; } = string.Empty; /// @@ -430,7 +436,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("id_card_address")] [System.Text.Json.Serialization.JsonPropertyName("id_card_address")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string? IdCardAddress { get; set; } /// @@ -469,7 +476,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("id_doc_name")] [System.Text.Json.Serialization.JsonPropertyName("id_doc_name")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string IdDocumentName { get; set; } = string.Empty; /// @@ -477,7 +485,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("id_doc_number")] [System.Text.Json.Serialization.JsonPropertyName("id_doc_number")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string IdDocumentNumber { get; set; } = string.Empty; /// @@ -485,7 +494,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("id_doc_address")] [System.Text.Json.Serialization.JsonPropertyName("id_doc_address")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string? IdDocumentAddress { get; set; } /// @@ -561,7 +571,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("ubo_id_doc_name")] [System.Text.Json.Serialization.JsonPropertyName("ubo_id_doc_name")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string IdName { get; set; } = string.Empty; /// @@ -583,7 +594,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("ubo_id_doc_number")] [System.Text.Json.Serialization.JsonPropertyName("ubo_id_doc_number")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string? IdNumber { get; set; } /// @@ -591,7 +603,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("ubo_id_doc_address")] [System.Text.Json.Serialization.JsonPropertyName("ubo_id_doc_address")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string? IdAddress { get; set; } /// @@ -1009,7 +1022,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("account_name")] [System.Text.Json.Serialization.JsonPropertyName("account_name")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string AccountName { get; set; } = string.Empty; /// @@ -1017,7 +1031,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("account_number")] [System.Text.Json.Serialization.JsonPropertyName("account_number")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string AccountNumber { get; set; } = string.Empty; /// diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/Apply4SubMerchant/Settlement/ModifyApplyForSubMerchantSettlementRequest.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/Apply4SubMerchant/Settlement/ModifyApplyForSubMerchantSettlementRequest.cs index e7297e96..f40db045 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/Apply4SubMerchant/Settlement/ModifyApplyForSubMerchantSettlementRequest.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/Apply4SubMerchant/Settlement/ModifyApplyForSubMerchantSettlementRequest.cs @@ -1,4 +1,4 @@ -namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models +namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models { /// /// 表示 [POST] /apply4sub/sub_merchants/{sub_mchid}/modify-settlement 接口的请求。 @@ -25,7 +25,8 @@ /// [Newtonsoft.Json.JsonProperty("account_number")] [System.Text.Json.Serialization.JsonPropertyName("account_number")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string AccountNumber { get; set; } = string.Empty; /// diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/Apply4Subject/CreateApplyForSubjectApplymentRequest.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/Apply4Subject/CreateApplyForSubjectApplymentRequest.cs index 6a216b2a..25f0a287 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/Apply4Subject/CreateApplyForSubjectApplymentRequest.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/Apply4Subject/CreateApplyForSubjectApplymentRequest.cs @@ -1,4 +1,4 @@ -using System.Collections.Generic; +using System.Collections.Generic; namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models { @@ -24,7 +24,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("name")] [System.Text.Json.Serialization.JsonPropertyName("name")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string ContactName { get; set; } = string.Empty; /// @@ -39,7 +40,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("id_card_number")] [System.Text.Json.Serialization.JsonPropertyName("id_card_number")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string? IdNumber { get; set; } /// @@ -82,7 +84,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("mobile")] [System.Text.Json.Serialization.JsonPropertyName("mobile")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string MobileNumber { get; set; } = string.Empty; } @@ -345,7 +348,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("identification_name")] [System.Text.Json.Serialization.JsonPropertyName("identification_name")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string IdName { get; set; } = string.Empty; /// @@ -353,7 +357,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("identification_number")] [System.Text.Json.Serialization.JsonPropertyName("identification_number")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string? IdNumber { get; set; } /// @@ -361,7 +366,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("identification_address")] [System.Text.Json.Serialization.JsonPropertyName("identification_address")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string? IdAddress { get; set; } /// @@ -414,7 +420,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("ubo_id_doc_name")] [System.Text.Json.Serialization.JsonPropertyName("ubo_id_doc_name")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string IdName { get; set; } = string.Empty; /// @@ -436,7 +443,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("ubo_id_doc_number")] [System.Text.Json.Serialization.JsonPropertyName("ubo_id_doc_number")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string? IdNumber { get; set; } /// @@ -444,7 +452,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("ubo_id_doc_address")] [System.Text.Json.Serialization.JsonPropertyName("ubo_id_doc_address")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string? IdAddress { get; set; } /// diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/Bill/GetBillSubMerchantFundflowBillResponse.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/Bill/GetBillSubMerchantFundflowBillResponse.cs index 28fad2dc..20fdd2aa 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/Bill/GetBillSubMerchantFundflowBillResponse.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/Bill/GetBillSubMerchantFundflowBillResponse.cs @@ -1,4 +1,4 @@ -namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models +namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models { /// /// 表示 [GET] /bill/sub-merchant-fundflowbill 接口的响应。 @@ -43,7 +43,8 @@ /// [Newtonsoft.Json.JsonProperty("encrypt_key")] [System.Text.Json.Serialization.JsonPropertyName("encrypt_key")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string EncryptKey { get; set; } = default!; /// diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/BrandProfitSharing/CreateBrandProfitSharingOrderRequest.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/BrandProfitSharing/CreateBrandProfitSharingOrderRequest.cs index a4347d11..e9f01a23 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/BrandProfitSharing/CreateBrandProfitSharingOrderRequest.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/BrandProfitSharing/CreateBrandProfitSharingOrderRequest.cs @@ -1,4 +1,4 @@ -using System.Collections.Generic; +using System.Collections.Generic; namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models { @@ -31,7 +31,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("name")] [System.Text.Json.Serialization.JsonPropertyName("name")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string? Name { get; set; } /// diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/Capital/Banks/QueryCapitalBanksByBankAccountRequest.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/Capital/Banks/QueryCapitalBanksByBankAccountRequest.cs index 4305873f..feed1d39 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/Capital/Banks/QueryCapitalBanksByBankAccountRequest.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/Capital/Banks/QueryCapitalBanksByBankAccountRequest.cs @@ -1,4 +1,4 @@ -namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models +namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models { /// /// 表示 [GET] /capital/capitallhh/banks/search-banks-by-bank-account 接口的请求。 @@ -11,7 +11,8 @@ /// [Newtonsoft.Json.JsonIgnore] [System.Text.Json.Serialization.JsonIgnore] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string AccountNumber { get; set; } = string.Empty; } } diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/Certificates/QueryCertificatesResponse.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/Certificates/QueryCertificatesResponse.cs index 052799f5..aa5a622b 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/Certificates/QueryCertificatesResponse.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/Certificates/QueryCertificatesResponse.cs @@ -1,4 +1,4 @@ -using System; +using System; namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models { @@ -42,7 +42,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("ciphertext")] [System.Text.Json.Serialization.JsonPropertyName("ciphertext")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.AEAD_AES_256_GCM)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.AEAD_AES_256_GCM)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.AEAD_SM4_128_GCM)] public string CipherText { get; set; } = default!; } } diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/EcommerceApplyments/CreateEcommerceApplymentRequest.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/EcommerceApplyments/CreateEcommerceApplymentRequest.cs index 30ddd809..c83c6c20 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/EcommerceApplyments/CreateEcommerceApplymentRequest.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/EcommerceApplyments/CreateEcommerceApplymentRequest.cs @@ -1,4 +1,4 @@ -using System.Collections.Generic; +using System.Collections.Generic; namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models { @@ -107,7 +107,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("id_card_name")] [System.Text.Json.Serialization.JsonPropertyName("id_card_name")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string IdCardName { get; set; } = string.Empty; /// @@ -115,7 +116,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("id_card_number")] [System.Text.Json.Serialization.JsonPropertyName("id_card_number")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string IdCardNumber { get; set; } = string.Empty; /// @@ -123,7 +125,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("id_card_address")] [System.Text.Json.Serialization.JsonPropertyName("id_card_address")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string? IdCardAddress { get; set; } /// @@ -162,7 +165,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("id_doc_name")] [System.Text.Json.Serialization.JsonPropertyName("id_doc_name")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string IdDocumentName { get; set; } = string.Empty; /// @@ -170,7 +174,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("id_doc_number")] [System.Text.Json.Serialization.JsonPropertyName("id_doc_number")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string IdDocumentNumber { get; set; } = string.Empty; /// @@ -178,7 +183,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("id_doc_address")] [System.Text.Json.Serialization.JsonPropertyName("id_doc_address")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string? IdDocumentAddress { get; set; } /// @@ -210,7 +216,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("contact_name")] [System.Text.Json.Serialization.JsonPropertyName("contact_name")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string ContactName { get; set; } = string.Empty; /// @@ -225,7 +232,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("contact_id_card_number")] [System.Text.Json.Serialization.JsonPropertyName("contact_id_card_number")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string? IdNumber { get; set; } /// @@ -268,7 +276,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("mobile_phone")] [System.Text.Json.Serialization.JsonPropertyName("mobile_phone")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string MobileNumber { get; set; } = string.Empty; /// @@ -276,7 +285,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("contact_email")] [System.Text.Json.Serialization.JsonPropertyName("contact_email")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string Email { get; set; } = string.Empty; } @@ -294,7 +304,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("ubo_id_doc_name")] [System.Text.Json.Serialization.JsonPropertyName("ubo_id_doc_name")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string IdName { get; set; } = string.Empty; /// @@ -316,7 +327,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("ubo_id_doc_number")] [System.Text.Json.Serialization.JsonPropertyName("ubo_id_doc_number")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string? IdNumber { get; set; } /// @@ -324,7 +336,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("ubo_id_doc_address")] [System.Text.Json.Serialization.JsonPropertyName("ubo_id_doc_address")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string? IdAddress { get; set; } /// @@ -383,7 +396,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("account_name")] [System.Text.Json.Serialization.JsonPropertyName("account_name")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string AccountName { get; set; } = string.Empty; /// @@ -391,7 +405,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("account_number")] [System.Text.Json.Serialization.JsonPropertyName("account_number")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string AccountNumber { get; set; } = string.Empty; /// diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/EcommerceApplyments/GetEcommerceApplymentByOutRequestNumberResponse.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/EcommerceApplyments/GetEcommerceApplymentByOutRequestNumberResponse.cs index 859cb86b..ea24d0ef 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/EcommerceApplyments/GetEcommerceApplymentByOutRequestNumberResponse.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/EcommerceApplyments/GetEcommerceApplymentByOutRequestNumberResponse.cs @@ -1,4 +1,4 @@ -using System; +using System; namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models { @@ -17,7 +17,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("account_name")] [System.Text.Json.Serialization.JsonPropertyName("account_name")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string AccountName { get; set; } = default!; /// @@ -25,7 +26,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("account_no")] [System.Text.Json.Serialization.JsonPropertyName("account_no")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string? AccountNumber { get; set; } /// diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/EcommerceBill/GetEcommerceBillFundflowBillResponse.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/EcommerceBill/GetEcommerceBillFundflowBillResponse.cs index 50eacb0c..ede08cc3 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/EcommerceBill/GetEcommerceBillFundflowBillResponse.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/EcommerceBill/GetEcommerceBillFundflowBillResponse.cs @@ -1,4 +1,4 @@ -namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models +namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models { /// /// 表示 [GET] /ecommerce/bill/fundflowbill 接口的响应。 @@ -43,7 +43,8 @@ /// [Newtonsoft.Json.JsonProperty("encrypt_key")] [System.Text.Json.Serialization.JsonPropertyName("encrypt_key")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string EncryptKey { get; set; } = default!; /// diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/EcommerceProfitSharing/CreateEcommerceProfitSharingOrderRequest.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/EcommerceProfitSharing/CreateEcommerceProfitSharingOrderRequest.cs index 8cbdf492..aebba4a2 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/EcommerceProfitSharing/CreateEcommerceProfitSharingOrderRequest.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/EcommerceProfitSharing/CreateEcommerceProfitSharingOrderRequest.cs @@ -1,4 +1,4 @@ -using System.Collections.Generic; +using System.Collections.Generic; namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models { @@ -31,7 +31,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("receiver_name")] [System.Text.Json.Serialization.JsonPropertyName("receiver_name")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string? Name { get; set; } /// diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/EcommerceProfitSharing/Receivers/AddEcommerceProfitSharingReceiverRequest.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/EcommerceProfitSharing/Receivers/AddEcommerceProfitSharingReceiverRequest.cs index 389aa1c3..405de0a1 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/EcommerceProfitSharing/Receivers/AddEcommerceProfitSharingReceiverRequest.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/EcommerceProfitSharing/Receivers/AddEcommerceProfitSharingReceiverRequest.cs @@ -1,4 +1,4 @@ -namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models +namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models { /// /// 表示 [POST] /ecommerce/profitsharing/receivers/add 接口的请求。 @@ -39,7 +39,8 @@ /// [Newtonsoft.Json.JsonProperty("encrypted_name")] [System.Text.Json.Serialization.JsonPropertyName("encrypted_name")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string? EncryptedName { get; set; } /// diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/HKCustoms/VerifyHKCustomsCertificateRequest.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/HKCustoms/VerifyHKCustomsCertificateRequest.cs index 11f54325..38b45228 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/HKCustoms/VerifyHKCustomsCertificateRequest.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/HKCustoms/VerifyHKCustomsCertificateRequest.cs @@ -1,4 +1,4 @@ -namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models +namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models { /// /// 表示 [POST] /customs/verify-certificate 接口的请求。 @@ -67,7 +67,8 @@ /// [Newtonsoft.Json.JsonProperty("certificate_id")] [System.Text.Json.Serialization.JsonPropertyName("certificate_id")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string CertificateId { get; set; } = string.Empty; /// @@ -75,7 +76,8 @@ /// [Newtonsoft.Json.JsonProperty("certificate_name")] [System.Text.Json.Serialization.JsonPropertyName("certificate_name")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string CertificateName { get; set; } = string.Empty; } } diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/HKMerchants/AddHKSubMerchantRequest.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/HKMerchants/AddHKSubMerchantRequest.cs index 388251bf..13f63ffc 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/HKMerchants/AddHKSubMerchantRequest.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/HKMerchants/AddHKSubMerchantRequest.cs @@ -1,4 +1,4 @@ -using System.Collections.Generic; +using System.Collections.Generic; namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models { @@ -17,7 +17,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("name")] [System.Text.Json.Serialization.JsonPropertyName("name")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string ContactName { get; set; } = string.Empty; /// @@ -25,7 +26,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("phone")] [System.Text.Json.Serialization.JsonPropertyName("phone")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string MobileNumber { get; set; } = string.Empty; /// @@ -33,7 +35,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("email")] [System.Text.Json.Serialization.JsonPropertyName("email")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string Email { get; set; } = string.Empty; } diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/HKMerchants/GetHKSubMerchantResponse.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/HKMerchants/GetHKSubMerchantResponse.cs index c9c61ecc..2e7a3623 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/HKMerchants/GetHKSubMerchantResponse.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/HKMerchants/GetHKSubMerchantResponse.cs @@ -1,4 +1,4 @@ -namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models +namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models { /// /// 表示 [GET] /merchants/{sub_mchid} 接口的响应。 @@ -14,7 +14,8 @@ /// [Newtonsoft.Json.JsonProperty("name")] [System.Text.Json.Serialization.JsonPropertyName("name")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string ContactName { get; set; } = default!; /// @@ -22,7 +23,8 @@ /// [Newtonsoft.Json.JsonProperty("phone")] [System.Text.Json.Serialization.JsonPropertyName("phone")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string MobileNumber { get; set; } = default!; /// @@ -30,7 +32,8 @@ /// [Newtonsoft.Json.JsonProperty("email")] [System.Text.Json.Serialization.JsonPropertyName("email")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string Email { get; set; } = default!; } diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/MarketingMemberCardOpen/Code/ImportMarketingMemberCardOpenCardPhoneRequest.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/MarketingMemberCardOpen/Code/ImportMarketingMemberCardOpenCardPhoneRequest.cs index ebe095e8..93dee329 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/MarketingMemberCardOpen/Code/ImportMarketingMemberCardOpenCardPhoneRequest.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/MarketingMemberCardOpen/Code/ImportMarketingMemberCardOpenCardPhoneRequest.cs @@ -1,4 +1,4 @@ -namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models +namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models { /// /// 表示 [POST] /marketing/membercard-open/cards/{card_id}/phone-membercard/import 接口的请求。 @@ -17,7 +17,8 @@ /// [Newtonsoft.Json.JsonProperty("encrypted_phone_number")] [System.Text.Json.Serialization.JsonPropertyName("encrypted_phone_number")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string EncryptedPhoneNumber { get; set; } = string.Empty; /// diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/MerchantService/ComplaintsV2/GetMerchantServiceComplaintByComplaintIdResponse.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/MerchantService/ComplaintsV2/GetMerchantServiceComplaintByComplaintIdResponse.cs index 2010955a..63fbccb5 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/MerchantService/ComplaintsV2/GetMerchantServiceComplaintByComplaintIdResponse.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/MerchantService/ComplaintsV2/GetMerchantServiceComplaintByComplaintIdResponse.cs @@ -118,7 +118,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("payer_phone")] [System.Text.Json.Serialization.JsonPropertyName("payer_phone")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string? PayerPhone { get; set; } /// diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/MerchantService/ComplaintsV2/QueryMerchantServiceComplaintsResponse.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/MerchantService/ComplaintsV2/QueryMerchantServiceComplaintsResponse.cs index 31262d79..a2d45905 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/MerchantService/ComplaintsV2/QueryMerchantServiceComplaintsResponse.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/MerchantService/ComplaintsV2/QueryMerchantServiceComplaintsResponse.cs @@ -1,4 +1,4 @@ -using System; +using System; namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models { @@ -65,7 +65,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("payer_phone")] [System.Text.Json.Serialization.JsonPropertyName("payer_phone")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string? PayerPhone { get; set; } /// diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/PartnerTransfer/Batches/GetPartnerTransferBatchDetailByOutDetailNumberResponse.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/PartnerTransfer/Batches/GetPartnerTransferBatchDetailByOutDetailNumberResponse.cs index 18b94927..8eff0e2c 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/PartnerTransfer/Batches/GetPartnerTransferBatchDetailByOutDetailNumberResponse.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/PartnerTransfer/Batches/GetPartnerTransferBatchDetailByOutDetailNumberResponse.cs @@ -1,4 +1,4 @@ -namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models +namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models { /// /// 表示 [GET] /partner-transfer/batches/out-batch-no/{out_batch_no}/details/out-detail-no/{out_detail_no} 接口的响应。 @@ -18,7 +18,8 @@ /// [Newtonsoft.Json.JsonProperty("username")] [System.Text.Json.Serialization.JsonPropertyName("username")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public override string UserName { get; set; } = default!; } } diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/PayScoreBill/GetPayScoreMerchantBillResponse.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/PayScoreBill/GetPayScoreMerchantBillResponse.cs index d7a89516..98a0e3ea 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/PayScoreBill/GetPayScoreMerchantBillResponse.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/PayScoreBill/GetPayScoreMerchantBillResponse.cs @@ -1,4 +1,4 @@ -namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models +namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models { /// /// 表示 [GET] /payscore/merchant-bill 接口的响应。 @@ -43,7 +43,8 @@ /// [Newtonsoft.Json.JsonProperty("encrypt_key")] [System.Text.Json.Serialization.JsonPropertyName("encrypt_key")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string EncryptKey { get; set; } = default!; /// diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/ProfitSharing/CreateProfitSharingOrderRequest.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/ProfitSharing/CreateProfitSharingOrderRequest.cs index 87e62bd4..46da683c 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/ProfitSharing/CreateProfitSharingOrderRequest.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/ProfitSharing/CreateProfitSharingOrderRequest.cs @@ -1,4 +1,4 @@ -using System.Collections.Generic; +using System.Collections.Generic; namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models { @@ -31,7 +31,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("name")] [System.Text.Json.Serialization.JsonPropertyName("name")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string? Name { get; set; } /// diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/ProfitSharing/Receivers/AddProfitSharingReceiverRequest.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/ProfitSharing/Receivers/AddProfitSharingReceiverRequest.cs index 5464a47c..841965e4 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/ProfitSharing/Receivers/AddProfitSharingReceiverRequest.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/ProfitSharing/Receivers/AddProfitSharingReceiverRequest.cs @@ -1,4 +1,4 @@ -namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models +namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models { /// /// 表示 [POST] /profitsharing/receivers/add 接口的请求。 @@ -46,7 +46,8 @@ /// [Newtonsoft.Json.JsonProperty("name")] [System.Text.Json.Serialization.JsonPropertyName("name")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string? Name { get; set; } /// diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/ProfitSharing/Receivers/AddProfitSharingReceiverResponse.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/ProfitSharing/Receivers/AddProfitSharingReceiverResponse.cs index 8c5f1437..547ac59b 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/ProfitSharing/Receivers/AddProfitSharingReceiverResponse.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/ProfitSharing/Receivers/AddProfitSharingReceiverResponse.cs @@ -1,4 +1,4 @@ -namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models +namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models { /// /// 表示 [POST] /profitsharing/receivers/add 接口的响应。 @@ -32,7 +32,8 @@ /// [Newtonsoft.Json.JsonProperty("name")] [System.Text.Json.Serialization.JsonPropertyName("name")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string? Name { get; set; } /// diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/SmartGuide/CreateSmartGuideRequest.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/SmartGuide/CreateSmartGuideRequest.cs index a1934bd0..84c3ebf1 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/SmartGuide/CreateSmartGuideRequest.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/SmartGuide/CreateSmartGuideRequest.cs @@ -1,4 +1,4 @@ -namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models +namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models { /// /// 表示 [POST] /smartguide/guides 接口的请求。 @@ -39,7 +39,8 @@ /// [Newtonsoft.Json.JsonProperty("name")] [System.Text.Json.Serialization.JsonPropertyName("name")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string UserName { get; set; } = string.Empty; /// @@ -47,7 +48,8 @@ /// [Newtonsoft.Json.JsonProperty("mobile")] [System.Text.Json.Serialization.JsonPropertyName("mobile")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string UserMobile { get; set; } = string.Empty; /// diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/SmartGuide/QuerySmartGuidesRequest.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/SmartGuide/QuerySmartGuidesRequest.cs index bbe2fc40..a283c56f 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/SmartGuide/QuerySmartGuidesRequest.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/SmartGuide/QuerySmartGuidesRequest.cs @@ -1,4 +1,4 @@ -namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models +namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models { /// /// 表示 [GET] /smartguide/guides 接口的请求。 @@ -32,7 +32,8 @@ /// [Newtonsoft.Json.JsonIgnore] [System.Text.Json.Serialization.JsonIgnore] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string? UserMobile { get; set; } /// diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/SmartGuide/QuerySmartGuidesResponse.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/SmartGuide/QuerySmartGuidesResponse.cs index e18e7fac..8c72bb38 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/SmartGuide/QuerySmartGuidesResponse.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/SmartGuide/QuerySmartGuidesResponse.cs @@ -1,4 +1,4 @@ -namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models +namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models { /// /// 表示 [GET] /smartguide/guides 接口的响应。 @@ -36,7 +36,8 @@ /// [Newtonsoft.Json.JsonProperty("name")] [System.Text.Json.Serialization.JsonPropertyName("name")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string UserName { get; set; } = default!; /// @@ -44,7 +45,8 @@ /// [Newtonsoft.Json.JsonProperty("mobile")] [System.Text.Json.Serialization.JsonPropertyName("mobile")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string UserMobile { get; set; } = default!; /// diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/SmartGuide/UpdateSmartGuideRequest.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/SmartGuide/UpdateSmartGuideRequest.cs index 09b0f8a5..f9977ae7 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/SmartGuide/UpdateSmartGuideRequest.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/SmartGuide/UpdateSmartGuideRequest.cs @@ -1,4 +1,4 @@ -namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models +namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models { /// /// 表示 [PATCH] /smartguide/guides/{guide_id} 接口的请求。 @@ -25,7 +25,8 @@ /// [Newtonsoft.Json.JsonProperty("name")] [System.Text.Json.Serialization.JsonPropertyName("name")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string? UserName { get; set; } /// @@ -33,7 +34,8 @@ /// [Newtonsoft.Json.JsonProperty("mobile")] [System.Text.Json.Serialization.JsonPropertyName("mobile")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string? UserMobile { get; set; } /// diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/Transfer/Batches/CreateTransferBatchRequest.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/Transfer/Batches/CreateTransferBatchRequest.cs index 0319bef6..b5c8777c 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/Transfer/Batches/CreateTransferBatchRequest.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/Transfer/Batches/CreateTransferBatchRequest.cs @@ -1,4 +1,4 @@ -using System.Collections.Generic; +using System.Collections.Generic; namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models { @@ -45,7 +45,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("user_name")] [System.Text.Json.Serialization.JsonPropertyName("user_name")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public string? UserName { get; set; } } } diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/Transfer/Batches/GetTransferBatchDetailByOutDetailNumberResponse.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/Transfer/Batches/GetTransferBatchDetailByOutDetailNumberResponse.cs index 8785c02a..013c0bce 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/Transfer/Batches/GetTransferBatchDetailByOutDetailNumberResponse.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Models/Transfer/Batches/GetTransferBatchDetailByOutDetailNumberResponse.cs @@ -1,4 +1,4 @@ -using System; +using System; namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models { @@ -83,7 +83,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Models /// [Newtonsoft.Json.JsonProperty("user_name")] [System.Text.Json.Serialization.JsonPropertyName("user_name")] - [WechatTenpaySensitiveProperty(algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256, algorithm: Constants.EncryptionAlgorithms.RSA_2048_ECB_PKCS8_OAEP_WITH_SHA1_AND_MGF1)] + [WechatTenpaySensitiveProperty(scheme: Constants.SignSchemes.WECHATPAY2_SM2_WITH_SM3, algorithm: Constants.EncryptionAlgorithms.SM2_C1C3C2_ASN1)] public virtual string UserName { get; set; } = default!; /// diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/README.md b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/README.md index 84a6b7d3..10934237 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/README.md +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/README.md @@ -10,8 +10,8 @@ - 基于微信支付 v3 版 API 封装。 - 支持直连商户、服务商两种模式。 -- 请求时自动生成签名,无需开发者手动干预。 -- 提供了微信支付所需的 RSA、AES、SHA-256 等算法工具类。 +- 请求时自动生成签名(同时支持国际 RSA 算法或国密 SM 算法),无需开发者手动干预。 +- 提供了微信支付所需的 RSA、AES、SM2/SM3/SM4、SHA-256 等算法工具类。 - 提供了调起支付签名、解析响应敏感数据、解析回调通知事件敏感数据等扩展方法。 --- diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Settings/CertificateEntry.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Settings/CertificateEntry.cs index d7e2315c..8d6e096f 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Settings/CertificateEntry.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Settings/CertificateEntry.cs @@ -7,17 +7,25 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Settings /// public struct CertificateEntry : IEquatable { + public const string ALGORITHM_TYPE_RSA = "RSA"; + public const string ALGORITHM_TYPE_SM2 = "SM2"; + /// - /// 获取证书序列号。 - /// 序列号相同的实体将被视为同一个证书。 + /// 获取证书算法类型。 + /// 取值范围:RSA、SM2。 /// - public string SerialNumber { get; } + public string AlgorithmType { get; } /// /// 获取证书内容(CRT/CER 格式,即 -----BEGIN CERTIFICATE----- ... -----END CERTIFICATE) /// public string Certificate { get; } + /// + /// 获取证书序列号。 + /// + public string SerialNumber { get; } + /// /// 获取生效时间。 /// @@ -30,39 +38,102 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Settings [Newtonsoft.Json.JsonConstructor] [System.Text.Json.Serialization.JsonConstructor] - public CertificateEntry(string serialNumber, string certificate, DateTimeOffset effectiveTime, DateTimeOffset expireTime) + public CertificateEntry(string algorithmType, string serialNumber, string certificate, DateTimeOffset effectiveTime, DateTimeOffset expireTime) { - if (string.IsNullOrEmpty(serialNumber)) - throw new ArgumentException("The value of `serialNumber` can not be empty.", nameof(serialNumber)); + if (string.IsNullOrEmpty(algorithmType)) + throw new ArgumentException("The value of `algorithmType` can not be empty.", nameof(algorithmType)); if (string.IsNullOrEmpty(certificate)) throw new ArgumentException("The value of `certificate` can not be empty.", nameof(certificate)); + if (string.IsNullOrEmpty(serialNumber)) + throw new ArgumentException("The value of `serialNumber` can not be empty.", nameof(serialNumber)); + if (!ALGORITHM_TYPE_RSA.Equals(algorithmType) && !ALGORITHM_TYPE_SM2.Equals(algorithmType)) + throw new ArgumentException("The value of `algorithmType` an invalid value.", nameof(algorithmType)); if (!certificate.Trim().StartsWith("-----BEGIN CERTIFICATE-----") || !certificate.Trim().EndsWith("-----END CERTIFICATE-----")) throw new ArgumentException("The value of `certificate` is an invalid certificate file content.", nameof(certificate)); - SerialNumber = serialNumber; + AlgorithmType = algorithmType; + SerialNumber = serialNumber.ToUpper(); Certificate = certificate; EffectiveTime = effectiveTime; ExpireTime = expireTime; } - public CertificateEntry(string certificate) + public CertificateEntry(string algorithmType, string certificate) { + if (string.IsNullOrEmpty(algorithmType)) + throw new ArgumentException("The value of `algorithmType` can not be empty.", nameof(algorithmType)); if (string.IsNullOrEmpty(certificate)) throw new ArgumentException("The value of `certificate` can not be empty.", nameof(certificate)); if (!certificate.Trim().StartsWith("-----BEGIN CERTIFICATE-----") || !certificate.Trim().EndsWith("-----END CERTIFICATE-----")) throw new ArgumentException("The value of `certificate` is an invalid certificate file content.", nameof(certificate)); - SerialNumber = Utilities.RSAUtility.ExportSerialNumberFromCertificate(certificate); + AlgorithmType = algorithmType; Certificate = certificate; - EffectiveTime = Utilities.RSAUtility.ExportEffectiveTimeFromCertificate(certificate); - ExpireTime = Utilities.RSAUtility.ExportExpireTimeFromCertificate(certificate); + + switch (algorithmType) + { + case ALGORITHM_TYPE_RSA: + { + SerialNumber = Utilities.RSAUtility.ExportSerialNumberFromCertificate(certificate).ToUpper(); + EffectiveTime = Utilities.RSAUtility.ExportEffectiveTimeFromCertificate(certificate); + ExpireTime = Utilities.RSAUtility.ExportExpireTimeFromCertificate(certificate); + } + break; + + case ALGORITHM_TYPE_SM2: + { + SerialNumber = Utilities.SM2Utility.ExportSerialNumberFromCertificate(certificate).ToUpper(); + EffectiveTime = Utilities.SM2Utility.ExportEffectiveTimeFromCertificate(certificate); + ExpireTime = Utilities.SM2Utility.ExportExpireTimeFromCertificate(certificate); + } + break; + + default: + { + throw new ArgumentException("The value of `algorithmType` an invalid value.", nameof(algorithmType)); + } + } } - public CertificateEntry(Models.QueryCertificatesResponse.Types.Certificate cert) - : this(cert.SerialNumber, cert.EncryptCertificate.CipherText, cert.EffectiveTime, cert.ExpireTime) + public CertificateEntry(string algorithmType, Models.QueryCertificatesResponse.Types.Certificate certificate) + : this(algorithmType, certificate.SerialNumber, certificate.EncryptCertificate.CipherText, certificate.EffectiveTime, certificate.ExpireTime) { } + public CertificateEntry(Models.QueryCertificatesResponse.Types.Certificate certificate) + { + AlgorithmType = default!; + Certificate = certificate.EncryptCertificate.CipherText; + SerialNumber = certificate.SerialNumber.ToUpper(); + EffectiveTime = certificate.EffectiveTime; + ExpireTime = certificate.ExpireTime; + + if (AlgorithmType == null) + { + try + { + Utilities.RSAUtility.ExportPublicKeyFromCertificate(Certificate); + AlgorithmType = ALGORITHM_TYPE_RSA; + } + catch { } + } + + if (AlgorithmType == null) + { + try + { + Utilities.SM2Utility.ExportPublicKeyFromCertificate(Certificate); + AlgorithmType = ALGORITHM_TYPE_SM2; + } + catch { } + } + + if (AlgorithmType == null) + { + throw new ArgumentException("Unrecognized certificate algorithm type, please make sure you have decrypted the certificate content first."); + } + } + public bool IsAvailable() { DateTimeOffset now = DateTimeOffset.Now; @@ -71,20 +142,35 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Settings public bool Equals(CertificateEntry other) { - return string.Equals(SerialNumber, other.SerialNumber); + if (ReferenceEquals(null, other)) + return false; + if (ReferenceEquals(this, other)) + return true; + + return string.Equals(AlgorithmType, other.AlgorithmType) && + string.Equals(Certificate, other.Certificate) && + string.Equals(SerialNumber, other.SerialNumber); } public override bool Equals(object? obj) { if (ReferenceEquals(null, obj)) return false; + if (ReferenceEquals(this, obj)) + return true; + if (GetType() != obj.GetType()) + return false; - return (obj is CertificateEntry other) && Equals(other); + return Equals((CertificateEntry)obj); } public override int GetHashCode() { - return SerialNumber?.GetHashCode() ?? base.GetHashCode(); +#if NETFRAMEWORK || NETSTANDARD2_0 + return (AlgorithmType?.GetHashCode(), Certificate?.GetHashCode(), SerialNumber?.GetHashCode()).GetHashCode(); +#else + return HashCode.Combine(AlgorithmType?.GetHashCode(), Certificate?.GetHashCode(), SerialNumber?.GetHashCode()); +#endif } public static bool operator ==(CertificateEntry left, CertificateEntry right) diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Settings/Credentials.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Settings/Credentials.cs index 03f96f73..eb9ddc37 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Settings/Credentials.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Settings/Credentials.cs @@ -1,4 +1,4 @@ -using System; +using System; namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Settings { @@ -24,6 +24,11 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Settings /// public string MerchantCertificatePrivateKey { get; } + /// + /// 初始化客户端时 的副本。 + /// + internal string SignScheme { get; } + internal Credentials(WechatTenpayClientOptions options) { if (options == null) throw new ArgumentNullException(nameof(options)); @@ -32,6 +37,7 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Settings MerchantV3Secret = options.MerchantV3Secret; MerchantCertificateSerialNumber = options.MerchantCertificateSerialNumber; MerchantCertificatePrivateKey = options.MerchantCertificatePrivateKey; + SignScheme = options.SignScheme; } } } diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Utilities/SM2Utility.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Utilities/SM2Utility.cs index a59f71b7..0baa6811 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Utilities/SM2Utility.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/Utilities/SM2Utility.cs @@ -26,25 +26,12 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Utilities /// public static class SM2Utility { - private static readonly X9ECParameters _ecX9Parameters = GMNamedCurves.GetByName("SM2P256v1"); - private static readonly ECDomainParameters _ecDomainParameters = new ECDomainParameters(_ecX9Parameters.Curve, _ecX9Parameters.G, _ecX9Parameters.N); + private static readonly X9ECParameters SM2_ECX9_PARAMS = GMNamedCurves.GetByName("SM2P256v1"); + private static readonly ECDomainParameters SM2_DOMAIN_PARAMS = new ECDomainParameters(SM2_ECX9_PARAMS.Curve, SM2_ECX9_PARAMS.G, SM2_ECX9_PARAMS.N); private static readonly byte[] SM2_DEFAULT_UID = new byte[] { 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, 0x38, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, 0x38 }; - private static readonly int SM2_C1_LENGTH; - private static readonly int SM2_C3_LENGTH; - private static readonly int SM2_RS_LENGTH; - - static SM2Utility() - { - SM2_C1_LENGTH = (_ecX9Parameters.Curve.FieldSize + 7) / 8 * 2 + 1; - SM2_C3_LENGTH = new SM3Digest().GetDigestSize(); - SM2_RS_LENGTH = 32; - - if (SM2_C1_LENGTH != 65) - throw new PlatformNotSupportedException($"Expected c1 length: {65}, actual: {SM2_C1_LENGTH}."); - - if (SM2_C3_LENGTH != 32) - throw new PlatformNotSupportedException($"Expected c3 length: {32}, actual: {SM2_C3_LENGTH}."); - } + private const int SM2_C1_LENGTH = 65; + private const int SM2_C3_LENGTH = 32; + private const int SM2_RS_LENGTH = 32; private static byte[] ConvertPrivateKeyPkcs8PemToByteArray(string privateKey) { @@ -87,7 +74,7 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Utilities private static ECPrivateKeyParameters ParseECPrivateKeyToPrivateKeyParameters(string ecPrivateKeyHex) { BigInteger ecPrivateKeyParamsD = new BigInteger(ecPrivateKeyHex, 16); - return new ECPrivateKeyParameters(ecPrivateKeyParamsD, _ecDomainParameters); + return new ECPrivateKeyParameters(ecPrivateKeyParamsD, SM2_DOMAIN_PARAMS); } private static ECPublicKeyParameters ParsePublicKeyPemToPublicKeyParameters(byte[] publicKeyBytes) @@ -114,7 +101,7 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Utilities BigInteger ecPublicKeyParamsX = new BigInteger(Hex.ToHexString(ecPublicKeyXBytes), 16); BigInteger ecPublicKeyParamsY = new BigInteger(Hex.ToHexString(ecPublicKeyYBytes), 16); - return new ECPublicKeyParameters(_ecX9Parameters.Curve.CreatePoint(ecPublicKeyParamsX, ecPublicKeyParamsY), _ecDomainParameters); + return new ECPublicKeyParameters(SM2_ECX9_PARAMS.Curve.CreatePoint(ecPublicKeyParamsX, ecPublicKeyParamsY), SM2_DOMAIN_PARAMS); } private static byte[] ConvertC1C3C2ToC1C2C3(byte[] c1c3c2) @@ -170,7 +157,7 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Utilities byte[] c3 = Asn1OctetString.GetInstance(sequence[2]).GetOctets(); byte[] c2 = Asn1OctetString.GetInstance(sequence[3]).GetOctets(); - ECPoint c1Point = _ecX9Parameters.Curve.CreatePoint(x, y); + ECPoint c1Point = SM2_ECX9_PARAMS.Curve.CreatePoint(x, y); byte[] c1 = c1Point.GetEncoded(false); return Arrays.ConcatenateAll(c1, c3, c2); @@ -790,8 +777,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Utilities { if (certificate == null) throw new ArgumentNullException(nameof(certificate)); - X509Certificate cert = ConvertCertificatePemToX509(certificate); - return cert.SerialNumber.ToString(16); + X509Certificate x509cert = ConvertCertificatePemToX509(certificate); + return x509cert.SerialNumber.ToString(16); } /// @@ -803,8 +790,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Utilities { if (certificate == null) throw new ArgumentNullException(nameof(certificate)); - X509Certificate cert = ConvertCertificatePemToX509(certificate); - return new DateTimeOffset(cert.NotBefore); + X509Certificate x509cert = ConvertCertificatePemToX509(certificate); + return new DateTimeOffset(x509cert.NotBefore); } /// @@ -816,8 +803,8 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.Utilities { if (certificate == null) throw new ArgumentNullException(nameof(certificate)); - X509Certificate cert = ConvertCertificatePemToX509(certificate); - return new DateTimeOffset(cert.NotAfter); + X509Certificate x509cert = ConvertCertificatePemToX509(certificate); + return new DateTimeOffset(x509cert.NotAfter); } /// diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/WechatTenpayClient.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/WechatTenpayClient.cs index c3f2b6a9..50805660 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/WechatTenpayClient.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/WechatTenpayClient.cs @@ -26,12 +26,12 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3 /// /// 获取是否自动加密请求中的敏感信息字段。 /// - protected bool AutoEncryptRequestSensitiveProperty { get; } + protected internal bool AutoEncryptRequestSensitiveProperty { get; } /// /// 获取是否自动解密请求中的敏感信息字段。 /// - protected bool AutoDecryptResponseSensitiveProperty { get; } + protected internal bool AutoDecryptResponseSensitiveProperty { get; } /// /// 用指定的配置项初始化 类的新实例。 @@ -165,11 +165,12 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3 where TResponse : WechatTenpayResponse, new() { TResponse result = await base.WrapResponseWithJsonAsync(flurlResponse, cancellationToken); - result.WechatpayRequestId = flurlResponse.Headers.GetAll("Request-ID").FirstOrDefault() ?? string.Empty; - result.WechatpayNonce = flurlResponse.Headers.GetAll("Wechatpay-Nonce").FirstOrDefault() ?? string.Empty; - result.WechatpayTimestamp = flurlResponse.Headers.GetAll("Wechatpay-Timestamp").FirstOrDefault() ?? string.Empty; - result.WechatpaySignature = flurlResponse.Headers.GetAll("Wechatpay-Signature").FirstOrDefault() ?? string.Empty; - result.WechatpayCertificateSerialNumber = flurlResponse.Headers.GetAll("Wechatpay-Serial").FirstOrDefault() ?? string.Empty; + result.WechatpayRequestId = flurlResponse.Headers.FirstOrDefault("Request-ID") ?? string.Empty; + result.WechatpayNonce = flurlResponse.Headers.FirstOrDefault("Wechatpay-Nonce") ?? string.Empty; + result.WechatpayTimestamp = flurlResponse.Headers.FirstOrDefault("Wechatpay-Timestamp") ?? string.Empty; + result.WechatpaySignatureType = flurlResponse.Headers.FirstOrDefault("Wechatpay-Signature-Type") ?? string.Empty; + result.WechatpaySignature = flurlResponse.Headers.FirstOrDefault("Wechatpay-Signature") ?? string.Empty; + result.WechatpayCertificateSerialNumber = flurlResponse.Headers.FirstOrDefault("Wechatpay-Serial") ?? string.Empty; if (AutoDecryptResponseSensitiveProperty && result.IsSuccessful()) { diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/WechatTenpayClientOptions.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/WechatTenpayClientOptions.cs index 3dd6378b..ef04db83 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/WechatTenpayClientOptions.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/WechatTenpayClientOptions.cs @@ -34,9 +34,9 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3 /// /// 获取或设置微信支付 API 签名认证方式。 - /// 默认值: + /// 默认值: /// - public string SignScheme { get; set; } = Constants.SignSchemes.WECHATPAY2_SHA256_RSA2048; + public string SignScheme { get; set; } = Constants.SignSchemes.WECHATPAY2_RSA_2048_WITH_SHA256; /// /// 获取或设置微信支付商户号。 diff --git a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/WechatTenpayResponse.cs b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/WechatTenpayResponse.cs index 28528014..9e589ad2 100644 --- a/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/WechatTenpayResponse.cs +++ b/src/SKIT.FlurlHttpClient.Wechat.TenpayV3/WechatTenpayResponse.cs @@ -77,6 +77,13 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3 [System.Text.Json.Serialization.JsonIgnore] public string WechatpayNonce { get; internal set; } = default!; + /// + /// 获取微信应答签名类型。 + /// + [Newtonsoft.Json.JsonIgnore] + [System.Text.Json.Serialization.JsonIgnore] + public string WechatpaySignatureType { get; internal set; } = default!; + /// /// 获取微信应答签名。 /// diff --git a/test/SKIT.FlurlHttpClient.Wechat.TenpayV3.UnitTests/TestCase_CertificateManagerTests.cs b/test/SKIT.FlurlHttpClient.Wechat.TenpayV3.UnitTests/TestCase_CertificateManagerTests.cs index f32fc03c..9ec3ecc6 100644 --- a/test/SKIT.FlurlHttpClient.Wechat.TenpayV3.UnitTests/TestCase_CertificateManagerTests.cs +++ b/test/SKIT.FlurlHttpClient.Wechat.TenpayV3.UnitTests/TestCase_CertificateManagerTests.cs @@ -1,4 +1,4 @@ -using System; +using System; using Xunit; namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.UnitTests @@ -8,11 +8,12 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.UnitTests [Fact(DisplayName = "测试用例:`CertificateEntry` 序列化")] public void TestCertificateEntrySerialization() { - var entry = new Settings.CertificateEntry("SN", "-----BEGIN CERTIFICATE-----END CERTIFICATE-----", DateTimeOffset.Now, DateTimeOffset.Now); + var entry = new Settings.CertificateEntry("RSA", "FAKE SERIAL NUMBER", "-----BEGIN CERTIFICATE-----FAKE CERTIFICATE-----END CERTIFICATE-----", DateTimeOffset.Now, DateTimeOffset.Now); var serialized1 = Newtonsoft.Json.JsonConvert.SerializeObject(entry); var deserialized1 = Newtonsoft.Json.JsonConvert.DeserializeObject(serialized1); + Assert.Equal(entry.AlgorithmType, deserialized1.AlgorithmType); Assert.Equal(entry.SerialNumber, deserialized1.SerialNumber); Assert.Equal(entry.Certificate, deserialized1.Certificate); Assert.Equal(entry.EffectiveTime, deserialized1.EffectiveTime); @@ -21,6 +22,7 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.UnitTests var serialized2 = System.Text.Json.JsonSerializer.Serialize(entry); var deserialized2 = System.Text.Json.JsonSerializer.Deserialize(serialized2); + Assert.Equal(entry.AlgorithmType, deserialized2.AlgorithmType); Assert.Equal(entry.SerialNumber, deserialized2.SerialNumber); Assert.Equal(entry.Certificate, deserialized2.Certificate); Assert.Equal(entry.EffectiveTime, deserialized2.EffectiveTime); diff --git a/test/SKIT.FlurlHttpClient.Wechat.TenpayV3.UnitTests/TestCase_RequestEncryptionTests.cs b/test/SKIT.FlurlHttpClient.Wechat.TenpayV3.UnitTests/TestCase_RequestEncryptionTests.cs index 9cbeb482..ccdcf948 100644 --- a/test/SKIT.FlurlHttpClient.Wechat.TenpayV3.UnitTests/TestCase_RequestEncryptionTests.cs +++ b/test/SKIT.FlurlHttpClient.Wechat.TenpayV3.UnitTests/TestCase_RequestEncryptionTests.cs @@ -1,4 +1,4 @@ -using System; +using System; using System.Collections.Generic; using Xunit; @@ -12,8 +12,9 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.UnitTests private const string MockText = "mock_text"; private readonly Lazy MockClientInstance = new Lazy(() => { - var certManager = new Settings.InMemoryCertificateManager(); - certManager.AddEntry(new Settings.CertificateEntry( + var manager = new Settings.InMemoryCertificateManager(); + manager.AddEntry(new Settings.CertificateEntry( + algorithmType: "RSA", serialNumber: RSA_CERTSN, certificate: RSA_CERTIFICATE, effectiveTime: DateTimeOffset.MinValue, @@ -21,7 +22,7 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.UnitTests )); return new WechatTenpayClient(new WechatTenpayClientOptions() { - PlatformCertificateManager = certManager + PlatformCertificateManager = manager }); }, isThreadSafe: false); @@ -35,7 +36,7 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.UnitTests }; var data = MockClientInstance.Value.EncryptRequestSensitiveProperty(mock); - Assert.Equal(RSA_CERTSN, data.WechatpayCertificateSerialNumber); + Assert.Equal(RSA_CERTSN, data.WechatpayCertificateSerialNumber, ignoreCase: true); Assert.Equal(MockText, data.Account); Assert.Equal(MockText, Utilities.RSAUtility.DecryptWithECB(RSA_PRIVATE_KEY, data.Name!)); } @@ -56,7 +57,7 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.UnitTests }; var data = MockClientInstance.Value.EncryptRequestSensitiveProperty(mock); - Assert.Equal(RSA_CERTSN, data.WechatpayCertificateSerialNumber); + Assert.Equal(RSA_CERTSN, data.WechatpayCertificateSerialNumber, ignoreCase: true); Assert.Equal(MockText, data.ReceiverList[0].Account); Assert.Equal(MockText, Utilities.RSAUtility.DecryptWithECB(RSA_PRIVATE_KEY, data.ReceiverList[0].Name!)); } diff --git a/test/SKIT.FlurlHttpClient.Wechat.TenpayV3.UnitTests/TestCase_ResponseVerificationTests.cs b/test/SKIT.FlurlHttpClient.Wechat.TenpayV3.UnitTests/TestCase_ResponseVerificationTests.cs index 7f9b8dcd..94177c96 100644 --- a/test/SKIT.FlurlHttpClient.Wechat.TenpayV3.UnitTests/TestCase_ResponseVerificationTests.cs +++ b/test/SKIT.FlurlHttpClient.Wechat.TenpayV3.UnitTests/TestCase_ResponseVerificationTests.cs @@ -1,4 +1,4 @@ -using System.Threading.Tasks; +using System.Threading.Tasks; using Xunit; namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.UnitTests @@ -17,6 +17,12 @@ namespace SKIT.FlurlHttpClient.Wechat.TenpayV3.UnitTests Assert.True(response.RawHeaders.Count > 0); Assert.True(response.RawBytes.Length > 0); Assert.True(TestClients.Instance.VerifyResponseSignature(response)); + Assert.NotNull(response.WechatpayRequestId); + Assert.NotNull(response.WechatpayNonce); + Assert.NotNull(response.WechatpayTimestamp); + Assert.NotNull(response.WechatpaySignature); + Assert.NotNull(response.WechatpaySignatureType); + Assert.NotNull(response.WechatpayCertificateSerialNumber); } } }