httpClient = $httpClient; $this->app = null; } /** * code2Session:小程序 wx.login 的 code 换取 openid / session_key * * @param string $code wx.login 返回的临时登录凭证 * @return array{openid: string, session_key: string, unionid?: string} */ public function code2Session(string $code): array { try { /** @var array{openid: string, session_key: string, unionid?: string} $session */ $session = $this->app()->getUtils()->codeToSession($code); } catch (HttpException|TransportExceptionInterface $e) { throw new RepositoryException('微信登录失败:' . $e->getMessage()); } return $session; } /** * 获取手机号:wx.getPhoneNumber 的 phoneCode 换取手机号 * * @param string $phoneCode 手机号授权事件返回的动态令牌 * @return string 用户手机号 */ public function getPhone(string $phoneCode): string { try { $result = $this->app()->getUtils()->getPhoneNumber($phoneCode); } catch (HttpException|TransportExceptionInterface $e) { throw new RepositoryException('获取手机号失败:' . $e->getMessage()); } $phone = (string) ($result['phone_info']['phoneNumber'] ?? $result['phone_info']['purePhoneNumber'] ?? ''); if ($phone === '') { throw new RepositoryException('获取手机号失败:微信未返回有效手机号'); } return $phone; } /** * EasyWeChat 小程序应用实例(懒构建单例) */ protected function app(): Application { if ($this->app === null) { $config = (array) config('services.wechat.mini', []); if (empty($config['appid']) || empty($config['secret'])) { throw new RepositoryException('微信小程序尚未配置(WECHAT_MINI_APPID / WECHAT_MINI_SECRET)'); } $this->app = new Application([ 'app_id' => (string) $config['appid'], 'secret' => (string) $config['secret'], ]); if ($this->httpClient !== null) { $this->app->setHttpClient($this->httpClient); } } return $this->app; } }