Flutter Provider: Provide 2 streams with one dependent on the other
The solution is to save the second stream (loggedInUserStream) in the state and change it whenever the first stream (authenticationStream) emits a new value (by listening to it) like in the code below:
class _FloatState extends State<Float> {
StreamSubscription<FirebaseUser> authenticationStreamSubscription;
Stream<User> loggedInUserStream;
StreamSubscription<FirebaseUser> setLoggedInUserStream() {
authenticationStreamSubscription =
FirebaseConnection.getAuthenticationStream().listen((firebaseUser) {
loggedInUserStream =
FirebaseConnection.getUserStream(uid: firebaseUser?.uid);
});
}
@override
void initState() {
super.initState();
authenticationStreamSubscription = setLoggedInUserStream();
}
@override
void dispose() {
super.dispose();
authenticationStreamSubscription.cancel();
}
@override
Widget build(BuildContext context) {
return StreamProvider<User>.value(
value: loggedInUserStream,
child: MaterialApp(
debugShowCheckedModeBanner: false,
initialRoute: LoginScreen.id,
onGenerateRoute: RouteGenerator.generateRoute,
),
);
}
}
I only needed the first stream (authenticationStream) to get the second one (loggedInUserStream) so I didn't provide it to the widgets below.
Isaak
Updated on December 16, 2022Comments
-
Isaak over 1 year
I'm using the provider package. In the root of the widget tree I have a multiprovider:
Widget build(BuildContext context) { return MultiProvider( providers: [ StreamProvider<FirebaseUser>.value( value: FirebaseConnection.getAuthenticationStream()), StreamProvider<User>.value( value: FirebaseConnection.getUserStream(uid: ???)) ], child: MaterialApp( debugShowCheckedModeBanner: false, initialRoute: LoginScreen.id, onGenerateRoute: RouteGenerator.generateRoute, ), ); }
The first StreamProvider provides the logged in user from firebase_auth. The second StreamProvider is supposed to provide additional information to that user (stored in the users collection). The problem is that to get the second stream I need the uid of the FirebaseUser provided with the first stream but I don't know how to access it.
Nesting the StreamProviders didn't work because in the second stream I can only access the (wrong) context of the build method (for Provider.of(context))