Google, Facebook Sign in support with Flutter - facebook

I am new to Flutter, Is there any way that i can provide Sign in using GOOGLE/FACEBOOK with Flutter.
Thanks

Adding this late answer since now there is a package, flutter_facebook_login that replaces flutter_facebook_connect. Here is a functioning main.dart example that should work. Just keep in mind you must have followed all configuration as described in the repository and must have a facebook app configured:
import 'package:flutter/material.dart';
import 'package:flutter_facebook_login/flutter_facebook_login.dart';
import 'dart:async';
void main() => runApp(new MyApp());
class MyApp extends StatelessWidget {
#override
Widget build(BuildContext context) {
return new MaterialApp(
title: 'Flutter Facebook Login',
theme: new ThemeData(
primarySwatch: Colors.blue,
),
home: new MyHomePage(title: 'Flutter Login Facebook'),
);
}
}
class MyHomePage extends StatefulWidget {
MyHomePage({Key key, this.title}) : super(key: key);
final String title;
#override
_MyHomePageState createState() => new _MyHomePageState();
}
class _MyHomePageState extends State<MyHomePage> {
login() async {
final facebookLogin = new FacebookLogin();
final result = await facebookLogin.logIn(['email']);
// final result = await facebookLogin.logInWithReadPermissions(['email']); --> Versions bellow 3.0
switch (result.status) {
case FacebookLoginStatus.loggedIn:
print(result.accessToken.token);
break;
case FacebookLoginStatus.cancelledByUser:
print('CANCELED BY USER');
break;
case FacebookLoginStatus.error:
print(result.errorMessage);
break;
}
}
#override
Widget build(BuildContext context) {
return new Scaffold(
appBar: new AppBar(
title: new Text(widget.title),
),
floatingActionButton: new FloatingActionButton(
onPressed: login,
tooltip: 'Login With Facebook',
child: new Icon(Icons.add),
),
);
}
}
You should see the login screen when clicking bottom right button, and check the printed response on your debug console:
This is the way to go right now since the package actually uses native Facebook Login SDKs on Android and iOS. So no excuse to use Firebase or having to interface yourself!
Hope it helps others who are having troubles with facebook login. And credits go to the package creator roughike
For google signin use google_sign_in, this package is actually quite mature and easier to get going.

As of Dec 2017, there is a Facebook Login Solution and also 1 for Facebook Login with Firebase to create a Facebook FirebaseUser. The initial Facebook Connect Login Package can be found # https://pub.dartlang.org/packages/flutter_facebook_connect
It requires the following webView package that redirects to Facebook's SignIn Page # https://pub.dartlang.org/packages/flutter_webview_plugin
And a custom button can be implemented like so...
final _facebookConnect = new FacebookConnect(
appId: '<APP_ID>',
clientSecret: '<CLIENT_SECRET');
FacebookOAuthToken token = await _facebookConnect.login();
The token can then be used with FirebaseAuth like so...
await FirebaseAuth.instance.signInWithFacebook(accessToken: null);
A few extra steps, but overall pretty straight forward execution. There's also a Firebase_Connect method to implement a FacebookLogin Button...
new FacebookLoginButton(
appId: '<APP_ID>',
clientSecret: '<CLIENT_SECRET>',
scope: [FacebookAuthScope.publicProfile],
onConnect: (api, token) {
...
}),
The Google Sign In is even easier. Simply add the Google_SignIn Package from https://pub.dartlang.org/packages/google_sign_in and add the following code to your custom Flutter button...
GoogleSignInAccount googleUser = await _googleSignIn.signIn();
GoogleSignInAuthentication googleAuth = await googleUser.authentication;
await FirebaseAuth.instance.signInWithGoogle(
idToken: googleAuth.idToken, accessToken: googleAuth.accessToken);

I don't think there is an implementation directly in Flutter Dart
But maybe by using a native implementation and communicate with Java/Swift code.
You can build your UI and trigger the native OAuth workflow from flutter.
https://github.com/flutter/flutter/tree/master/examples/hello_services

Google sign-in exists for Flutter via the google-sign-in package. Check out the Firebase for Flutter codelab for more info.
AFAIK, there isn't yet a Facebook sign-in package for Flutter (although one exists in Dart for the server side). Writing such a package should be an interesting exercise...

Related

Flutter : Replace LaunchUrl with WebView

Within my flutter app, I am launching a payment gateway using the url_launcher plugin with opens the page in a browser. However I would rather have it open in a WebView plugin instead, within the app.
Do I need to use both? how can implement such.
Please assist
Url launcher
if (selectedPaymentMethod == 'Pay Now' &&
_formKey.currentState!.validate()) {
() async {
final ozowApiRes = await OzowApiProvider()
.createPaymentRequest(
'R${(cart.totalAmount + cart.serviceFee + value * cart.newCylinderPrice).toStringAsFixed(0)}',
userData?['username'],
userData?['phoneNumber'],
userData?['email'],
);
() async {
try {
await launchUrl(
Uri.parse(ozowApiRes.data),
);
} catch (ex) {
throw 'Could not launch $ozowApiRes';
}
}();
}();
To do this, you can use url_launcher or flutter_inappwebview. I will recommend you to use flutter_inappwebview if possible cause url_launcher 100% not guaranteed you to launch in inAppWebView and also flutter_inappwebview gives you the granular controll in a page.
(1) you can use url_launcher with mode LaunchMode.inAppWebView
await launchUrl(
Uri.parse("https://www.google.com/"),
mode: LaunchMode.inAppWebView,
);
(2) or you can use a stateless widget page with flutter_inappwebview and just pass the purchase url
import 'package:flutter/material.dart';
import 'package:flutter_inappwebview/flutter_inappwebview.dart';
class InAppPurchasePage extends StatelessWidget {
const InAppPurchasePage({Key? key}) : super(key: key);
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: const Text("Purchase Page"),
),
body: InAppWebView(
initialUrlRequest: URLRequest(
url: Uri.parse(
"https://flutter.dev",
),
),
),
);
}
}

Flutter Stripe CardField not working in web

I am trying to get a CardField from the flutter_stripe package to appear on web. Simply with this code, a card field will display on ios and android. Though once I run on the app on Chrome, a blank line appears with the error, "Bad state: Source maps are not done loading".
I have the flutter_stripe and flutter_stripe_web package both installed and I cannot seem to figure this out. Any advice would be appreciated!
import 'package:flutter/material.dart';
import 'package:flutter_stripe/flutter_stripe.dart';
void main() {
runApp(const MyApp());
}
class MyApp extends StatefulWidget {
const MyApp({super.key});
#override
MyAppState createState() => MyAppState();
}
class MyAppState extends State<MyApp> {
CardFieldInputDetails? _card;
#override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Test',
home: Scaffold(
body: Column(
children: [
CardField(
cursorColor: Colors.black,
enablePostalCode: true,
countryCode: 'US',
postalCodeHintText: 'Enter the us postal code',
onCardChanged: (card) {
setState(() {
_card = card;
});
},
),
],
),
),
);
}
}
ios image
web image
Turns out I just needed to include Stripe.publishableKey = 'your publishable key' inside main()!
The flutter_stripe project only has limited, experimental support for the web right now. The maintainers recommend you use Stripe Checkout instead.
If you really want to get the CardField working on the web I was going to suggest you post an issue to the flutter_stripe repo, but it looks like you've already done so.

How to get back to app home page after successful login in Flutter

I'm trying to implement the user authentification into my Flutter app that is supposed to work for both Android and iOS.
I am using the JWT for the authentification of the app's request to the server, so I provide the user with a JWT token at login and the app saves the token securely on the device and then uses the token to communicate with my server.
When the app launches, I run the HomePage where there is a if statement where app looks to the secure storage for a JWT token if there is no token, the app shows the login page.
HomePage class:
class MyApp extends StatelessWidget {
#override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Flutter Demo',
theme: ThemeData(
primarySwatch: Colors.orange,
visualDensity: VisualDensity.adaptivePlatformDensity,
),
home: MyHomePage(title: 'App Title'),
routes: <String, WidgetBuilder>{
'/login': (BuildContext context) => new SignInPage(),
},
);
}
}
class MyHomePage extends StatefulWidget {
MyHomePage({Key key, this.title}) : super(key: key);
final String title;
#override
_MyHomePageState createState() => _MyHomePageState();
}
class _MyHomePageState extends State<MyHomePage> {
...
#override
Widget build(BuildContext context) {
storage.read(key: 'jwt_token').then((token) {
logger.d('MAIN APP GOT TOKEN: ' + token.toString());
if (token == null) {
Navigator.pushReplacementNamed(context, '/login');
}
});
return Scaffold(...);
}
}
I tried Navigator.pushReplacementNamed, Navigator.pushNamed, Navigator.popAndPushNamed... All of those get me to the login page. So that's fine. My problem is, that it doesn't work the other way around.
When I login sucessfully (obtain a JWT token), I can't make the app to return to the home page. If I restart the application it correctly shows the home page (as now there is a JWT in the secure storage), so the token check works fine. It must be something in rerouting from the login page to the home page.
login page snippet:
if (serverResponse.containsKey('jwt_token')) {
await storage.write(
key: 'jwt_token', value: serverResponse['jwt_token']);
Navigator.pushReplacementNamed(context, '/');
I tried also Navigator.pop and Navigator.pushNamed(context, '/'), Navigator.pushNamedAndRemoveUntil(context, '/', (route) => false), Navigator.pushReplacementNamed(context, '/'), non of which worked.
It looks like the page is changing, but it ends up being the login page again. I checked that the token is already inside the storage when the rerouting command is called. Also I have a debug message above the token check in the HomePage and the debug string is never printed after the login, so the Home page is simply not called at all.
Do you see something wrong in my code? How can I make it work?
The issue here is that you're checking the token on the home page build.
So every time you start the screen, and the user is not logged in, it's being redirected to the login page correctly.
However, since you've used the Navigator.pushReplacementNamed, which is removing the home from your routes list, then if you try any option to move back the routing list, like with Navigator.pop, there's no home anymore on the routes list.
So you basically have two options to deal with, according to the behavior you want:
1. Login page as default
This is the most common approach I've seen in practice, where your first app screen is the login one, so you only send with Navigator.pushReplacementNamed to /home after the login succeeds, replacing login with home, and providing the way to return to login screen through a Logout feature.
2. Refactor the login you're using for the token check
Instead of using a check on the build, I suggest using the initState, to check the session and redirect, so you have a more concise life cycle usage for redirecting. Just a thing I didn't understand, is that you didn't define in your / route. Even though they seem the same, I've seen already some issues related to that, because the home defines which view is started with the app, and the / defines the route mapping, so try that as well, just in case, to remove other variable, if that's the case (I personally only use named routes, to become clear code-wise where the users is being sent).
Follows one example that uses the Option 1, but uses the suggested on the Option 2 of using the initState:
class LoginScreen extends StatefulWidget {
#override
_LoginScreenState createState() => _LoginScreenState();
}
class _LoginScreenState extends State<LoginScreen> {
void checkPreviousSessionAndRedirect() async {
String loginToken = await LocalDb.getAttribute('loginToken');
if (loginToken != null) {
Navigator.pushNamedAndRemoveUntil(
context, RouteViews.MAIN, (Route<dynamic> route) => false);
}
}
void initState() {
super.initState();
checkPreviousSessionAndRedirect();
}
...
Hope that helps, and if it doesn't, please let me know if you have any question / issues.

How to generate Pre Launch report for Flutter App?

I have a login screen which uses phone authentication for creating account.
I have used Firebase Phone auth for login and also have stored one number for testing purpose.
But don't know how to pass the number and OTP to generate Pre Launch Report.
They are asking for Username, Username Resource ID, Password , Password Resource ID.
Where to find Resource ID for username and password fields in flutter code.
In the Google play console at the bottom of the left
Click on App content
Click on App access
Click on manage
Click on add new instructions
Add your all details here it should be test accounts
Try this :
dependencies:
flutter_runtime_env: ^0.0.4
Example:
import 'dart:async';
import 'package:flutter/material.dart';
import 'package:flutter_runtime_env/flutter_runtime_env.dart';
void main() => runApp(MyApp());
class MyApp extends StatefulWidget {
#override
_MyAppState createState() => _MyAppState();
}
class _MyAppState extends State<MyApp> {
bool _isInFirebaseTestLab = false;
#override
void initState() {
super.initState();
initPlatformState();
}
// Platform messages are asynchronous, so we initialize in an async method.
Future<void> initPlatformState() async {
var result = await inFirebaseTestLab();
setState(() {
_isInFirebaseTestLab = result;
});
}
#override
Widget build(BuildContext context) {
return MaterialApp(
home: Scaffold(
appBar: AppBar(
title: const Text('is in FirebaseTest Lab'),
),
body: Center(
child: Text('is in FirebaseTest Lab: $_isInFirebaseTestLab\n'),
),
),
);
}
}

Manage social user details in Google Flutter application

I am a beginner in developing Flutter application, and try to create a sample application for educational purpose. Last few weeks I decided to do a sample application in flutter that have no inbuilt login or register section because it's have social login options like Facebook and Google. I searched the web and got many code examples for how to implement Facebook and Google authentication in Flutter application.
I have a doubt about this social login implementation maybe it's happening because of lack of working experience in mobile application architecture level. At this point I am asking a question to myself "How to manage social login users in applications"
I have a solution like if the user can login ed successfully, store the user details into our (Firebase) db check the user email exists in database if there is no matching entries in db it will create a new user in database or if exists update the last login date time of that particular user. Because this application shows some user related data in other forms, it's work on the basis of logined userid, so I need to store the logined user details in the database.
Your proposed solution is good enough. The returned id is unique for your app.
Use the id returned to your app as the identifier for users in your app.
Checkout this answer on unique id
Just leaving the social_login plugin here
// Import package
import 'package:social_login/social_login.dart';
// Instantiate it
final socialLogin = SocialLogin();
//Before calling any methods, set the configuration
socialLogin.setConfig(SocialConfig(
facebookAppId: FACEBOOK_APP_ID,
googleWebClientId: GOOGLE_WEB_CLIENT_ID, /*In case a Google tokenId is needed*/
twitterConsumer: TWITTER_CONSUMER_KEY,
twitterSecret: TWITTER_CONSUMER_SECRET,
));
// Get current logged user
final FacebookUser facebookUser = await socialLogin.getCurrentFacebookUser();
final GoogleUser googleUser = await socialLogin.getCurrentGoogleUser();
final TwitterUser twitterUser = await socialLogin.getCurrentTwitterUser();
//Log in social networks
final FacebookUser facebookUser = await socialLogin.logInFacebookWithPermissions(FacebookPermissions.DEFAULT);
final GoogleUser googleUser = await socialLogin.logInGoogle();
final TwitterUser twitterUser = await socialLogin.logInTwitter();
//Log out from social networks
await socialLogin.logOutFacebook();
await socialLogin.logOutGoogle();
await socialLogin.logOutTwitter();
By using the built-in sign in using Firebase Authentication SDK (Official Guide), you will be able to obtain login information for different platforms like Google, Twitter, Facebook and even Github.
You do not need to code your own login/signup, everything is handle hassle free by using the right function from Firebase.
After that you will have the login information like so (this is from email login but Facebook, Google, Twitter and Github is available):
You can then link either the identifier or the User UID to the information in your database.
Oh and last but not least, do remember to set the persistence setting for the login provider to keep user login after they close their apps.
You should split Flutter app into 2 parts:
The "main" part of the app. It shows user related data.
Sign in/Sign up part.
The logic is quite simple. On the app start you check if the user is authenticated. If yes, navigate him to the main screen. If not, present him a sign up screen. Here's how it can be achieved using Firebase as a backend:
final currentUser = await FirebaseAuth.instance.currentUser();
if (currentUser != null){
// We're good: the user is authenticated.
// Show him the main screen.
Navigator.of(context).pushReplacement(MaterialPageRoute(
builder: (context) => HomeScreen()
));
} else {
// The user is not logged in.
// Show him the sign in/sign up screen.
Navigator.of(context).pushReplacement(MaterialPageRoute(
builder: (context) => SignInScreen()
));
}
Maybe this example meet your needs:
https://github.com/instaflutter/flutter-login-screen-firebase-auth-facebook-login
If you need some help to understand, i can help you!
you should go with the token logic (which is used by google and facebook).
you should generate a token to each user and store it in your data base . through this token you can mange every thing about the user .
when you call facebook authtinicating it will give you back a token for specific user .
this token when you send it again to facebook or google they will respond back with the details of the user .
so you can work like them .. create a token for the user and recall it for the info from your data base .. and you can store the token responded from facebook and match it in the future ..
the purpose of my answer to go and search for token concept cause it will give you a lot of benefits .
The idea is simple. The users get logged in with facebook/google/instagram and get an accessToken from the services mentioned above. This token has to be sent with each request that need authentication.
Use flutter storage to save the persist the token: https://pub.dev/packages/flutter_secure_storage
I will post you an example of one of my flutter app where I implemented the login with instagram.
Resuming the code below:
loginService.dart is responsible for login api calls and saving the token into the storage
main.dart is the first view of the app. Here if the user is not logged in the Login widget is shown ( the LoginWidget is in login.dart ).
login.dart is the view of the login page. There is a button that calls functions from LoginService class
Here's the code:
~/lib/service/loginService.dart
import 'dart:async';
import 'dart:convert' as JSON;
import 'package:http/http.dart' as http;
import 'package:flutter_webview_plugin/flutter_webview_plugin.dart';
import 'package:choose/model/User.dart';
import 'package:flutter_secure_storage/flutter_secure_storage.dart';
import 'package:choose/config.dart' as config;
String apiBaseUrl = config.apiBase;
String apiPort = config.port;
class LoginService {
String clientID;
String secretID;
String redirectURI;
final FlutterSecureStorage storage = new FlutterSecureStorage();
final String authKey = "token";
LoginService(this.clientID, this.secretID, this.redirectURI);
String get authenticationURI {
return "https://api.instagram.com/oauth/authorize/?client_id=$clientID&redirect_uri=$redirectURI&response_type=code";
}
String get authorizationURI {
return "https://api.instagram.com/oauth/access_token";
}
Future<User> authenticate() async {
clean();
FlutterWebviewPlugin _flutterWebviewPlugin = FlutterWebviewPlugin();
// Stream<String> onCode = await _openServer();
_flutterWebviewPlugin.launch(
authenticationURI
);
Completer<User> loginCompleter = Completer();
_flutterWebviewPlugin.onStateChanged.listen((viewState) async {
String url = viewState.url;
int indexOfCode = url.lastIndexOf("?code=");
if(url != null && indexOfCode >= 0 && viewState.type == WebViewState.finishLoad) {
String code = url.substring(url.indexOf('?code=') + 6, url.length);
http.Response userResponse = await http.get(
"${config.endpoints['getUserByCode']}?code=$code",
);
if(userResponse.statusCode == 200) {
User user = User.fromMap(JSON.jsonDecode(userResponse.body));
saveToken(user.token);
loginCompleter.complete(user);
} else {
loginCompleter.completeError("User not found");
}
_flutterWebviewPlugin.close();
}
});
return loginCompleter.future;
}
void saveToken(token) async {
storage.write(key: authKey, value: token);
}
void clean() async {
storage.delete(key: authKey);
}
Future<String> getToken() async {
return storage.read(key: authKey);
}
static Future<String> getStaticToken() async {
FlutterSecureStorage storage = FlutterSecureStorage();
return storage.read(key: "token");
}
}
~lib/main.dart
import 'package:choose/friends.dart';
import 'package:choose/model/User.dart';
import 'package:flutter/material.dart';
import 'package:choose/login.dart';
import 'package:choose/service/loginService.dart';
import 'package:web_socket_channel/io.dart';
import 'feed.dart';
import 'notification.dart';
import 'newPost.dart';
import 'config.dart' as config;
void main() => runApp(MyApp());
LoginService loginService = new LoginService(
"71b818abd18043fb8b7c1833912b62ae",
"3d9d6f87d2354085a74534c13bdda51f",
config.endpoints['authorize'],
);
class MyApp extends StatelessWidget {
// This widget is the root of your application.
#override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Flutter Demo',
theme: ThemeData(
// This is the theme of your application.
//
// Try running your application with "flutter run". You'll see the
// application has a blue toolbar. Then, without quitting the app, try
// changing the primarySwatch below to Colors.green and then invoke
// "hot reload" (press "r" in the console where you ran "flutter run",
// or simply save your changes to "hot reload" in a Flutter IDE).
// Notice that the counter didn't reset back to zero; the application
// is not restarted.
primarySwatch: Colors.blue,
),
home: MyHomePage(title: 'Flutter Demo Home Page'),
routes: {
'/feed': (context) => DefaultTabController(
length: 2,
child: FeedWidget()
),
'/newpost': (context) => NewPost(),
'/notifications': (context) => NotificationWidget(
channel: IOWebSocketChannel.connect(config.websocketURI)
),
'/friends': (context) => FriendsWidget(),
}
);
}
}
class MyHomePage extends StatefulWidget {
MyHomePage({Key key, this.title}) : super(key: key);
// This widget is the home page of your application. It is stateful, meaning
// that it has a State object (defined below) that contains fields that affect
// how it looks.
// This class is the configuration for the state. It holds the values (in this
// case the title) provided by the parent (in this case the App widget) and
// used by the build method of the State. Fields in a Widget subclass are
// always marked "final".
final String title;
#override
_MyHomePageState createState() => _MyHomePageState();
}
class _MyHomePageState extends State<MyHomePage> {
User user;
String label = 'Continue with Instagram';
void openLoginPage() async {
try {
User _user = await loginService.authenticate();
this.openPostPage();
} catch(e) {
this.setState(() {
label = 'Try Again';
});
}
}
void openPostPage() async {
print(await loginService.getToken());
print("token");
Navigator.pushReplacementNamed(context, '/feed');
}
void actionDelegator() {
if(user != null) {
return openPostPage();
} else {
return openLoginPage();
}
}
#override
Widget build(BuildContext context) {
// This method is rerun every time setState is called, for instance as done
// by the _incrementCounter method above.
//
// The Flutter framework has been optimized to make rerunning build methods
// fast, so that you can just rebuild anything that needs updating rather
// than having to individually change instances of widgets.
return Login(loginAction: actionDelegator, user: user, label: label);
}
}
~/lib/service/login.dart
import 'package:flutter/material.dart';
import 'package:font_awesome_flutter/font_awesome_flutter.dart';
import 'package:choose/model/User.dart';
class Login extends StatefulWidget {
Login({this.loginAction, this.user, this.label});
final loginAction;
final User user;
final String label;
_Login createState() => _Login();
}
class _Login extends State<Login> {
String imageURI = "https://www.travelcontinuously.com/wp-content/uploads/2018/04/empty-avatar.png";
#override
Widget build(BuildContext context) {
if(widget.user != null && widget.user.profilePicture != '' ) {
imageURI = widget.user.profilePicture;
}
return Container (
color: Colors.green,
child: Column (
crossAxisAlignment: CrossAxisAlignment.center,
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
CircleAvatar (
backgroundColor: Colors.transparent,
radius: 50.0,
backgroundImage: NetworkImage(imageURI, scale: 2.0),
),
Container(
padding: EdgeInsets.all(0.0),
margin: EdgeInsets.all(20.0),
color: Colors.transparent,
child: MaterialButton(
elevation: 5.0,
color: Color.fromRGBO(193, 53, 132, 1.0),
child: FlatButton.icon(
label: Text(widget.label, style: TextStyle(color: Color.fromRGBO(255,220,128, 1.0), fontWeight: FontWeight.w900, fontSize: 16.0)),
icon: Icon(FontAwesomeIcons.instagram, color: Color.fromRGBO(255,220,128, 1.0)),
),
onPressed: () async {
widget.loginAction();
},
)
)
],
),
);
}
}
(Someone might find this helpful). For easy oauth in flutter, Try visa - https://github.com/e-oj/visa
Here's an example with Facebook auth (It also supports google, twitch, discord, and Github):
import 'package:visa/auth-data.dart';
import 'package:visa/fb.dart';
class AuthPage extends StatelessWidget {
#override
Widget build(BuildContext context) {
return Scaffold(
/// Simply Provide all the necessary credentials
body: FaceBookAuth().visa.authenticate(
clientID: '139732240983759',
redirectUri: 'https://www.e-oj.com/oauth',
scope: 'public_profile,email',
state: 'fbAuth',
onDone: done
)
);
}
}
and the "done" callback:
done(AuthData authData){
print(authData);
/// You can pass the [AuthData] object to a
/// post-authentication screen. It contaions
/// all the user and OAuth data collected during
/// the authentication process. In this example,
/// our post-authentication screen is "complete-profile".
Navigator.pushReplacementNamed(
context, '/complete-profile', arguments: authData
);
}