1. 使用composer安装所需要的短信SDK。

阿里云短信SDK

$ composer require alibabacloud/sdk

腾讯云短信SDK

$ composer require tencentcloud/tencentcloud-sdk-php
  1. 目录结构
project
|-- app
     |--common
         |--lib
         |   |--sms
         |   |   |--AilSms.php
         |   |   |--TenSms.php
         |   |   |--SmsBase.php
         |   `--ClassArr.php
         `--business
             |--api
                 |--SmsBusinee.php
  1. SmsBase为短信统一接口,所有短信使用都使用该接口,达到统一约束。
<?php
/**
 * PHP version 7.1
 *
 * @date    2021-12-17 16:01:54
 * @author  xiangyang <827544120@qq.com>
 */


/**
 * End file SmsBase.php
 */
declare(strict_types=1);

namespace app\common\lib\sms;

interface  SmsBase
{
    /**
     *
     * 短信统一接口
     * @method  SmsSend
     * @param string $phone 接收手机号
     * @param array  $code 短信内容
     * @param string $templateCode 短息模板ID
     * @param string $signName 短信签名
     *
     * @return  mixed
     *
     * @author  xiangyang <827544120@qq.com>
     */
    public static function SmsSend(string $phone, array $code, string $templateCode, string $signName);
}
  1. AliSms阿里云短信SDK调用方式。
<?php
/**
 * PHP version 7.1
 *
 * @date    2021-12-16 15:10:03
 * @author  xiangyang <827544120@qq.com>
 */


/**
 * End file Alisms.php
 */
declare(strict_types=1);

namespace app\common\lib\sms;


use AlibabaCloud\Client\AlibabaCloud;
use AlibabaCloud\Client\Exception\ClientException;
use AlibabaCloud\Client\Exception\ServerException;
use think\facade\Log;

class AliSms implements SmsBase
{
    /**
     *
     * 阿里云短信发送板块
     * @method  LoginSmsSend
     * @param string $phone 发送手机号
     * @param array  $code  短信内容
     * @param string $templateCode 短信模板ID
     * @param string $signName 短信签名
     *
     * @return  bool
     * @throws ClientException
     *
     * @author  xiangyang <827544120@qq.com>
     */
    public static function SmsSend(string $phone, array $code,string $templateCode,
    string $signName): bool
    {
        AlibabaCloud::accessKeyClient("填入ACCESSKEYID","填入ACCESSKEYSECRET")->regionId('cn-shanghai')->asDefaultClient();
        try {
            $result = AlibabaCloud::rpc()
                ->product('Dysmsapi')
                ->version('2017-05-25')
                ->action('SendSms')
                ->method('POST')
                ->host('dysmsapi.aliyuncs.com')
                ->options([
                    'query' => [
                        'PhoneNumbers' => $phone,
                        'SignName' => $signName,
                        'TemplateCode' => $templateCode,
                        'TemplateParam' => json_encode($code),
                    ],
                ])
                ->request();
            $result = $result->toArray();

          //发送成功后并将阿里云返回写入日志
            if (isset($result["Code"]) && $result["Code"] == "OK") {
                Log::info("AliSms_LoginSmsSend_phone-{$phone}_Send_Success-" . json_encode($result));
                return true;
            }
            //发送失败将阿里云返回写入日志
            Log::info("AliSms_LoginSmsSend_phone-{$phone}_Send_Exception-".json_encode($result));
           //将各种异常写入日志
        } catch (ClientException $e) {
            Log::error("AliSms_LoginSmsSend_phone-{$phone}_Send_Exception-" . $e->getMessage());
        } catch (ServerException $e) {
            Log::error("AliSms_LoginSmsSend_phone-{$phone}_Send_Exception-" . $e->getMessage());
        }
        return false;
    }
}
  1. TenSms腾讯云短信SDK调用方法。
<?php
/**
 * PHP version 7.1
 *
 * @date    2022-01-18 11:48:06
 * @author  xiangyang <827544120@qq.com>
 */


/**
 * End file TenSms.php
 */

namespace app\common\lib\sms;

use TencentCloud\Common\Credential;
use TencentCloud\Common\Exception\TencentCloudSDKException;
use TencentCloud\Common\Profile\ClientProfile;
use TencentCloud\Common\Profile\HttpProfile;
use TencentCloud\Sms\V20210111\Models\SendSmsRequest;
use TencentCloud\Sms\V20210111\SmsClient;
use think\facade\Log;

class TenSms implements SmsBase
{
    /**
     *
     * 腾讯云短信发送板块
     * @method  LoginSmsSend
     *
     * @param string $phone        发送手机号
     * @param array  $code         短信内容
     * @param string $templateCode 短信模板ID
     * @param string $signName     短信签名
     *
     * @return  bool
     *
     * @author  xiangyang <827544120@qq.com>
     */
    public static function SmsSend(string $phone, array $codeDataArray, string $templateCode, string $signName)
    {
        try {
            $cred = new Credential("填入SECRETID","填入SECRETKEY";
            $httpProfile = new HttpProfile();
            $httpProfile->setEndpoint("sms.tencentcloudapi.com");
            $clientProfile = new ClientProfile();
            $clientProfile->setHttpProfile($httpProfile);
            $client = new SmsClient($cred, "ap-guangzhou", $clientProfile);
            $req = new SendSmsRequest();
            $phoneDataArray = array($phone);
            $params = array(
                "PhoneNumberSet" => $phoneDataArray,
                "SmsSdkAppId" => "填入SDKAPPID",
                "SignName" => $signName,
                "TemplateId" => $templateCode,
                "TemplateParamSet" => $codeDataArray,
            );
            $req->fromJsonString(json_encode($params));
            $resp = $client->SendSms($req);
            $result = json_decode(json_encode($resp),true);
            //短信发送成功后将返回见过写入日志
            if($result['SendStatusSet']['0']['Code'] === "Ok"){
                Log::info("TenSms_LoginSmsSend_Phone-{$phone}_Send_Success-".json_encode($resp));
                return true;
            }
            //短信发送失败将返回结果写入日志
            Log::error("TenSms_LoginSmsSend_Phone-{$phone}_Send-Exception-".json_encode($resp));
         //将异常写入日志
        }catch (TencentCloudSDKException $e){
            Log::error("TenSms_LoginSmsSend_Phone-{$phone}_Send_Exception-".$e->getMessage());
        }
        return false;
    }
}
  1. ClassArr短信类集合
<?php
/**
 * PHP version 7.1
 *
 * @date    2022-01-15 09:55:36
 * @author  xiangyang <827544120@qq.com>
 */


/**
 * End file ClassArr.php
 */

namespace app\common\lib;

class ClassArr
{
    public static function smsClassStat()
    {
        return [
            'Ali' => 'app\common\lib\sms\AliSms',
            'Ten' => 'app\common\lib\sms\TenSms',
        ];
    }

    public static function initClass($type, $class, $params = [], $sendIns = false)
    {
        if (!array_key_exists($type, $class)) {
            return false;
        }
        $classObject = $class[$type];
        return $sendIns == true ? (new \ReflectionClass($classObject))->newInstanceArgs($params) : $classObject;
    }
}
  1. SmsBusiness短信验证码公共方法
<?php
/**
 * PHP version 7.1
 *
 * @date    2021-12-16 15:56:28
 * @author  xiangyang <827544120@qq.com>
 */


/**
 * End file SmsBusiness.php
 */
declare(strict_types=1);

namespace app\common\business\api;

use app\common\lib\ClassArr;
use app\common\lib\sms\AliSms;

class SmsBusiness
{

    /**
     *
     * bus商城用户登录发送短信验证码,发送成功后写入Redis
     * @method  LoginSmsSend
     * 发送短信
     * @param array  $data         手机号
     * @param int    $code         短信内容
     * @param string $templateCode 短信模板ID
     * @param string $signName     短信签名
     *
     * @return  bool
     * @throws \AlibabaCloud\Client\Exception\ClientException
     *
     * @author  xiangyang <827544120@qq.com>
     */
    public function LoginSmsSend(array $data, array $codeDataArray, string $code,string $templateCode, string $signName,string $type = 'ten'): bool {
        $type = ucfirst($type);
        $ClassArr = new ClassArr();
        $smsObject = $ClassArr::smsClassStat();
        $smsSend = $ClassArr::initClass($type, $smsObject);
        $results = $smsSend::SmsSend($data['phone'], $codeDataArray, $templateCode, $signName);
        if ($results) {
            //发送成功
            return true;
        }
        //发送失败
        return false;
    }

    /**
     * 短信参数格式化(因平台不一样所以短信的数据格式会有差异)
     * @param int $code  随机验证码
     * @param string $type 短信平台 ten=>TenSms;ali=>AliSms
     * @return array
     */
    public function LoginSmsParameter(int $code, string $type = 'ten'): array
    {

        if (strcasecmp($type, 'ali') == 0) {
            $codeDataArray = [
                'code' => $code,
            ];
            $result = [
                'code'=> $code,
                'code_data_array' => $codeDataArray,
                'templateCode' => config("Ali.templateCode.login"),
                'signName' => config("Ali.signName.mall"),
            ];
            return $result;
        }else if(strcasecmp($type,'ten') == 0 ){
            $codeDataArray = array((string)$code);
            $result = [
                'code'=>$code,
                'code_data_array'=>$codeDataArray,
                'templateCode'=>config("Ten.sms.template_id.login"),
                'signName'=>config("Ten.sms.sign_name.1"),
            ];
            return $result;
        }
        return [];
    }
}
  1. 短信验证码调用
<?php
/**
 * PHP version 7.1
 *
 * @date    2021-12-16 15:52:25
 * @author  xiangyang <827544120@qq.com>
 */


/**
 * End file Sms.php
 */

namespace app\api\controller;

use app\BaseController;
use app\common\business\api\SmsBusiness;
use app\Request;
use think\facade\Log;

class Sms extends BaseController
{
    /**
     *
     * 用户登录发送短信验证码
     * @method  LoginSmsSend
     *
     * @param Request $request
     *
     * @return  \think\response\Json
     *
     * @author  xiangyang <827544120@qq.com>
     */
    public function LoginSmsSend(Request $request)
    {
        //获取手机号
        $phone = $request->param("phone_number", null);
        $data = [
            'phone' => $phone,
        ];
        try {
            $SmsBusiness = new SmsBusiness();
            //短信验证码内容
            $code =100666 ;
            //短信验证码 发送方
            $type = 'ali';
            //发送内容整理
            $smsResult = $SmsBusiness->LoginSmsParameter($code,$type);
            //发送短信
            if(!empty($smsResult)){
                $result = $SmsBusiness->LoginSmsSend($data,$smsResult['code_data_array'], $code,$smsResult['templateCode'],$smsResult['signName'],$type);
                if ($result) {
                    return show(1, "短信验证码发送成功!");
                }
            }
        } catch (\Exception $exception) {
            Log::error("Sms_loginSmsSend_{$data['phone']}_exception-" . $exception->getMessage());
        }
        return show(0, "短信验证码发送失败!");
    }
}

结语:短信验证码在发送短信的时候应该验证该手机号是否合法,验证码内容应该使用随机函数。

最后修改:2022 年 05 月 10 日
如果觉得我的文章对你有用,请随意赞赏