.net core 华为云发送短信

Service

        /// <summary>
        /// 发送验证码
        /// </summary>
        /// <param name="phone">手机号码</param>
        /// <returns></returns>
        public async Task<Result> SendPhoneVerifCode(string phone)
        {
            try
            {
                var options = new ShortMessageOptions();
                _configuration.GetSection(ShortMessageOptions.ShortMessage).Bind(options);

                var verifCode = PhoneVerifCodeHelper.SendPhoneVerifCode(phone, options);

                var model = new PhoneVerifCode
                {
                    CreatedBy = 0,
                    CreatedTime = DateTime.UtcNow,
                    Phone = phone,
                    VerifCode = verifCode,
                    EffectiveTime = DateTime.UtcNow.AddMinutes(+5),
                };
                await _phoneVerifCodeRepository.InsertAsync(model);
                return Result.Success();
            }
            catch (Exception)
            {
                return Result.Fail(ResultCodeConsts.Exception, "发送验证码错误!");
            }
        }

实体

    public class ShortMessageOptions
    {
        public const string ShortMessage = "ShortMessage";

        /// <summary>
        /// 接口地址
        /// </summary>
        public string ApiAddress { get; set; }

        /// <summary>
        /// AppKey
        /// </summary>
        public string AppKey { get; set; }

        /// <summary>
        /// AppSecret
        /// </summary>
        public string AppSecret { get; set; }

        /// <summary>
        /// 通道号
        /// </summary>
        public string Sender { get; set; }

        /// <summary>
        /// 模板Id
        /// </summary>
        public string TemplateId { get; set; }

        /// <summary>
        /// 签名名称
        /// </summary>
        public string Signature { get; set; }
    }

配置:ShortMessage

 

 SendPhoneVerifCode方法

    public class PhoneVerifCodeHelper
    {
        public static string SendPhoneVerifCode(string phone, ShortMessageOptions options)
        {
            string apiAddress = options.ApiAddress; // APP接入地址
            string appKey = options.AppKey; // APPKey
            string appSecret = options.AppSecret; // APPSecret
            string sender = options.Sender; // 通道号
            string templateId = options.TemplateId; // 模板ID
            string signature = options.Signature; // 签名

            string[] receiver = { phone }; // 接收号码

            // 选填,短信状态报告接收地址,推荐使用域名,为空或者不填表示不接收状态报告
            string statusCallBack = "";

            /*
             * 选填,使用无变量模板时请赋空值 string[] templateParas = {};
             */
            var ran = new Random().Next(100000, 999999);
            string[] templateParas = { ran.ToString() }; // 模板变量

            ArrayList smsContent = new ArrayList
            {
                // smsContent,不携带签名名称时,signature请填null
                InitDiffSms(receiver, templateId, templateParas, signature),
            };

            try
            {
                // 为防止因HTTPS证书认证失败造成API调用失败,需要先忽略证书信任问题
                HttpClient client = new HttpClient();
                ServicePointManager.ServerCertificateValidationCallback = delegate { return true; };

                // 请求Headers
                client.DefaultRequestHeaders.Add("Authorization", "WSSE realm=\"SDP\",profile=\"UsernameToken\",type=\"Appkey\"");
                client.DefaultRequestHeaders.Add("X-WSSE", BuildWSSEHeader(appKey, appSecret));
                // 请求Body
                var body = new Dictionary<string, object>{
                    {"from", sender},
                    {"statusCallback", statusCallBack},
                    {"smsContent", smsContent}
                };

                HttpContent content = new StringContent(JsonConvert.SerializeObject(body));

                // 请求Headers中的Content-Type参数
                content.Headers.ContentType = new MediaTypeHeaderValue("application/json");

                var response = client.PostAsync(apiAddress, content).Result;
                var res = response.Content.ReadAsStringAsync().Result;
                return ran.ToString();
            }
            catch (Exception e)
            {
                return e.Message.ToString();
            }
        }

        /// <summary>
        /// 构造smsContent参数值
        /// </summary>
        /// <param name="receiver"></param>
        /// <param name="templateId"></param>
        /// <param name="templateParas"></param>
        /// <param name="signature">签名名称,使用国内短信通用模板时填写</param>
        /// <returns></returns>
        static Dictionary<string, object> InitDiffSms(string[] receiver, string templateId, string[] templateParas, string signature)
        {
            Dictionary<string, object> dic = new Dictionary<string, object>
            {
                {"to", receiver},
                {"templateId", templateId},
                {"templateParas", templateParas}
            };
            if (!signature.Equals(null) && signature.Length > 0)
            {
                dic.Add("signature", signature);
            }

            return dic;
        }

        /// <summary>
        /// 构造X-WSSE参数值
        /// </summary>
        /// <param name="appKey"></param>
        /// <param name="appSecret"></param>
        /// <returns></returns>
        static string BuildWSSEHeader(string appKey, string appSecret)
        {
            string now = DateTime.UtcNow.ToString("yyyy-MM-ddTHH:mm:ssZ"); // Created
            string nonce = Guid.NewGuid().ToString().Replace("-", ""); // Nonce

            byte[] material = Encoding.UTF8.GetBytes(nonce + now + appSecret);
            byte[] hashed = SHA256Managed.Create().ComputeHash(material);
            string hexdigest = BitConverter.ToString(hashed).Replace("-", "");
            string base64 = Convert.ToBase64String(Encoding.UTF8.GetBytes(hexdigest)); // PasswordDigest

            return String.Format("UsernameToken Username=\"{0}\",PasswordDigest=\"{1}\",Nonce=\"{2}\",Created=\"{3}\"", appKey, base64, nonce, now);
        }
    }

 

posted on 2022-04-27 17:05  小乐丶  阅读(190)  评论(0编辑  收藏  举报