优化google.rs

This commit is contained in:
李运家 2025-01-23 14:15:19 +08:00
parent 9bdbe32311
commit 139536924d

View File

@ -31,6 +31,13 @@ pub struct GoogleSocial {
// 假设GOOGLE_PUBLIC_CERT_URL是Google提供的公钥URL
const GOOGLE_PUBLIC_CERT_URL: &str = "https://www.googleapis.com/oauth2/v3/certs";
// Google OAuth2 相关常量
const GOOGLE_AUTH_URL: &str = "https://accounts.google.com/o/oauth2/v2/auth";
const GOOGLE_TOKEN_URL: &str = "https://oauth2.googleapis.com/token";
const GOOGLE_REVOCATION_URL: &str = "https://oauth2.googleapis.com/revoke";
const GOOGLE_GAMES_SCOPE: &str = "https://www.googleapis.com/auth/games";
const GOOGLE_PROFILE_SCOPE: &str = "https://www.googleapis.com/auth/userinfo.profile";
#[derive(Debug, Default, Deserialize)]
pub struct GoogleJwtProfile {
// iss (issuer):签发人
@ -186,61 +193,41 @@ impl GoogleSocial {
// 1. 创建 OAuth2 client
let client = BasicClient::new(ClientId::new(config!().social.google.client_id.clone()))
.set_client_secret(ClientSecret::new(config!().social.google.client_secret.clone()))
.set_auth_uri(AuthUrl::new(
"https://accounts.google.com/o/oauth2/v2/auth".to_string(),
)?)
.set_token_uri(TokenUrl::new(
"https://oauth2.googleapis.com/token".to_string(),
)?)
.set_redirect_uri(RedirectUrl::new(
"http://localhost:8080/auth/google/callback".to_string(),
)?)
.set_auth_uri(AuthUrl::new(GOOGLE_AUTH_URL.to_string())?)
.set_token_uri(TokenUrl::new(GOOGLE_TOKEN_URL.to_string())?)
// Google supports OAuth 2.0 Token Revocation (RFC-7009)
.set_revocation_url(
RevocationUrl::new("https://oauth2.googleapis.com/revoke".to_string())
RevocationUrl::new(GOOGLE_REVOCATION_URL.to_string())
.expect("Invalid revocation endpoint URL"),
);
// Google supports Proof Key for Code Exchange (PKCE - https://oauth.net/2/pkce/).
// Create a PKCE code verifier and SHA-256 encode it as a code challenge.
let (pkce_code_challenge, pkce_code_verifier) = PkceCodeChallenge::new_random_sha256();
// Generate the authorization URL to which we'll redirect the user.
let (_authorize_url, _csrf_state) = client
.authorize_url(CsrfToken::new_random)
// This example is requesting access to the "calendar" features and the user's profile.
.add_scope(Scope::new(
"https://www.googleapis.com/auth/calendar".to_string(),
))
.add_scope(Scope::new(
"https://www.googleapis.com/auth/plus.me".to_string(),
))
.set_pkce_challenge(pkce_code_challenge)
.url();
// 2. 执行 token exchange
let token_response = client
.exchange_code(AuthorizationCode::new(play_games_token.to_string()))
.set_pkce_verifier(pkce_code_verifier)
.request_async(&reqwest::Client::new())
.await?;
let access_token = token_response.access_token();
// 3. 使用新的 access token 获取用户信息
// 3. 获取用户信息和额外信息
let mut profile = self.fetch_play_games_profile(access_token.secret()).await?;
// 4. 获取额外的用户信息(如果需要)
if let Some(additional_info) = self
.fetch_additional_player_info(access_token.secret())
.await?
{
profile.google_play_games_profile = Some(serde_json::to_string(&additional_info)?);
}
self.enrich_profile_with_additional_info(&mut profile, access_token.secret()).await?;
Ok(profile)
}
/// 使用额外信息丰富用户资料
async fn enrich_profile_with_additional_info(
&self,
profile: &mut GoogleJwtProfile,
access_token: &str,
) -> SocialResult<()> {
if let Some(additional_info) = self.fetch_additional_player_info(access_token).await? {
profile.google_play_games_profile = Some(serde_json::to_string(&additional_info)?);
}
Ok(())
}
/// 获取 Google Play Games 用户资料
async fn fetch_play_games_profile(&self, access_token: &str) -> SocialResult<GoogleJwtProfile> {
const PLAY_GAMES_PROFILE_URL: &str = "https://games.googleapis.com/games/v1/players/me";