oauth_secret_is_configured($settings['oauth_proxy_secret'] ?? '', $stored['oauth_proxy_secret'] ?? ''); if ($mode === 'client') { $url = trim((string) ($settings['oauth_proxy_server_url'] ?? '')); if (!$this->is_secure_oauth_url($url)) { $errors[] = __('客户端代理模式需要有效的 HTTPS 服务端地址', 'aksrt'); } if (!$secret_configured) { $errors[] = __('客户端代理模式需要代理 HMAC 密钥', 'aksrt'); } if (empty($settings['oauth_proxy_client_providers']) || !is_array($settings['oauth_proxy_client_providers'])) { $errors[] = __('客户端代理模式至少需要启用一个登录平台', 'aksrt'); } return $errors; } if ($mode === 'server') { if (!$secret_configured) { $errors[] = __('服务端代理模式需要代理 HMAC 密钥', 'aksrt'); } $selected = is_array($settings['oauth_proxy_server_providers'] ?? null) ? $settings['oauth_proxy_server_providers'] : []; if ($selected === []) { $errors[] = __('服务端代理模式至少需要允许一个登录平台', 'aksrt'); } $provider_fields = [ 'github' => ['GitHub', 'github_appid', 'github_appkey'], 'gitee' => ['Gitee', 'gitee_appid', 'gitee_appkey'], 'qq' => ['QQ', 'qq_appid', 'qq_appkey'], 'google' => ['Google', 'google_client_id', 'google_client_secret'], 'weibo' => ['微博', 'weibo_appid', 'weibo_appkey'], 'weixin' => ['微信开放平台', 'weixin_appid', 'weixin_appsecret'], ]; foreach ($selected as $provider) { if (!isset($provider_fields[$provider])) { continue; } [$label, $id_key, $secret_key] = $provider_fields[$provider]; if (trim((string) ($settings[$id_key] ?? '')) === '' || !$this->oauth_secret_is_configured($settings[$secret_key] ?? '', $stored[$secret_key] ?? '')) { $errors[] = sprintf(__('代理服务端的 %s 平台缺少完整凭据', 'aksrt'), $label); } } return $errors; } $providers = [ 'github' => ['GitHub', 'github_appid', 'github_appkey'], 'gitee' => ['Gitee', 'gitee_appid', 'gitee_appkey'], 'qq' => ['QQ', 'qq_appid', 'qq_appkey'], 'google' => ['Google', 'google_client_id', 'google_client_secret'], 'weibo' => ['微博', 'weibo_appid', 'weibo_appkey'], 'weixin' => ['微信开放平台', 'weixin_appid', 'weixin_appsecret'], ]; $enabled = 0; foreach ($providers as $provider => [$label, $id_key, $secret_key]) { if (empty($settings['oauth_' . $provider . '_s'])) { continue; } $enabled++; if (trim((string) ($settings[$id_key] ?? '')) === '' || !$this->oauth_secret_is_configured($settings[$secret_key] ?? '', $stored[$secret_key] ?? '')) { $errors[] = sprintf(__('%s 登录已启用,请填写完整凭据', 'aksrt'), $label); } } if (!empty($settings['oauth_weixingzh_s'])) { $enabled++; $gzh_type = sanitize_key((string) ($settings['weixingzh_gzh_type'] ?? 'service')); $base_ready = $this->oauth_secret_is_configured($settings['weixingzh_token'] ?? '', $stored['weixingzh_token'] ?? '') && trim((string) ($settings['weixingzh_appid'] ?? '')) !== ''; $mode_ready = $gzh_type === 'subscribe' ? trim((string) ($settings['weixingzh_code_qrcode'] ?? '')) !== '' && trim((string) ($settings['weixingzh_code_keyword'] ?? '')) !== '' : $this->oauth_secret_is_configured($settings['weixingzh_appsecret'] ?? '', $stored['weixingzh_appsecret'] ?? ''); if (!$base_ready || !$mode_ready) { $errors[] = $gzh_type === 'subscribe' ? __('微信公众号订阅号登录已启用,请填写 Token、AppID、二维码和回复关键词', 'aksrt') : __('微信公众号服务号登录已启用,请填写 Token、AppID 和 AppSecret', 'aksrt'); } } if (!empty($settings['clogin_s'])) { $enabled++; if (!$this->is_secure_oauth_url((string) ($settings['clogin_url'] ?? '')) || trim((string) ($settings['clogin_id'] ?? '')) === '' || !$this->oauth_secret_is_configured($settings['clogin_key'] ?? '', $stored['clogin_key'] ?? '') || empty($settings['clogin_oauth_s']) ) { $errors[] = __('彩虹聚合登录已启用,请填写 HTTPS 接口地址、AppID、AppKey 并选择平台', 'aksrt'); } } if ($enabled === 0) { $errors[] = __('启用第三方登录后,至少需要启用一个本地登录提供商', 'aksrt'); } return $errors; } private function oauth_secret_is_configured($value, $stored_value = ''): bool { $value = trim((string) $value); if ($value === '***') { return trim((string) $stored_value) !== ''; } return $value !== ''; } private function is_secure_oauth_url(string $url): bool { $url = trim($url); if ($url === '' || filter_var($url, FILTER_VALIDATE_URL) === false) { return false; } $parts = wp_parse_url($url); return is_array($parts) && strtolower((string) ($parts['scheme'] ?? '')) === 'https' && !empty($parts['host']) && empty($parts['user']) && empty($parts['pass']) && empty($parts['fragment']); } }