Mpapp.php 8.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239
  1. <?php
  2. declare(strict_types=1);
  3. namespace app\api\controller;
  4. use app\common\model\Admin;
  5. use app\common\model\MpSubscribe;
  6. use app\common\model\Qrcode;
  7. use app\common\model\Third;
  8. use app\common\model\QrcodeScan;
  9. use app\common\model\User;
  10. class Mpapp extends Api{
  11. protected $noNeedLogin = ['*'];
  12. protected $config=[];
  13. const PAGE=[
  14. //首页
  15. 'index'=>'/pages/index/index',
  16. //绑定用户
  17. 'binduser'=>'/pages/index/index',
  18. //NEXT页
  19. 'next'=>'/pages/index/next',
  20. ];
  21. protected function _initialize()
  22. {
  23. parent::_initialize();
  24. $this->config=[
  25. 'appid'=>site_config("uniapp.mpapp_id"),
  26. 'appsecret'=>site_config("uniapp.mpapp_secret"),
  27. 'token'=>site_config("uniapp.mpapp_token"),
  28. 'encodingaeskey'=>site_config("uniapp.mpapp_aeskey")
  29. ];
  30. }
  31. /**
  32. * 发起授权
  33. */
  34. public function connect()
  35. {
  36. if($this->auth->id){
  37. return $this->gourl();
  38. }else{
  39. $arr=$this->request->get();
  40. if(count($arr)>0){
  41. $str='';
  42. foreach ($arr as $k=>$v){
  43. $str.=$k.'='.$v.'&';
  44. }
  45. $str=substr($str,0,strlen($str)-1);
  46. $callback=$this->request->domain().'/api/mpapp/callback?'.$str;
  47. }else{
  48. $callback=$this->request->domain().'/api/mpapp/callback';
  49. }
  50. $wechat = new \WeChat\Oauth($this->config);
  51. // 执行操作
  52. $result = $wechat->getOauthRedirect($callback, '', 'snsapi_userinfo');
  53. return redirect($result);
  54. }
  55. }
  56. /**
  57. * 授权回调
  58. */
  59. public function callback()
  60. {
  61. // 授权成功后的回调
  62. $wechat = new \WeChat\Oauth($this->config);
  63. $result = $wechat->getOauthAccessToken();
  64. $userinfo = $wechat->getUserInfo($result['access_token'],$result['openid']);
  65. $result['nickname']=$userinfo['nickname'];
  66. $result['avatar']=$userinfo['headimgurl'];
  67. //判断是否启用账号绑定
  68. $third=Third::connect('mpapp', $result);
  69. $this->auth->loginByThirdPlatform(Third::PLATFORM('微信公众号'),$third);
  70. return $this->gourl();
  71. }
  72. private function gourl()
  73. {
  74. $arr=$this->request->get();
  75. $action=$arr['action'];
  76. unset($arr['action']);
  77. unset($arr['code']);
  78. unset($arr['state']);
  79. $query='&'.http_build_query($arr);
  80. $url=request()->domain().'/h5/#'.self::PAGE[$action].'?token='.$this->auth->getToken().$query;
  81. return redirect($url);
  82. }
  83. /**
  84. * 创建菜单
  85. */
  86. public function menu()
  87. {
  88. $this->error('请删除这行代码后重试');
  89. $menu = new \WeChat\Menu($this->config);
  90. $json=array('button'=>[
  91. //跳转到公众号页面
  92. [
  93. "name"=>"首页",
  94. "url"=>$this->request->domain()."/h5/#/pages/index/index",
  95. "type"=>"view",
  96. ],
  97. //跳转到小程序页面
  98. [
  99. "name"=>"列表",
  100. "type"=>"miniprogram",
  101. "appid"=>site_config("uniapp.miniapp_id"),
  102. "pagepath"=>"pages/index/list",
  103. ],
  104. //二级页面
  105. [
  106. "name"=>"我的",
  107. "sub_button"=>[
  108. //先登陆,再跳转到指定页面
  109. [
  110. "name"=>"我的余额",
  111. "url"=>$this->request->domain()."api/mpapp/connect?action=101",
  112. "type"=>"view",
  113. ],
  114. [
  115. "name"=>"其他菜单",
  116. "type"=>"click",
  117. "key"=>"V1001_GOOD",
  118. ],
  119. ]
  120. ]
  121. ]);
  122. // 执行创建菜单
  123. $menu->create($json);
  124. $this->success('创建菜单成功');
  125. }
  126. /**
  127. * 公众号事件接收方法
  128. */
  129. public function event()
  130. {
  131. $api = new \WeChat\Receive($this->config);
  132. $msgtype=$api->getMsgType();
  133. if($msgtype=='text'){
  134. $api->text('尊敬客户您好,感谢您使用【'.site_config("basic.sitename").'】公众号!')->reply();
  135. return;
  136. }
  137. if($msgtype=='event'){
  138. $message = $api->getReceive();
  139. event('write_log','微信消息:'.json_encode($message));
  140. $event = $message['Event'];
  141. $eventkey = isset($message['EventKey'])? $message['EventKey'] : '';
  142. $openid=$message['FromUserName'];
  143. switch ($event) {
  144. //添加关注
  145. case 'subscribe':
  146. $user = new \WeChat\User($this->config);
  147. $userinfo=$user->getUserInfo($openid);
  148. $unionid=isset($userinfo['unionid'])?$userinfo['unionid'] : '';
  149. //记录关注
  150. MpSubscribe::create([
  151. 'openid'=>$openid,
  152. 'unionid'=>$unionid,
  153. ]);
  154. //普通关注
  155. if(is_array($eventkey)){
  156. $api->text('尊敬客户您好,感谢您使用【'.site_config("basic.sitename").'】公众号!')->reply();
  157. return;
  158. }
  159. //扫码关注
  160. if(strpos($eventkey,'qrscene_')===0){
  161. $eventkey=substr($eventkey,8);
  162. $resp=$this->scanQrcode($openid,$unionid,$eventkey);
  163. $api->text($resp)->reply();
  164. return;
  165. }
  166. //取消关注
  167. case 'unsubscribe':
  168. MpSubscribe::where(['openid'=>$openid])->delete();
  169. return;
  170. //扫二维码
  171. case 'SCAN':
  172. $user = new \WeChat\User($this->config);
  173. $userinfo=$user->getUserInfo($openid);
  174. $unionid=isset($userinfo['unionid'])?$userinfo['unionid'] : '';
  175. $resp=$this->scanQrcode($openid,$unionid,$eventkey);
  176. $api->text($resp)->reply();
  177. return;
  178. //跳转链接
  179. case 'VIEW':
  180. }
  181. }
  182. }
  183. /**
  184. * 扫码回调事件
  185. */
  186. private function scanQrcode($openid,$unionid,$qrcode_id)
  187. {
  188. $qrcode=Qrcode::find($qrcode_id);
  189. if(!$qrcode){
  190. return '尊敬客户您好,感谢您使用【'.site_config("basic.sitename").'】公众号!';
  191. }
  192. //记录扫码
  193. $scan=QrcodeScan::where(['openid'=>$openid,'qrcode_id'=>$qrcode->id])->find();
  194. if(!$scan){
  195. //生成的扫码记录表,可以在用户注册时,查询该表从而绑定推荐人
  196. QrcodeScan::create([
  197. 'openid'=>$openid,
  198. 'unionid'=>$unionid,
  199. 'qrcode_id'=>$qrcode->id,
  200. 'foreign_key'=>$qrcode->foreign_key,
  201. 'type'=>$qrcode->type,
  202. ]);
  203. }
  204. //根据业务场景返回不同的消息
  205. switch ($qrcode->type){
  206. case 'backend-login':
  207. $third=Third::where(['platform'=>Third::PLATFORM('微信公众号'),'openid'=>$openid])->find();
  208. if(!$third){
  209. return '您的微信没有绑定管理员,登陆失败!';
  210. }
  211. $admin=Admin::where(['third_id'=>$third->id])->find();
  212. if(!$admin){
  213. return '您的微信没有绑定管理员,登陆失败!';
  214. }
  215. if($admin->status=='hidden'){
  216. return '管理员已经被禁止,登陆失败!';
  217. }
  218. return '登陆成功!';
  219. case 'bind-third-user':
  220. $path=$this->request->domain()."/api/mpapp/connect?action=binduser";
  221. $end="<a href=\"{$path}\">👉👉点击这里授权👈️👈️</a>";
  222. return "您正在使用微信扫码授权获取您的微信头像、昵称\n\n{$end}";
  223. case 'toker':
  224. $user=User::find($qrcode->foreign_key);
  225. return '尊敬客户您好,您的好友'.$user->nickname.'推荐您使用【'.site_config("basic.sitename").'】公众号!';
  226. }
  227. }
  228. }