优化验证token接口-暂时不验证token有效性
This commit is contained in:
@@ -393,7 +393,7 @@ class Playx extends Api
|
||||
|
||||
/**
|
||||
* Token 验证 - POST /api/v1/playx/verify-token
|
||||
* 配置 playx.verify_token_local_only=true 时仅本地校验 token(不请求 PlayX)。
|
||||
* 配置 playx.verify_token_local_only=true 时:不向 PlayX 请求,且不校验传入 token(联调占位)。
|
||||
*/
|
||||
public function verifyToken(Request $request): Response
|
||||
{
|
||||
@@ -402,15 +402,15 @@ class Playx extends Api
|
||||
return $response;
|
||||
}
|
||||
|
||||
if (config('playx.verify_token_local_only', false)) {
|
||||
return $this->verifyTokenLocalOpen();
|
||||
}
|
||||
|
||||
$token = strval($request->post('token', $request->post('session', $request->get('token', ''))));
|
||||
if ($token === '') {
|
||||
return $this->error(__('Token expiration'), null, 0, ['statusCode' => 401]);
|
||||
}
|
||||
|
||||
if (config('playx.verify_token_local_only', false)) {
|
||||
return $this->verifyTokenLocal($token);
|
||||
}
|
||||
|
||||
$baseUrl = config('playx.api.base_url', '');
|
||||
$verifyUrl = config('playx.api.token_verify_url', '/api/v1/auth/verify-token');
|
||||
if ($baseUrl === '') {
|
||||
@@ -470,128 +470,32 @@ class Playx extends Api
|
||||
}
|
||||
|
||||
/**
|
||||
* 联调:合作方 JWT payload 的 base64url 解码(不验签),仅用于 dev_verify_token_exact 命中后的 session 字段。
|
||||
*
|
||||
* @return array{sub?: string, user_fullname?: string, exp?: int}|null
|
||||
* 本地联调:不校验 token,按配置默认用户签发新 mall_session(待 PlayX 远程校验就绪后关闭 verify_token_local_only)。
|
||||
*/
|
||||
private function parsePartnerJwtPayloadForDev(string $jwt): ?array
|
||||
private function verifyTokenLocalOpen(): Response
|
||||
{
|
||||
$parts = explode('.', $jwt);
|
||||
if (count($parts) < 2) {
|
||||
return null;
|
||||
}
|
||||
$payload = $parts[1];
|
||||
$b64 = strtr($payload, '-_', '+/');
|
||||
$pad = strlen($b64) % 4;
|
||||
if ($pad > 0) {
|
||||
$b64 .= str_repeat('=', 4 - $pad);
|
||||
}
|
||||
$raw = base64_decode($b64, true);
|
||||
if ($raw === false || $raw === '') {
|
||||
return null;
|
||||
}
|
||||
$decoded = json_decode($raw, true);
|
||||
if (!is_array($decoded)) {
|
||||
return null;
|
||||
}
|
||||
|
||||
return $decoded;
|
||||
}
|
||||
|
||||
/**
|
||||
* 本地校验 temLogin 等写入的商城 token(类型 muser),写入 mall_session
|
||||
*/
|
||||
private function verifyTokenLocal(string $token): Response
|
||||
{
|
||||
$devExact = strval(config('playx.dev_verify_token_exact', ''));
|
||||
if ($devExact !== '' && hash_equals($devExact, $token)) {
|
||||
$payload = $this->parsePartnerJwtPayloadForDev($token);
|
||||
if ($payload === null) {
|
||||
return $this->error(__('Token expiration'), null, 0, ['statusCode' => 401]);
|
||||
}
|
||||
if (isset($payload['exp'])) {
|
||||
$exp = intval($payload['exp']);
|
||||
if ($exp > 0 && $exp <= time()) {
|
||||
return $this->error(__('Token expiration'), null, 0, ['statusCode' => 401]);
|
||||
}
|
||||
}
|
||||
|
||||
$overrideUserId = strval(config('playx.dev_verify_session_user_id', ''));
|
||||
$playxUserId = $overrideUserId;
|
||||
if ($playxUserId === '' && isset($payload['sub']) && is_string($payload['sub'])) {
|
||||
$playxUserId = $payload['sub'];
|
||||
}
|
||||
if ($playxUserId === '') {
|
||||
return $this->error(__('Token expiration'), null, 0, ['statusCode' => 401]);
|
||||
}
|
||||
|
||||
$overrideUsername = strval(config('playx.dev_verify_session_username', ''));
|
||||
$username = $overrideUsername;
|
||||
if ($username === '') {
|
||||
if (isset($payload['user_fullname']) && is_string($payload['user_fullname']) && $payload['user_fullname'] !== '') {
|
||||
$username = $payload['user_fullname'];
|
||||
} elseif (isset($payload['sub']) && is_string($payload['sub'])) {
|
||||
$username = $payload['sub'];
|
||||
}
|
||||
}
|
||||
|
||||
$expireAt = time() + intval(config('playx.session_expire_seconds', 3600));
|
||||
$sessionId = bin2hex(random_bytes(16));
|
||||
MallSession::create([
|
||||
'session_id' => $sessionId,
|
||||
'user_id' => $playxUserId,
|
||||
'username' => $username,
|
||||
'expire_time' => $expireAt,
|
||||
'create_time' => time(),
|
||||
'update_time' => time(),
|
||||
]);
|
||||
|
||||
return $this->success('', [
|
||||
'session_id' => $sessionId,
|
||||
'user_id' => $playxUserId,
|
||||
'username' => $username,
|
||||
'token_expire_at' => date('c', $expireAt),
|
||||
]);
|
||||
}
|
||||
|
||||
$tokenData = Token::get($token);
|
||||
if (empty($tokenData) || (isset($tokenData['expire_time']) && intval($tokenData['expire_time']) <= time())) {
|
||||
return $this->error(__('Token expiration'), null, 0, ['statusCode' => 401]);
|
||||
}
|
||||
$tokenType = strval($tokenData['type'] ?? '');
|
||||
if ($tokenType !== UserAuth::TOKEN_TYPE_MALL_USER) {
|
||||
return $this->error(__('Token expiration'), null, 0, ['statusCode' => 401]);
|
||||
}
|
||||
$assetId = intval($tokenData['user_id'] ?? 0);
|
||||
if ($assetId <= 0) {
|
||||
return $this->error(__('Token expiration'), null, 0, ['statusCode' => 401]);
|
||||
}
|
||||
|
||||
$asset = MallUserAsset::where('id', $assetId)->find();
|
||||
if (!$asset) {
|
||||
return $this->error(__('Token expiration'), null, 0, ['statusCode' => 401]);
|
||||
}
|
||||
|
||||
$playxUserId = strval($asset->playx_user_id ?? '');
|
||||
$playxUserId = strval(config('playx.verify_token_local_default_user_id', 'testmyr'));
|
||||
$username = strval(config('playx.verify_token_local_default_username', 'yangyang123'));
|
||||
if ($playxUserId === '') {
|
||||
$playxUserId = strval($assetId);
|
||||
return $this->error(__('PlayX API not configured'));
|
||||
}
|
||||
|
||||
$expireAt = time() + intval(config('playx.session_expire_seconds', 3600));
|
||||
$sessionId = bin2hex(random_bytes(16));
|
||||
$now = time();
|
||||
MallSession::create([
|
||||
'session_id' => $sessionId,
|
||||
'user_id' => $playxUserId,
|
||||
'username' => strval($asset->username ?? ''),
|
||||
'username' => $username,
|
||||
'expire_time' => $expireAt,
|
||||
'create_time' => time(),
|
||||
'update_time' => time(),
|
||||
'create_time' => $now,
|
||||
'update_time' => $now,
|
||||
]);
|
||||
|
||||
return $this->success('', [
|
||||
return $this->success('Success', [
|
||||
'session_id' => $sessionId,
|
||||
'user_id' => $playxUserId,
|
||||
'username' => strval($asset->username ?? ''),
|
||||
'username' => $username,
|
||||
'token_expire_at' => date('c', $expireAt),
|
||||
]);
|
||||
}
|
||||
|
||||
@@ -20,23 +20,14 @@ return [
|
||||
// token 会话缓存过期时间(秒)
|
||||
'session_expire_seconds' => intval(env('PLAYX_SESSION_EXPIRE_SECONDS', '3600')),
|
||||
/**
|
||||
* 为 true 时:/api/v1/playx/verify-token 仅本地校验(查 token 表 + mall_playx_user_asset),不请求 PlayX。
|
||||
* 联调/无 PlayX 环境可开;上线对接 PlayX 后请设为 false 并配置 api.base_url。
|
||||
* 为 true 时:verifyToken 不向 PlayX 请求;当前实现为联调占位——不校验请求中的 token,
|
||||
* 每次签发新 session,用户标识见 verify_token_local_default_*(待对方提供校验接口后请设为 false 并走远程校验)。
|
||||
*/
|
||||
'verify_token_local_only' => filter_var(env('PLAYX_VERIFY_TOKEN_LOCAL_ONLY', '1'), FILTER_VALIDATE_BOOLEAN),
|
||||
/**
|
||||
* 联调占位(待对方提供 token 校验接口后删除或清空):verify_token_local_only 为 true 时,
|
||||
* 若请求中的 token 与此字符串完全一致则视为有效合作方 JWT,并写入 mall_session。
|
||||
* 生产环境务必置空或通过环境变量覆盖为空。
|
||||
*/
|
||||
'dev_verify_token_exact' => strval(env(
|
||||
'PLAYX_DEV_VERIFY_TOKEN_EXACT',
|
||||
'eyJhbGciOiJIUzUxMiJ9.eyJzdWIiOiJ0ZXN0bXlyIiwiYXV0aCI6IlJPTEVfTUVNQkVSIiwibWVyY2hhbnQiOiJwbHgiLCJ1c2VyX2Z1bGxuYW1lIjoiQW5uYSIsImN1cnJlbmN5IjoiTVlSIiwibGFuZ3VhZ2UiOiJ6aC1DTiIsInZpcCI6ZmFsc2UsImV4cCI6MTc3NjkzODI4N30.XVvNcnBcAEqdxqoNRmygkl826bLUfwH2xyBE8wiSTOSeJjv99DHKJOAgsE4ukJ-M_t1hPbraz9GO4qvOszOeDg'
|
||||
)),
|
||||
/** 命中 dev_verify_token_exact 时写入 session 的展示用户名(空则取 JWT user_fullname 或 sub) */
|
||||
'dev_verify_session_username' => strval(env('PLAYX_DEV_VERIFY_SESSION_USERNAME', 'yangyang123')),
|
||||
/** 命中 dev_verify_token_exact 时写入 session 的 user_id(空则取 JWT sub) */
|
||||
'dev_verify_session_user_id' => strval(env('PLAYX_DEV_VERIFY_SESSION_USER_ID', '')),
|
||||
/** verify_token_local_only 为 true 时写入 mall_session 的 playx 用户标识 */
|
||||
'verify_token_local_default_user_id' => strval(env('PLAYX_VERIFY_TOKEN_LOCAL_DEFAULT_USER_ID', 'testmyr')),
|
||||
/** verify_token_local_only 为 true 时写入 mall_session 的展示用户名 */
|
||||
'verify_token_local_default_username' => strval(env('PLAYX_VERIFY_TOKEN_LOCAL_DEFAULT_USERNAME', 'yangyang123')),
|
||||
// PlayX API 配置(商城调用 PlayX 时使用)
|
||||
'api' => [
|
||||
'base_url' => strval(env('PLAYX_API_BASE_URL', '')),
|
||||
|
||||
Reference in New Issue
Block a user