I am doing an app in flutter and I am working on the authentication part. I want to know how I can keep my user logged in after I reload the app. Now the thing is that my app has 2 kinds of users (Client and Driver). So each has its own space, like sign in and sign up and main (after logging in). This is the code that I used for logging.
class Initializer extends StatefulWidget {
// Access to this Screen
static String id = 'initializer';
@override
_InitializerState createState() => _InitializerState();
}
class _InitializerState extends State<Initializer> {
// Firebase Stuff
final _auth = FirebaseAuth.instance;
final FirebaseFirestore _firestore = FirebaseFirestore.instance;
User _user;
// To Check if There's a Driver
bool isDriver = true;
void getCurrentUser() async {
try {
final getCurrentUser = _auth.currentUser;
if (getCurrentUser != null) {
getUserKind();
_user = getCurrentUser;
}
} catch (e) {
print(e);
}
}
getUserKind() async {
try {
// To fetch Database for Driver
final QuerySnapshot checkOfDriver =
await _firestore.collection('driver').where('uid', isEqualTo: _user.uid).get().catchError((error) {
print(error);
});
if (checkOfDriver.docs.isEmpty)
setState(() {
isDriver = false;
});
else
setState(() {
isDriver = true;
});
} catch (e) {
print(e);
return null;
}
}
@override
void setState(fn) {
if (mounted) {
super.setState(fn);
}
}
@override
void initState() {
super.initState();
getCurrentUser();
}
@override
Widget build(BuildContext context) {
getCurrentUser();
SizeConfig().init(context);
return _user == null
? WelcomeScreen()
: isDriver
? DriverMain()
: ClientMain();
}
}
It's actually working but not properly, because when I reload the app while I'm logging in as a Client, the app shows me DriverMain at the beginning for one second then it switches to the right side which is ClientMain and that causes me some errors sometimes, and it's not an efficient work anyway.
So, what I should add to the code or ...
Firebase already persists the users credentials, and restores them automatically when the app restarts.
But this is an asynchronous process, as it requires a call to the server. By the time your
getCurrentUser = _auth.currentUser
code runs, that asynchronous process hasn't finished yet, so you getnull
.To properly respond to the auth state being restored (and other changes), you'll want to use an auth state change listener as shown in the documentation on authentication state:
If you want to use this in your UI, you'll typically wrap it in a
StreamBuilder
instead of callinglisten
yourself.