WechatService.php 4.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129
  1. <?php
  2. // +----------------------------------------------------------------------
  3. // | LARAVEL8.0 框架 [ LARAVEL ][ RXThinkCMF ]
  4. // +----------------------------------------------------------------------
  5. // | 版权所有 2017~2021 LARAVEL研发中心
  6. // +----------------------------------------------------------------------
  7. // | 官方网站: http://www.laravel.cn
  8. // +----------------------------------------------------------------------
  9. // | Author: laravel开发员 <laravel.qq.com>
  10. // +----------------------------------------------------------------------
  11. namespace App\Services;
  12. use App\Services\Api\MemberService;
  13. use Dotenv\Dotenv;
  14. use Laravel\Socialite\Facades\Socialite;
  15. use SocialiteProviders\WeixinWeb\Provider;
  16. /**
  17. * 微信服务管理-服务类
  18. * @author laravel开发员
  19. * @since 2020/11/11
  20. * Class WechatService
  21. * @package App\Services
  22. */
  23. class WechatService extends BaseService
  24. {
  25. // 静态对象
  26. protected static $instance = null;
  27. public function __construct()
  28. {
  29. $wxAppid = ConfigService::make()->getConfigByCode('wechat_appid');
  30. $wxAppSecret = ConfigService::make()->getConfigByCode('wechat_appsecret');
  31. // 配置更新
  32. if($wxAppid != env('WEIXIN_APP_ID') || $wxAppSecret != env('WEIXIN_SECRET')){
  33. $env = Dotenv::createArrayBacked(base_path())->load();
  34. $env['WEIXIN_APP_ID'] = $wxAppid;
  35. $env['WEIXIN_SECRET'] = $wxAppSecret;
  36. $envStr = '';
  37. foreach($env as $k => $v){
  38. $envStr .= $k.'='.$v."\n";
  39. }
  40. file_put_contents(base_path().'/.env', $envStr);
  41. }
  42. }
  43. /**
  44. * 静态入口
  45. * @return WechatService|static|null
  46. */
  47. public static function make()
  48. {
  49. if (!self::$instance) {
  50. self::$instance = new static();
  51. }
  52. return self::$instance;
  53. }
  54. /**
  55. * 微信授权登录
  56. * @param array $params
  57. * @return mixed
  58. */
  59. public function auth($params=[])
  60. {
  61. $openid = isset($params['openid'])? $params['openid'] : '';
  62. $referrer = isset($params['invite_code'])? $params['invite_code'] : '';
  63. $accessToken = isset($params['access_token'])? $params['access_token'] : '';
  64. if(empty($openid) || empty($accessToken)){
  65. $this->error = '2016';
  66. return false;
  67. }
  68. // 获取微信用户信息
  69. $wechatInfo = $this->getUserInfo($openid, $accessToken);
  70. RedisService::set("caches:wechat:{$openid}:temp", ['params'=> $params,'user'=>$wechatInfo], 7200);
  71. // 注册
  72. $appSources = isset($params['app_sources'])? $params['app_sources'] : '';
  73. $wechatInfo['openid'] = $openid;
  74. $wechatInfo['mobile'] = isset($params['mobile'])? trim($params['mobile']) : '';
  75. $wechatInfo['device'] = $appSources=='android'? 2 : 1;
  76. $wechatInfo['invite_code'] = $referrer;
  77. if(!$result = MemberService::make()->loginByWechat($wechatInfo)){
  78. $this->error = MemberService::make()->getError();
  79. return false;
  80. }else{
  81. return $result;
  82. }
  83. }
  84. /**
  85. * 微信用户信息
  86. * @param $openid
  87. * @param $accessToken
  88. * @param false $refresh 是否强制刷新
  89. * @return array|mixed
  90. */
  91. public function getUserInfo($openid, $accessToken, $refresh = false)
  92. {
  93. // 获取授权信息
  94. $cacheKey = "caches:wechat:{$openid}:info_".md5($accessToken);
  95. $data = RedisService::get($cacheKey);
  96. $info = isset($data['info'])? $data['info'] : [];
  97. if($info && !$refresh){
  98. return $info;
  99. }
  100. try {
  101. $driver = Socialite::with('weixin');
  102. $driver->setOpenId($openid);
  103. $wechatInfo = $driver->userFromToken($accessToken);
  104. if ($wechatInfo) {
  105. RedisService::set($cacheKey, ['openid' => $openid, 'access_token' => $accessToken, 'info' => $wechatInfo], rand(3600, 7200));
  106. }
  107. return $wechatInfo;
  108. }catch (\Exception $exception){
  109. RedisService::set($cacheKey.'_error', ['openid' => $openid, 'access_token' => $accessToken, 'error' => $exception->getMessage()], rand(3600, 7200));
  110. return [];
  111. }
  112. }
  113. }