Sms.php 19 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545
  1. <?php
  2. /**
  3. * NiuShop商城系统 - 团队十年电商经验汇集巨献!
  4. * =========================================================
  5. * Copy right 2019-2029 杭州牛之云科技有限公司, 保留所有权利。
  6. * ----------------------------------------------
  7. * 官方网址: https://www.niushop.com
  8. */
  9. namespace addon\niusms\model;
  10. use addon\niusms\model\Config as ConfigModel;
  11. use app\model\BaseModel;
  12. /**
  13. * 牛云短信
  14. */
  15. class Sms extends BaseModel
  16. {
  17. private $api = "https://www.niushop.com/api";// http://cs.www.niuteam.cn/api
  18. // 审核状态(0 未审核,1 待审核,2 审核通过, 3 审核不通过)
  19. private $audit_status = [
  20. '未审核',
  21. '待审核',
  22. '审核通过',
  23. '审核不通过'
  24. ];
  25. private $error_msg = [
  26. 4000 => '短信余额不足',
  27. 4001 => '用户名错误',
  28. 4002 => '密码不能为空',
  29. 4004 => '手机号码错误',
  30. 4006 => 'IP鉴权错误',
  31. 4007 => '短信账号被禁用',
  32. 4008 => '时间戳格式错误',
  33. 4009 => '密码错误',
  34. 4013 => '定时时间错误',
  35. 4014 => '模板错误',
  36. 4015 => '扩展号错误',
  37. 4019 => '用户类型错误',
  38. 4023 => '签名错误',
  39. 4025 => '模板变量内容为空',
  40. 4026 => '手机号码数最大2000个',
  41. 4027 => '模板变量内容最大200组',
  42. 4029 => '请使用post请求',
  43. 4030 => 'Content-Type请使用application/json',
  44. 9998 => 'JSON解析错误',
  45. 9999 => '非法请求'
  46. ];
  47. public function getAuditStatus()
  48. {
  49. return $this->audit_status;
  50. }
  51. /**
  52. * 查询短信签名报备状态
  53. * @param $site_id
  54. * @param $app_module
  55. * @return array|mixed
  56. */
  57. public function querySignature($site_id, $app_module)
  58. {
  59. $config_model = new ConfigModel();
  60. $sms_config = $config_model->getSmsConfig($site_id, $app_module);
  61. $sms_config = $sms_config[ 'data' ][ 'value' ];
  62. $tKey = time();
  63. $data = [
  64. 'username' => $sms_config[ 'username' ],
  65. 'password' => md5(md5($sms_config[ 'password' ]) . $tKey),
  66. 'tKey' => $tKey,
  67. 'sign' => input('signature', $sms_config[ 'signature' ]),//短信签名
  68. ];
  69. $url = 'https://api.mix2.zthysms.com/sms/v1/sign/query';
  70. $res = $this->sendSms($url, $data);
  71. return $res;
  72. }
  73. /**
  74. * 创建子账号
  75. * @param $data
  76. * @return array|mixed
  77. */
  78. public function createChildAccount($data, $site_id, $app_module)
  79. {
  80. $url = $this->api . '/sms/createChildAccountNew';
  81. $res = $this->httpPost($url, $data);
  82. if ($res[ 'code' ] == 0) {
  83. $config_model = new ConfigModel();
  84. $data[ 'signature' ] = "";
  85. $config_model->setSmsConfig($data, 1, $site_id, $app_module);
  86. }
  87. return $res;
  88. }
  89. /**
  90. * 账号登录
  91. * @param $data
  92. * @param $site_id
  93. * @param $app_module
  94. * @return array|mixed
  95. */
  96. public function loginAccount($data, $site_id, $app_module)
  97. {
  98. $url = $this->api . '/sms/loginAccount';
  99. $res = $this->httpPost($url, $data);
  100. if ($res[ 'code' ] == 0 && !empty($res[ 'data' ])) {
  101. $config_model = new ConfigModel();
  102. $res[ 'data' ][ 'password' ] = $data[ 'password' ];
  103. $config_model->setSmsConfig($res[ 'data' ], 1, $site_id, $app_module);
  104. // 清空短信模板配置信息
  105. model('sms_template')->update([ 'tem_id' => 0, 'status' => 0, 'audit_status' => 0 ], [ [ 'site_id', '=', $site_id ] ]);
  106. // 刷新模板id
  107. $this->getSmsTemplatePageList($site_id, [], 1, 0, 'template_id desc', 'template_id,tem_id,template_name,audit_status');
  108. }
  109. return $res;
  110. }
  111. /**
  112. * 重置密码
  113. * @param $data
  114. * @return mixed
  115. */
  116. public function resetPassword($data)
  117. {
  118. $url = $this->api . '/sms/resetPassword';
  119. $res = $this->httpPost($url, $data);
  120. return $res;
  121. }
  122. /**
  123. * 获取动态数字码
  124. * @return mixed
  125. */
  126. public function captcha()
  127. {
  128. $url = $this->api . '/captcha/captcha';
  129. $res = $this->httpPost($url, []);
  130. return $res;
  131. }
  132. /**
  133. * 获取手机验证码
  134. * @param $data
  135. * @return mixed
  136. */
  137. public function mobileCode($data)
  138. {
  139. $url = $this->api . '/sms/mobileCode';
  140. $res = $this->httpPost($url, $data);
  141. return $res;
  142. }
  143. /**
  144. * 子账号添加短信签名
  145. * @param $data
  146. * @param $site_id
  147. * @param $app_module
  148. * @return array|mixed
  149. */
  150. public function addChildSignature($data, $site_id, $app_module)
  151. {
  152. $url = $this->api . '/sms/addChildSignature';
  153. $res = $this->httpPost($url, $data);
  154. // if ($res[ 'code' ] == 0) {
  155. // $config_model = new ConfigModel();
  156. // $sms_config = $config_model->getSmsConfig($site_id, $app_module);
  157. // $sms_config = $sms_config[ 'data' ][ 'value' ];
  158. // if (!empty($sms_config)) {
  159. // $save_data = $sms_config;
  160. // } else {
  161. // $save_data = $data;
  162. // }
  163. // $save_data[ 'signature' ] = "【" . $data[ 'signature' ] . "】";
  164. // $config_model->setSmsConfig($save_data, 1, $site_id, $app_module);
  165. // }
  166. return $res;
  167. }
  168. /**
  169. * 查询子账号信息
  170. */
  171. public function getChildAccountInfo($data)
  172. {
  173. $url = $this->api . '/sms/getChildAccountInfo';
  174. $res = $this->httpPost($url, $data);
  175. return $res;
  176. }
  177. /**
  178. * 获取签名列表
  179. * @param $data
  180. * @return mixed
  181. */
  182. public function getChildSignatureList($data)
  183. {
  184. $url = $this->api . '/sms/getChildSignatureList';
  185. $res = $this->httpPost($url, $data);
  186. return $res;
  187. }
  188. /**
  189. * 获取短信套餐包
  190. * @return mixed
  191. */
  192. public function getSmsPackageList()
  193. {
  194. $url = $this->api . '/sms/getSmsPackageList';
  195. $res = $this->httpPost($url, '');
  196. return $res;
  197. }
  198. /******************************************** 短信模板 start ********************************************************************/
  199. /**
  200. * 设置短信模板开启
  201. * @param $template_id
  202. * @param $status
  203. * @param $sms_config
  204. * @return array|mixed
  205. */
  206. public function enableTemplate($template_id, $status, $sms_config, $site_id, $app_module)
  207. {
  208. //获取模板信息
  209. $template_info = model('sms_template')->getInfo([ [ 'template_id', '=', $template_id ] ]);
  210. if (empty($template_info)) {
  211. return $this->error('', '模板不存在');
  212. }
  213. if (empty($sms_config)) {
  214. return $this->error('', '账号不存在,请先注册牛云短信账号');
  215. }
  216. model('sms_template')->startTrans();
  217. try {
  218. $signature_status = $this->querySignature($site_id, $app_module);
  219. if ($signature_status[ 'auditResult' ] != 2) {
  220. model('sms_template')->rollback();
  221. return $this->error('', $signature_status[ 'msg' ]);
  222. }
  223. if ($template_info[ 'tem_id' ] == 0) {
  224. $data = [
  225. 'username' => $sms_config[ 'username' ],
  226. 'signature' => $sms_config[ 'signature' ],
  227. 'template_name' => $template_info[ 'template_name' ],
  228. 'template_type' => $template_info[ 'template_type' ],
  229. 'template_content' => $template_info[ 'template_content' ],
  230. 'param_json' => $template_info[ 'param_json' ]
  231. ];
  232. $url = $this->api . '/sms/addChildSmsTemplate';
  233. $res = $this->httpPost($url, $data);
  234. if ($res[ 'code' ] < 0) {
  235. model('sms_template')->rollback();
  236. return $res;
  237. }
  238. //修改状态
  239. $template_data = [
  240. 'tem_id' => $res[ 'data' ][ 'temId' ],
  241. 'status' => $status,
  242. 'audit_status' => 1,
  243. 'update_time' => time()
  244. ];
  245. } else {
  246. //修改状态
  247. $template_data = [
  248. 'status' => $status,
  249. 'update_time' => time()
  250. ];
  251. }
  252. model('sms_template')->update($template_data, [ [ 'template_id', '=', $template_id ] ]);
  253. //判断message信息是否存在
  254. $message_info = model('message')->getInfo([ [ 'keywords', '=', $template_info[ 'keywords' ] ] ]);
  255. if ($message_info) {
  256. $message_data = [
  257. 'sms_is_open' => $status
  258. ];
  259. model('message')->update($message_data, [ [ 'keywords', '=', $template_info[ 'keywords' ] ] ]);
  260. } else {
  261. $message_data = [
  262. 'site_id' => 1,
  263. 'keywords' => $template_info[ 'keywords' ],
  264. 'sms_is_open' => $status
  265. ];
  266. model('message')->add($message_data);
  267. }
  268. model('sms_template')->commit();
  269. return $this->success();
  270. } catch (\Exception $e) {
  271. model('sms_template')->rollback();
  272. return $this->error('', $e->getMessage());
  273. }
  274. }
  275. /**
  276. * 设置短信模板关闭
  277. * @param $template_ids
  278. * @param $status
  279. * @param $sms_config
  280. * @return array|mixed
  281. */
  282. public function disableTemplate($template_ids, $status, $sms_config)
  283. {
  284. //获取模板信息
  285. $template_list = model('sms_template')->getList([ [ 'template_id', 'in', $template_ids ] ]);
  286. if (empty($template_list)) {
  287. return $this->error('', '模板不存在');
  288. }
  289. if (empty($sms_config)) {
  290. return $this->error('', '账号不存在,请先注册牛云短信账号');
  291. }
  292. model('sms_template')->startTrans();
  293. try {
  294. //修改状态
  295. $template_data = [
  296. 'status' => $status,
  297. 'update_time' => time()
  298. ];
  299. model('sms_template')->update($template_data, [ [ 'template_id', 'in', $template_ids ] ]);
  300. foreach ($template_list as $k => $v) {
  301. //判断message信息是否存在
  302. $message_info = model('message')->getInfo([ [ 'keywords', '=', $v[ 'keywords' ] ] ]);
  303. if ($message_info) {
  304. $message_data = [
  305. 'sms_is_open' => $status
  306. ];
  307. model('message')->update($message_data, [ [ 'keywords', '=', $v[ 'keywords' ] ] ]);
  308. } else {
  309. $message_data = [
  310. 'site_id' => 1,
  311. 'keywords' => $v[ 'keywords' ],
  312. 'sms_is_open' => $status
  313. ];
  314. model('message')->add($message_data);
  315. }
  316. }
  317. model('sms_template')->commit();
  318. return $this->success();
  319. } catch (\Exception $e) {
  320. model('sms_template')->rollback();
  321. return $this->error('', $e->getMessage());
  322. }
  323. }
  324. /**
  325. * 修改审核状态
  326. * @param $audit_status
  327. * @param $template_id
  328. * @return array
  329. */
  330. public function modifyAuditStatus($audit_status, $template_id)
  331. {
  332. $res = model('sms_template')->update([ 'audit_status' => $audit_status ], [ [ 'template_id', '=', $template_id ] ]);
  333. return $this->success($res);
  334. }
  335. /**
  336. * 查询短信模板审核状态
  337. * @param $data
  338. * @return array|mixed
  339. */
  340. public function queryTemplate($data)
  341. {
  342. $url = 'https://api.mix2.zthysms.com/sms/v2/template/query';
  343. $res = $this->sendSms($url, $data);
  344. return $res;
  345. }
  346. /**
  347. * 获取短信模板分页列表
  348. * @param $site_id
  349. * @param array $condition
  350. * @param int $page
  351. * @param int $page_size
  352. * @param string $order
  353. * @param string $field
  354. * @return array
  355. */
  356. public function getSmsTemplatePageList($site_id, $condition = [], $page = 1, $page_size = PAGE_LIST_ROWS, $order = 'template_id desc', $field = '*')
  357. {
  358. $res = model('sms_template')->pageList($condition, $field, $order, $page, $page_size);
  359. $config_model = new ConfigModel();
  360. $sms_config = $config_model->getSmsConfig($site_id, 'shop');
  361. $sms_config = $sms_config[ 'data' ][ 'value' ];
  362. $url = $this->api . '/sms/getChildSmsTemplateList';
  363. $sms_template_list = $this->httpPost($url, [ 'username' => $sms_config[ 'username' ] ]);
  364. $sms_template_list = $sms_template_list[ 'data' ];
  365. // 修改模板id、审核状态
  366. if (!empty($sms_template_list)) {
  367. foreach ($res[ 'list' ] as $k => $v) {
  368. if ($v[ 'tem_id' ] == 0 || $v[ 'audit_status' ] != 2) {
  369. foreach ($sms_template_list as $ck => $cv) {
  370. if ($cv[ 'temName' ] == $v[ 'template_name' ] && $cv[ 'auditResult' ] == 2) {
  371. $res[ 'list' ][ $k ][ 'tem_id' ] = $cv[ 'temId' ];
  372. $res[ 'list' ][ $k ][ 'audit_status' ] = 2;
  373. $res[ 'list' ][ $k ][ 'status' ] = 1;
  374. model('sms_template')->update([ 'tem_id' => $cv[ 'temId' ], 'audit_status' => 2, 'status' => 1 ], [ [ 'template_id', '=', $v[ 'template_id' ] ] ]);
  375. }
  376. }
  377. }
  378. }
  379. }
  380. return $this->success($res);
  381. }
  382. /**
  383. * 发送短信
  384. * @param $params
  385. * @return array
  386. */
  387. public function send($params)
  388. {
  389. $config_model = new ConfigModel();
  390. $sms_config = $config_model->getSmsConfig($params[ 'site_id' ], 'shop')[ 'data' ];
  391. if ($sms_config[ 'is_use' ]) {
  392. $config = $sms_config[ 'value' ];
  393. if (empty($config)) return $this->error([], "牛云短信尚未配置");
  394. $sms_info = $params[ "message_info" ][ "sms_json_array" ];//消息类型模板 短信模板信息
  395. if (empty($sms_info)) return $this->error([], "消息模板尚未配置");
  396. if ($sms_info[ 'audit_status' ] != 2) return $this->error([], "消息模板尚未审核通过");
  397. $time = time();
  398. $data = [
  399. 'username' => $config[ 'username' ],
  400. 'password' => md5(md5($config[ 'password' ]) . $time),
  401. 'signature' => $config[ 'signature' ],
  402. 'tKey' => $time,
  403. 'tpId' => $sms_info[ 'tem_id' ],
  404. 'records' => [
  405. 'mobile' => $params[ 'sms_account' ],
  406. 'tpContent' => $params[ 'var_parse' ]
  407. ]
  408. ];
  409. $result = $this->sendSms('https://api.mix2.zthysms.com/v2/sendSmsTp', $data);
  410. if ($result[ 'code' ] == 200) {
  411. return $this->success([ "addon" => "niusms", "addon_name" => "牛云短信", "content" => $sms_info[ "template_content" ] ]);
  412. } else {
  413. return $this->error([], $this->error_msg[ $result[ 'code' ] ] ?? $result[ 'msg' ]);
  414. }
  415. }
  416. }
  417. /******************************************** 短信模板 end ********************************************************************/
  418. /**
  419. * 数据请求
  420. * @param $url
  421. * @param $data
  422. * @return mixed
  423. */
  424. public function httpPost($url, $data)
  425. {
  426. // 模拟提交数据函数
  427. $curl = curl_init(); // 启动一个CURL会话
  428. curl_setopt($curl, CURLOPT_URL, $url); // 要访问的地址
  429. curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, false); // 对认证证书来源的检查
  430. curl_setopt($curl, CURLOPT_SSL_VERIFYHOST, false); // 从证书中检查SSL加密算法是否存在
  431. curl_setopt($curl, CURLOPT_USERAGENT, $_SERVER[ 'HTTP_USER_AGENT' ]); // 模拟用户使用的浏览器
  432. curl_setopt($curl, CURLOPT_POST, true); // 发送一个常规的Post请求
  433. curl_setopt($curl, CURLOPT_POSTFIELDS, json_encode($data)); // Post提交的数据包
  434. curl_setopt($curl, CURLOPT_TIMEOUT, 30); // 设置超时限制防止死循环
  435. curl_setopt($curl, CURLOPT_RETURNTRANSFER, true); // 获取的信息以文件流的形式返回
  436. curl_setopt($curl, CURLOPT_HEADER, false); //开启header
  437. curl_setopt($curl, CURLOPT_HTTPHEADER, array (
  438. 'Content-Type: application/json; charset=utf-8',
  439. )); //类型为json
  440. //类型为json
  441. $result = curl_exec($curl); // 执行操作
  442. if (curl_errno($curl)) {
  443. return $this->error('', '系统错误,请联系平台进行处理');
  444. }
  445. curl_close($curl); // 关键CURL会话
  446. $return = json_decode($result, true); // 返回数据
  447. if (!empty($return)) {
  448. if ($return[ 'code' ] < 0) {
  449. return $this->error($return[ 'code' ], $return[ 'message' ]);
  450. } else {
  451. return $this->success($return[ 'data' ]);
  452. }
  453. } else {
  454. return $result;
  455. }
  456. }
  457. public function sendSms($url, $data)
  458. {
  459. // 模拟提交数据函数
  460. $curl = curl_init(); // 启动一个CURL会话
  461. curl_setopt($curl, CURLOPT_URL, $url); // 要访问的地址
  462. curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, false); // 对认证证书来源的检查
  463. curl_setopt($curl, CURLOPT_SSL_VERIFYHOST, false); // 从证书中检查SSL加密算法是否存在
  464. curl_setopt($curl, CURLOPT_USERAGENT, $_SERVER[ 'HTTP_USER_AGENT' ]); // 模拟用户使用的浏览器
  465. curl_setopt($curl, CURLOPT_POST, true); // 发送一个常规的Post请求
  466. curl_setopt($curl, CURLOPT_POSTFIELDS, json_encode($data)); // Post提交的数据包
  467. curl_setopt($curl, CURLOPT_TIMEOUT, 30); // 设置超时限制防止死循环
  468. curl_setopt($curl, CURLOPT_RETURNTRANSFER, true); // 获取的信息以文件流的形式返回
  469. curl_setopt($curl, CURLOPT_HEADER, false); //开启header
  470. curl_setopt($curl, CURLOPT_HTTPHEADER, array (
  471. 'Content-Type: application/json; charset=utf-8',
  472. )); //类型为json
  473. //类型为json
  474. $result = curl_exec($curl); // 执行操作
  475. if (curl_errno($curl)) {
  476. return $this->error('', '系统错误,请联系平台进行处理');
  477. }
  478. curl_close($curl); // 关键CURL会话
  479. return json_decode($result, true); // 返回数据
  480. }
  481. public function updateNiusmsTel($mobiles, $username)
  482. {
  483. $url = $this->api . '/sms/updateMemberNiusmsTel';
  484. $res = $this->httpPost($url, [ 'mobiles' => $mobiles, "username" => $username ]);
  485. return $res;
  486. }
  487. }