You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

49 lines
1.4 KiB

<?php
namespace App\Services;
use Illuminate\Support\Facades\Http;
use RuntimeException;
class WeChatMiniProgramService
{
/**
* @return array{openid: string, unionid?: string, session_key: string}
*/
public function codeToSession(string $code): array
{
$appId = config('services.wechat.mini_program.app_id');
$secret = config('services.wechat.mini_program.secret');
if (! $appId || ! $secret) {
throw new RuntimeException('微信小程序 AppID/Secret 未配置');
}
$response = Http::timeout(10)->get('https://api.weixin.qq.com/sns/jscode2session', [
'appid' => $appId,
'secret' => $secret,
'js_code' => $code,
'grant_type' => 'authorization_code',
]);
$payload = $response->json();
if (! is_array($payload)) {
throw new RuntimeException('微信登录响应异常');
}
if (! empty($payload['errcode'])) {
throw new RuntimeException((string) ($payload['errmsg'] ?? '微信登录失败'));
}
if (empty($payload['openid'])) {
throw new RuntimeException('微信登录未返回 openid');
}
return [
'openid' => (string) $payload['openid'],
'unionid' => isset($payload['unionid']) ? (string) $payload['unionid'] : null,
'session_key' => (string) ($payload['session_key'] ?? ''),
];
}
}