Skip to content

Commit 1fb9019

Browse files
feat(auth, android): Play Games provider sign-in support (#12201)
Co-authored-by: Mike Diarmid <[email protected]>
1 parent e34e072 commit 1fb9019

File tree

9 files changed

+120
-28
lines changed

9 files changed

+120
-28
lines changed

docs/auth/federated-auth.md

+19-27
Original file line numberDiff line numberDiff line change
@@ -91,37 +91,29 @@ Ensure the "Google" sign-in provider is enabled on the [Firebase Console](https:
9191
}
9292
```
9393

94-
## Google Play Games {:#games}
94+
## Google Play Games (Android only) {:#games}
9595

96-
You can authenticate users in your Android game using Play Games Sign-In.
96+
Ensure the "Play Games" sign-in provider is enabled on the [Firebase Console](https://console.firebase.google.com/project/_/authentication/providers).
97+
Follow these instructions for [Play Games Firebase project set-up](https://firebase.google.com/docs/auth/android/play-games#set-up-firebase-project).
9798

98-
* {Android}
99-
100-
Follow the instructions for Google setup on Android, then configure
101-
[Play Games services with your Firebase app information](https://firebase.google.com/docs/auth/android/play-games#configure-play-games-with-firebase-info).
102-
103-
The following will trigger the sign-in flow, create a new credential and sign in the user:
104-
105-
```dart
106-
final googleUser = await GoogleSignIn(
107-
signInOption: SignInOption.games,
108-
).signIn();
109-
110-
final googleAuth = await googleUser?.authentication;
111-
112-
if (googleAuth != null) {
113-
// Create a new credential
114-
final credential = GoogleAuthProvider.credential(
115-
accessToken: googleAuth.accessToken,
116-
idToken: googleAuth.idToken,
117-
);
118-
119-
// Once signed in, return the UserCredential
120-
await _auth.signInWithCredential(credential);
121-
}
122-
```
99+
Follow these [instructions for configuring Play Games services](https://firebase.google.com/docs/auth/android/play-games#configure-play-games-with-firebase-info)
100+
with your Firebase app.
123101

102+
* {Android}
124103

104+
```dart
105+
Future<void> _signInWithPlayGames() async {
106+
// Get server auth code from 3rd party provider
107+
// See PR description for details on how you might get the server auth code:
108+
// https://github.com/firebase/flutterfire/pull/12201#issue-2100392487
109+
final serverAuthCode = '...';
110+
final playGamesCredential = PlayGamesAuthProvider.credential(
111+
serverAuthCode: serverAuthCode);
112+
113+
await FirebaseAuth.instance
114+
.signInWithCredential(playGamesCredential);
115+
}
116+
```
125117

126118
## Facebook
127119

packages/firebase_auth/firebase_auth/android/src/main/java/io/flutter/plugins/firebase/auth/Constants.java

+2-1
Original file line numberDiff line numberDiff line change
@@ -19,7 +19,7 @@ public class Constants {
1919
public static final String SIGN_IN_METHOD_GITHUB = "github.com";
2020
public static final String SIGN_IN_METHOD_PHONE = "phone";
2121
public static final String SIGN_IN_METHOD_OAUTH = "oauth";
22-
22+
public static final String SIGN_IN_METHOD_PLAY_GAMES = "playgames.google.com";
2323
// User
2424
public static final String USER = "user";
2525
public static final String EMAIL = "email";
@@ -37,6 +37,7 @@ public class Constants {
3737
public static final String SIGN_IN_METHOD = "signInMethod";
3838
public static final String FORCE_RESENDING_TOKEN = "forceResendingToken";
3939
public static final String NAME = "name";
40+
public static final String SERVER_AUTH_CODE = "serverAuthCode";
4041

4142
// MultiFactor
4243
public static final String MULTI_FACTOR_HINTS = "multiFactorHints";

packages/firebase_auth/firebase_auth/android/src/main/java/io/flutter/plugins/firebase/auth/PigeonParser.java

+7
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,7 @@
2828
import com.google.firebase.auth.OAuthProvider;
2929
import com.google.firebase.auth.PhoneAuthProvider;
3030
import com.google.firebase.auth.PhoneMultiFactorInfo;
31+
import com.google.firebase.auth.PlayGamesAuthProvider;
3132
import com.google.firebase.auth.TwitterAuthProvider;
3233
import com.google.firebase.auth.UserInfo;
3334
import java.util.ArrayList;
@@ -226,6 +227,12 @@ static AuthCredential getCredential(Map<String, Object> credentialMap) {
226227

227228
return builder.build();
228229
}
230+
case Constants.SIGN_IN_METHOD_PLAY_GAMES:
231+
{
232+
String serverAuthCode =
233+
(String) Objects.requireNonNull(credentialMap.get(Constants.SERVER_AUTH_CODE));
234+
return PlayGamesAuthProvider.getCredential(serverAuthCode);
235+
}
229236
default:
230237
return null;
231238
}

packages/firebase_auth/firebase_auth/example/android/app/src/main/AndroidManifest.xml

+2
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,8 @@
1010
<meta-data
1111
android:name="com.facebook.sdk.ClientToken"
1212
android:value="@string/facebook_client_token" />
13+
<meta-data android:name="com.google.android.gms.games.APP_ID"
14+
android:value="@string/game_services_project_id"/>
1315
<activity
1416
android:name=".MainActivity"
1517
android:configChanges="orientation|keyboardHidden|keyboard|screenSize|smallestScreenSize|locale|layoutDirection|fontScale|screenLayout|density|uiMode"

packages/firebase_auth/firebase_auth/example/android/app/src/main/res/values/strings.xml

+3
Original file line numberDiff line numberDiff line change
@@ -3,4 +3,7 @@
33
<string name="facebook_app_id">128693022464535</string>
44
<!-- The Facebook client token should not be made public but this is a developer mode app with whitelisted user access -->
55
<string name="facebook_client_token">16dbbdf0cfb309034a6ad98ac2a21688</string>
6+
<!-- Default web client id for Play games -->
7+
<string name="default_web_client_id">406099696497-a12gakvts4epfk5pkio7dphc1anjiggc.apps.googleusercontent.com</string>
8+
<string translatable="false" name="game_services_project_id">406099696497</string>
69
</resources>

packages/firebase_auth/firebase_auth/lib/firebase_auth.dart

+2
Original file line numberDiff line numberDiff line change
@@ -39,6 +39,8 @@ export 'package:firebase_auth_platform_interface/firebase_auth_platform_interfac
3939
EmailAuthCredential,
4040
FacebookAuthProvider,
4141
FacebookAuthCredential,
42+
PlayGamesAuthProvider,
43+
PlayGamesAuthCredential,
4244
GithubAuthProvider,
4345
GithubAuthCredential,
4446
GoogleAuthProvider,

packages/firebase_auth/firebase_auth_platform_interface/lib/firebase_auth_platform_interface.dart

+1
Original file line numberDiff line numberDiff line change
@@ -36,6 +36,7 @@ export 'src/providers/phone_auth.dart';
3636
export 'src/providers/saml_auth.dart';
3737
export 'src/providers/twitter_auth.dart';
3838
export 'src/providers/yahoo_auth.dart';
39+
export 'src/providers/play_games_auth.dart';
3940
export 'src/types.dart';
4041
export 'src/user_info.dart';
4142
export 'src/user_metadata.dart';

packages/firebase_auth/firebase_auth_platform_interface/lib/src/providers/oauth.dart

+5
Original file line numberDiff line numberDiff line change
@@ -81,6 +81,7 @@ class OAuthCredential extends AuthCredential {
8181
this.idToken,
8282
this.secret,
8383
this.rawNonce,
84+
this.serverAuthCode,
8485
}) : super(
8586
providerId: providerId,
8687
signInMethod: signInMethod,
@@ -100,6 +101,9 @@ class OAuthCredential extends AuthCredential {
100101
/// must match the nonce field in the ID token.
101102
final String? rawNonce;
102103

104+
/// the server auth code for Play Games credential.
105+
final String? serverAuthCode;
106+
103107
@override
104108
Map<String, String?> asMap() {
105109
return <String, String?>{
@@ -109,6 +113,7 @@ class OAuthCredential extends AuthCredential {
109113
'accessToken': accessToken,
110114
'secret': secret,
111115
'rawNonce': rawNonce,
116+
'serverAuthCode': serverAuthCode,
112117
};
113118
}
114119
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,79 @@
1+
// Copyright 2024 The Chromium Authors. All rights reserved.
2+
// Use of this source code is governed by a BSD-style license that can be
3+
// found in the LICENSE file.
4+
5+
import 'package:firebase_auth_platform_interface/firebase_auth_platform_interface.dart';
6+
7+
const _kProviderId = 'playgames.google.com';
8+
9+
/// This class should be used to either create a new Play Games credential with an
10+
/// access code, or use the provider to trigger user authentication flows.
11+
///
12+
/// If authenticating with Play Games via a 3rd party, use the returned
13+
/// `serverAuthCode` to sign-in or link the user with the created credential,
14+
/// for example:
15+
///
16+
/// ```dart
17+
/// String serverAuthCode = '...'; // From 3rd party provider
18+
/// var playGamesAuthCredential = PlayGamesAuthCredential.credential(serverAuthCode: serverAuthCode);
19+
///
20+
/// FirebaseAuth.instance.signInWithCredential(playGamesAuthCredential)
21+
/// .then(...);
22+
/// ```
23+
class PlayGamesAuthProvider extends AuthProvider {
24+
/// Creates a new instance.
25+
PlayGamesAuthProvider() : super(_kProviderId);
26+
27+
/// Create a new [PlayGamesAuthCredential] from a provided [serverAuthCode]
28+
static OAuthCredential credential({
29+
required String serverAuthCode,
30+
}) {
31+
return PlayGamesAuthCredential._credential(
32+
serverAuthCode: serverAuthCode,
33+
);
34+
}
35+
36+
/// This corresponds to the sign-in method identifier.
37+
static String get PLAY_GAMES_SIGN_IN_METHOD {
38+
return _kProviderId;
39+
}
40+
41+
// ignore: public_member_api_docs
42+
static String get PROVIDER_ID {
43+
return _kProviderId;
44+
}
45+
46+
Map<String, String> _parameters = {};
47+
48+
/// Returns the parameters for this provider instance.
49+
Map<String, String> get parameters {
50+
return _parameters;
51+
}
52+
53+
/// Sets the OAuth custom parameters to pass in a Play Games OAuth request for
54+
/// popup and redirect sign-in operations.
55+
PlayGamesAuthProvider setCustomParameters(
56+
Map<String, String> customOAuthParameters,
57+
) {
58+
_parameters = customOAuthParameters;
59+
return this;
60+
}
61+
}
62+
63+
/// The auth credential returned from calling
64+
/// [PlayGamesAuthProvider.credential].
65+
class PlayGamesAuthCredential extends OAuthCredential {
66+
PlayGamesAuthCredential._({
67+
required String serverAuthCode,
68+
}) : super(
69+
providerId: _kProviderId,
70+
signInMethod: _kProviderId,
71+
serverAuthCode: serverAuthCode,
72+
);
73+
74+
factory PlayGamesAuthCredential._credential({
75+
required String serverAuthCode,
76+
}) {
77+
return PlayGamesAuthCredential._(serverAuthCode: serverAuthCode);
78+
}
79+
}

0 commit comments

Comments
 (0)