From 699c31e11a296623a0517025a304e81e28e2d34e Mon Sep 17 00:00:00 2001 From: Davinci9196 Date: Fri, 29 May 2026 17:44:54 +0800 Subject: [PATCH] Games: Added a new method to prevent login issues. --- .../org/microg/gms/auth/signin/extensions.kt | 4 +- .../org/microg/gms/games/GamesService.kt | 42 +++++++++++++------ .../gms/games/internal/IGamesCallbacks.aidl | 1 + .../gms/games/internal/IGamesService.aidl | 1 + 4 files changed, 33 insertions(+), 15 deletions(-) diff --git a/play-services-core/src/main/kotlin/org/microg/gms/auth/signin/extensions.kt b/play-services-core/src/main/kotlin/org/microg/gms/auth/signin/extensions.kt index f2d62ad334..05d689c8db 100644 --- a/play-services-core/src/main/kotlin/org/microg/gms/auth/signin/extensions.kt +++ b/play-services-core/src/main/kotlin/org/microg/gms/auth/signin/extensions.kt @@ -94,8 +94,8 @@ fun getServerAuthTokenManager(context: Context, packageName: String, options: Go val serverAuthTokenManager = AuthManager(context, account.name, packageName, "oauth2:server:client_id:${options.serverClientId}:api_scope:${options.scopeUris.joinToString(" ")}") serverAuthTokenManager.includeEmail = if (options.includeEmail) "1" else "0" serverAuthTokenManager.includeProfile = if (options.includeProfile) "1" else "0" - serverAuthTokenManager.forceRefreshToken = options.isForceCodeForRefreshToken - serverAuthTokenManager.setOauth2Prompt("auto") + serverAuthTokenManager.forceRefreshToken = true + serverAuthTokenManager.setOauth2Prompt(if (options.isForceCodeForRefreshToken) "consent" else "auto") serverAuthTokenManager.setItCaveatTypes("2") return serverAuthTokenManager } diff --git a/play-services-core/src/main/kotlin/org/microg/gms/games/GamesService.kt b/play-services-core/src/main/kotlin/org/microg/gms/games/GamesService.kt index cd30a1675b..e6bfd913f7 100644 --- a/play-services-core/src/main/kotlin/org/microg/gms/games/GamesService.kt +++ b/play-services-core/src/main/kotlin/org/microg/gms/games/GamesService.kt @@ -22,6 +22,7 @@ import androidx.core.os.bundleOf import androidx.lifecycle.Lifecycle import androidx.lifecycle.LifecycleOwner import androidx.lifecycle.lifecycleScope +import com.google.android.gms.auth.api.signin.GoogleSignInOptions import com.google.android.gms.common.ConnectionResult import com.google.android.gms.common.Scopes import com.google.android.gms.common.api.CommonStatusCodes @@ -51,6 +52,7 @@ import org.microg.gms.auth.AuthConstants import org.microg.gms.auth.AuthManager import org.microg.gms.auth.AuthPrefs import org.microg.gms.auth.signin.checkAccountAuthStatus +import org.microg.gms.auth.signin.getServerAuthTokenManager import org.microg.gms.common.Constants import org.microg.gms.common.GmsService import org.microg.gms.common.PackageUtils @@ -769,24 +771,38 @@ class GamesServiceImpl(val context: Context, override val lifecycle: Lifecycle, } override fun requestServerSideAccess(callbacks: IGamesCallbacks, serverClientId: String, forceRefreshToken: Boolean) { + Log.d(TAG, "requestServerSideAccess: $serverClientId $forceRefreshToken") + requestServerAuthCode(serverClientId, forceRefreshToken, emptyList()) { status, auth, _ -> + callbacks.onServerAuthCode(status, auth) + } + } + + override fun requestServerSideAccessForScopes(callbacks: IGamesCallbacks, serverClientId: String, forceRefreshToken: Boolean, scopes: List?) { + val requestedScopes = scopes.orEmpty() + Log.d(TAG, "requestServerSideAccessForScopes: $serverClientId $forceRefreshToken ${requestedScopes.joinToString(" ")}") + requestServerAuthCode(serverClientId, forceRefreshToken, requestedScopes) { status, auth, grantedScopes -> + callbacks.onServerAuthCodeWithScopes(status, auth, grantedScopes) + } + } + + private fun requestServerAuthCode(serverClientId: String, forceRefreshToken: Boolean, scopes: List, onResult: (Status, String?, List) -> Unit) { lifecycleScope.launchWhenStarted { try { - val serverAuthTokenResponse = withContext(Dispatchers.IO) { - val serverAuthTokenManager = AuthManager(context, account.name, packageName, "oauth2:server:client_id:${serverClientId}:api_scope:${Scopes.GAMES_LITE}") - serverAuthTokenManager.setOauth2Prompt(if (forceRefreshToken) "consent" else "auto") - serverAuthTokenManager.setItCaveatTypes("2") - serverAuthTokenManager.isPermitted = true - serverAuthTokenManager.invalidateAuthToken() - serverAuthTokenManager.requestAuthWithBackgroundResolution(true) - } - if (serverAuthTokenResponse.auth != null) { - callbacks.onServerAuthCode(Status(CommonStatusCodes.SUCCESS), serverAuthTokenResponse.auth) - } else { - callbacks.onServerAuthCode(Status(CommonStatusCodes.SIGN_IN_REQUIRED), null) + val options = GoogleSignInOptions.Builder().apply { + requestScopes(Scope(Scopes.GAMES_LITE)) + scopes.forEach { requestScopes(Scope(it)) } + requestServerAuthCode(serverClientId, forceRefreshToken) + }.build() + val response = getServerAuthTokenManager(context, packageName, options, account)?.let { + it.isPermitted = true + withContext(Dispatchers.IO) { it.requestAuthWithBackgroundResolution(true) } } + val auth = response?.auth + Log.d(TAG, "requestServerAuthCode result: auth=${auth != null} grantedScopes=${response?.grantedScopes} issueAdvice=${response?.issueAdvice}") + onResult(Status(if (auth != null) CommonStatusCodes.SUCCESS else CommonStatusCodes.SIGN_IN_REQUIRED), auth, if (auth != null) scopes else emptyList()) } catch (e: Exception) { Log.w(TAG, e) - runCatching { callbacks.onServerAuthCode(Status(CommonStatusCodes.INTERNAL_ERROR), null) } + runCatching { onResult(Status(CommonStatusCodes.INTERNAL_ERROR), null, emptyList()) } } } } diff --git a/play-services-games/src/main/aidl/com/google/android/gms/games/internal/IGamesCallbacks.aidl b/play-services-games/src/main/aidl/com/google/android/gms/games/internal/IGamesCallbacks.aidl index 5e317c1f0a..5cd0b369d9 100644 --- a/play-services-games/src/main/aidl/com/google/android/gms/games/internal/IGamesCallbacks.aidl +++ b/play-services-games/src/main/aidl/com/google/android/gms/games/internal/IGamesCallbacks.aidl @@ -49,4 +49,5 @@ interface IGamesCallbacks { void onResolveSnapshotHead(in DataHolder data, in Contents contents) = 12003; void commitSnapshotResult(in DataHolder data) = 12004; void onServerAuthCode(in Status status, String serverAuthCode) = 25002; + void onServerAuthCodeWithScopes(in Status status, String serverAuthCode, in List grantedScopes) = 25006; } diff --git a/play-services-games/src/main/aidl/com/google/android/gms/games/internal/IGamesService.aidl b/play-services-games/src/main/aidl/com/google/android/gms/games/internal/IGamesService.aidl index f5e4b88e2d..d11900d720 100644 --- a/play-services-games/src/main/aidl/com/google/android/gms/games/internal/IGamesService.aidl +++ b/play-services-games/src/main/aidl/com/google/android/gms/games/internal/IGamesService.aidl @@ -116,5 +116,6 @@ interface IGamesService { Intent getCompareProfileIntentWithAlternativeNameHints(String otherPlayerId, String otherPlayerInGameName, String currentPlayerInGameName) = 25015; void requestServerSideAccess(IGamesCallbacks callbacks, String serverClientId, boolean forceRefreshToken) = 27002; + void requestServerSideAccessForScopes(IGamesCallbacks callbacks, String serverClientId, boolean forceRefreshToken, in List scopes) = 27011; }