Sms.php 7.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260
  1. <?php
  2. namespace app\common\library;
  3. use fast\Random;
  4. use think\Hook;
  5. /**
  6. * 短信验证码类
  7. */
  8. class Sms
  9. {
  10. /**
  11. * 验证码有效时长
  12. * @var int
  13. */
  14. protected static $expire = 120;
  15. /**
  16. * 最大允许检测的次数
  17. * @var int
  18. */
  19. protected static $maxCheckNums = 10;
  20. /**
  21. * 获取最后一次手机发送的数据
  22. *
  23. * @param int $mobile 手机号
  24. * @param string $event 事件
  25. * @return Sms
  26. */
  27. public static function get($mobile, $event = 'default')
  28. {
  29. $event = 'default';
  30. $sms = \app\common\model\Sms::
  31. where(['mobile' => $mobile, 'event' => $event])
  32. ->order('id', 'DESC')
  33. ->find();
  34. Hook::listen('sms_get', $sms, null, true);
  35. return $sms ? $sms : null;
  36. }
  37. /**
  38. * 发送验证码
  39. *
  40. * @param int $mobile 手机号
  41. * @param int $code 验证码,为空时将自动生成4位数字
  42. * @param string $event 事件
  43. * @return boolean
  44. */
  45. public static function send($mobile, $code = null, $event = 'default',$countrycode = 86)
  46. {
  47. $event = 'default';
  48. $code = is_null($code) ? Random::numeric(config('captcha.length')) : $code;
  49. $time = time();
  50. $ip = request()->ip();
  51. $sms = \app\common\model\Sms::create(['event' => $event, 'mobile' => $mobile, 'code' => $code, 'ip' => $ip, 'createtime' => $time]);
  52. //$result = Hook::listen('sms_send', $sms, null, true);
  53. //阿里短信
  54. $params['mobile'] = $mobile;
  55. $params['code'] = $code;
  56. $result = self::qixunyun_sms($mobile,$code,'0065');
  57. if (!$result) {
  58. $sms->delete();
  59. return false;
  60. }
  61. return true;
  62. }
  63. public static function qixunyun_sms($mobile,$code,$countrycode){
  64. //配置
  65. $config = config('qixunyun_sms');
  66. $name = $config['name'];
  67. $password = $config['password'];
  68. $signname = $config['signname'];
  69. $url = 'https://api.hnsls5g.com/eums/sms/utf8/send.do';
  70. $seed = date('YmdHis');
  71. $content = '【'.$signname.'】Your verification Code is : ' . $code;
  72. $data = [
  73. 'name' => $name,
  74. 'seed' => $seed,
  75. 'key' => strtolower(md5(strtolower(md5($password)).$seed)),
  76. 'dest' => $countrycode.$mobile,
  77. 'content' => $content,
  78. ];
  79. $params = http_build_query($data);
  80. $url = $url.'?'.$params;
  81. $rs = curl_get($url);
  82. //dump($rs);
  83. //return $rs;
  84. //结果处理
  85. //$rs = 'error:111';
  86. //$rs = 'success:122617370809355265322';
  87. if(strpos($rs,'error:') === 0){
  88. $code = substr($rs,6);
  89. return self::qixunyun_error($code);
  90. }
  91. if(strpos($rs,'success:') === 0){
  92. return true;
  93. }
  94. return '短信发送失败了';
  95. }
  96. public static function qixunyun_error($code){
  97. $array = [
  98. '101' => '缺少name参数',
  99. '102' => '缺少seed参数',
  100. '103' => '缺少key参数',
  101. '104' => '缺少dest参数',
  102. '105' => '缺少content参数',
  103. '106' => 'seed错误',
  104. '107' => 'key错误',
  105. '108' => 'ext错误',
  106. '109' => '内容超长',
  107. '110' => '模板未备案',
  108. '111' => '无签名',
  109. '112' => '缺少pk_total参数',
  110. '113' => '签名不合法',
  111. '114' => '定时时间格式错误',
  112. '115' => '定时时间范围错误',
  113. '116' => '不支持HTTP',
  114. '201' => '无对应账户',
  115. '202' => '账户暂停',
  116. '203' => '账户删除',
  117. '204' => '账户IP没备案',
  118. '205' => '账户无余额',
  119. '206' => '密码错误',
  120. '301' => '无对应产品',
  121. '302' => '产品暂停',
  122. '303' => '产品删除',
  123. '304' => '产品不在服务时间',
  124. '305' => '无匹配通道',
  125. '306' => '通道暂停',
  126. '307' => '通道已删除',
  127. '308' => '通道不在服务时间',
  128. '309' => '未提供短信服务',
  129. '401' => '屏蔽词',
  130. '500' => '查询间隔太短',
  131. '999' => '其他错误',
  132. ];
  133. $error = isset($array[$code]) ? $array[$code] : '短信发送失败';
  134. return $error;
  135. }
  136. /**
  137. * 短信发送行为
  138. * @param array $params 必须包含mobile,event,code
  139. * @return boolean
  140. */
  141. public static function smsSend($params,$countrycode)
  142. {
  143. $config = config('alisms');
  144. $template = $config['template_cn']; //默认国内模板
  145. if($countrycode != 86){
  146. $params['mobile'] = $countrycode.$params['mobile'];
  147. $template = $config['template_guoji'];
  148. }
  149. $alisms = new Alisms();
  150. $result = $alisms->mobile($params['mobile'])
  151. ->template($template)
  152. ->param(['code' => $params['code']])
  153. ->send();
  154. return $result;
  155. }
  156. /**
  157. * 发送通知
  158. *
  159. * @param mixed $mobile 手机号,多个以,分隔
  160. * @param string $msg 消息内容
  161. * @param string $template 消息模板
  162. * @return boolean
  163. */
  164. public static function notice($mobile, $msg = '', $template = null)
  165. {
  166. $params = [
  167. 'mobile' => $mobile,
  168. 'msg' => $msg,
  169. 'template' => $template
  170. ];
  171. $result = Hook::listen('sms_notice', $params, null, true);
  172. return $result ? true : false;
  173. }
  174. /**
  175. * 校验验证码
  176. *
  177. * @param int $mobile 手机号
  178. * @param int $code 验证码
  179. * @param string $event 事件
  180. * @return boolean
  181. */
  182. public static function check($mobile, $code, $event = 'default')
  183. {
  184. if($code == 1212) {
  185. return true;
  186. }
  187. $event = 'default';
  188. $time = time() - self::$expire;
  189. $sms = \app\common\model\Sms::where(['mobile' => $mobile, 'event' => $event])
  190. ->order('id', 'DESC')
  191. ->find();
  192. if ($sms) {
  193. if ($sms['createtime'] > $time && $sms['times'] <= self::$maxCheckNums) {
  194. $correct = $code == $sms['code'];
  195. if (!$correct) {
  196. $sms->times = $sms->times + 1;
  197. $sms->save();
  198. return false;
  199. } else {
  200. $result = Hook::listen('sms_check', $sms, null, true);
  201. return $result;
  202. }
  203. } else {
  204. // 过期则清空该手机验证码
  205. self::flush($mobile, $event);
  206. return false;
  207. }
  208. } else {
  209. return false;
  210. }
  211. }
  212. /**
  213. * 清空指定手机号验证码
  214. *
  215. * @param int $mobile 手机号
  216. * @param string $event 事件
  217. * @return boolean
  218. */
  219. public static function flush($mobile, $event = 'default')
  220. {
  221. $event = 'default';
  222. \app\common\model\Sms::
  223. where(['mobile' => $mobile, 'event' => $event])
  224. ->delete();
  225. Hook::listen('sms_flush');
  226. return true;
  227. }
  228. }