🐛 [firebase_dynamic_links] mode and oobCode not parsed from dynamic link - sendSignInLinkToEmail
Bug report
Describe the bug
Using the firebase auth sign in with email link sendSignInLinkToEmail, the link sent to user's email has its query params mode and oobCode, however when using firebase_dynamic_links onLink stream, I just get the path and no query params. mode and oobCode are required to signInWithEmailLink and verified with the isSignInWithEmailLink.
Steps to reproduce
Steps to reproduce the behavior:
- Follow basic implementation: https://firebase.google.com/docs/auth/flutter/email-link-auth and https://firebase.google.com/docs/dynamic-links/flutter/receive
Expected behavior
The received link from onLink stream of firebase_dynamic_links should contain the query params mode and oobCode for sign in with email link to work.
Sample project
Link from the mail sent to the user:
https://[#######].page.link/?link=https://[######].firebaseapp.com/__/auth/action?apiKey%3DAIzaSyAi9dbZpJeoSI8_NS[#########]%26mode%3DsignIn%26oobCode%3D2fhaxreC[##########]K6mAcjR-7Ou4KaovMmssUAAAGBNO_-lg%26continueUrl%3Dhttps://[########].page.link/BnhH%26lang%3Den&apn=com.[######].[######]_admin.dev&amv=19
resolves to:
https://[#########].firebaseapp.com/__/auth/action?apiKey=AIzaSyAi9dbZpJ[##########]c0VXsCYDgKxo&mode=signIn&oobCode=2fhaxre[#########]wzK6mAcjR-7Ou4KaovMmssUAAAGBNO_-lg&continueUrl=https://[########].page.link/BnhH&lang=en
then:
https://[#########].page.link/BnhH?apiKey=AIzaSyAi9db[########]sCYDgKxo&oobCode=2fhaxreCW[##########]zK6mAcjR-7Ou4KaovMmssUAAAGBNO_-lg&mode=signIn&lang=en
But I just get: https://[#########].page.link/BnhH on the following stream:
Stream<Uri> get onLink => _firebaseDynamicLinks.onLink.map(
(event) => event.link,
);
final isEmailLink = isSignInWithEmailLink(link); // THIS IS ALWAYS FALSE AS `mode` and `oobCode` ARE MISSING
if (isEmailLink) {
await signInWithEmailLink(email: email, link: link);
}
Additional context
Yes, I have seen #5530 and #4711 Same as #5913
Flutter doctor
Run flutter doctor and paste the output below:
Click To Expand
Doctor summary (to see all details, run flutter doctor -v):
[✓] Flutter (Channel stable, 3.0.1, on macOS 12.4 21F79 darwin-arm, locale es-PE)
[✓] Android toolchain - develop for Android devices (Android SDK version
32.1.0-rc1)
[✓] Xcode - develop for iOS and macOS (Xcode 13.3.1)
[✓] Chrome - develop for the web
[✓] Android Studio (version 2021.2)
[✓] IntelliJ IDEA Ultimate Edition (version 2022.1.1)
[✓] IntelliJ IDEA Ultimate Edition (version 2022.1.1)
[✓] VS Code (version 1.67.2)
[✓] Connected device (3 available)
[✓] HTTP Host Availability
• No issues found!
Flutter dependencies
Run flutter pub deps -- --style=compact and paste the output below:
Click To Expand
Dart SDK 2.17.1
Flutter SDK 3.0.1
meskbo_admin 1.0.0+1
dependencies:
- bloc 8.0.3 [meta]
- cloud_firestore 3.1.17 [cloud_firestore_platform_interface cloud_firestore_web collection firebase_core firebase_core_platform_interface flutter meta]
- firebase_auth 3.3.19 [firebase_auth_platform_interface firebase_auth_web firebase_core firebase_core_platform_interface flutter meta]
- firebase_core 1.17.1 [firebase_core_platform_interface firebase_core_web flutter meta]
- flutter 0.0.0 [characters collection material_color_utilities meta vector_math sky_engine]
- flutter_bloc 8.0.1 [flutter bloc provider]
- flutter_localizations 0.0.0 [flutter intl characters clock collection material_color_utilities meta path vector_math]
- freezed_annotation 2.0.3 [collection json_annotation meta]
- intl 0.17.0 [clock path]
- json_annotation 4.5.0 [meta]
- meskbo_core 1.0.0+1 [cloud_firestore firebase_analytics firebase_auth firebase_dynamic_links firebase_remote_config flutter flutter_facebook_auth freezed_annotation google_sign_in json_annotation sign_in_with_apple twitter_login]
- meskbo_ui 1.0.0+1 [flutter]
dev dependencies:
- bloc_test 9.0.3 [bloc diff_match_patch meta mocktail test]
- build_runner 2.1.11 [args async analyzer build build_config build_daemon build_resolvers build_runner_core code_builder collection crypto dart_style frontend_server_client glob graphs http_multi_server io js logging meta mime package_config path pool pub_semver pubspec_parse shelf shelf_web_socket stack_trace stream_transform timing watcher web_socket_channel yaml]
- flutter_test 0.0.0 [flutter test_api path fake_async clock stack_trace vector_math async boolean_selector characters charcode collection matcher material_color_utilities meta source_span stream_channel string_scanner term_glyph]
- freezed 2.0.3+1 [analyzer build build_config collection meta source_gen freezed_annotation json_annotation]
- json_serializable 6.2.0 [analyzer async build build_config collection json_annotation meta path pub_semver pubspec_parse source_gen source_helper]
- mocktail 0.3.0 [collection matcher test]
- very_good_analysis 3.0.0
transitive dependencies:
- _fe_analyzer_shared 40.0.0 [meta]
- analyzer 4.1.0 [_fe_analyzer_shared collection convert crypto glob meta package_config path pub_semver source_span watcher yaml]
- args 2.3.1
- async 2.8.2 [collection meta]
- boolean_selector 2.1.0 [source_span string_scanner]
- build 2.3.0 [analyzer async convert crypto glob logging meta path]
- build_config 1.0.0 [checked_yaml json_annotation path pubspec_parse yaml]
- build_daemon 3.1.0 [built_collection built_value http_multi_server logging path pool shelf shelf_web_socket stream_transform watcher web_socket_channel]
- build_resolvers 2.0.9 [analyzer async build crypto graphs logging path package_config pool pub_semver stream_transform yaml]
- build_runner_core 7.2.3 [async build build_config build_resolvers collection convert crypto glob graphs json_annotation logging meta path package_config pool timing watcher yaml]
- built_collection 5.1.1
- built_value 8.3.2 [built_collection collection fixnum meta]
- characters 1.2.0
- charcode 1.3.1
- checked_yaml 2.0.1 [json_annotation source_span yaml]
- clock 1.1.0
- cloud_firestore_platform_interface 5.5.7 [collection firebase_core flutter meta plugin_platform_interface]
- cloud_firestore_web 2.6.16 [cloud_firestore_platform_interface collection firebase_core firebase_core_web flutter flutter_web_plugins js]
- code_builder 4.1.0 [built_collection built_value collection matcher meta]
- collection 1.16.0
- convert 3.0.2 [typed_data]
- coverage 1.3.2 [args logging package_config path source_maps stack_trace vm_service]
- crypto 3.0.2 [typed_data]
- dart_style 2.2.3 [analyzer args path pub_semver source_span]
- diff_match_patch 0.4.1
- fake_async 1.3.0 [clock collection]
- file 6.1.2 [meta path]
- firebase_analytics 9.1.9 [firebase_analytics_platform_interface firebase_analytics_web firebase_core firebase_core_platform_interface flutter]
- firebase_analytics_platform_interface 3.1.7 [firebase_core flutter meta plugin_platform_interface]
- firebase_analytics_web 0.4.0+14 [firebase_analytics_platform_interface firebase_core firebase_core_web flutter flutter_web_plugins js]
- firebase_auth_platform_interface 6.2.7 [firebase_core flutter meta plugin_platform_interface]
- firebase_auth_web 3.3.16 [firebase_auth_platform_interface firebase_core firebase_core_web flutter flutter_web_plugins http_parser intl js meta]
- firebase_core_platform_interface 4.4.0 [collection flutter meta plugin_platform_interface]
- firebase_core_web 1.6.4 [firebase_core_platform_interface flutter flutter_web_plugins js meta]
- firebase_dynamic_links 4.2.5 [firebase_core firebase_core_platform_interface firebase_dynamic_links_platform_interface flutter meta plugin_platform_interface]
- firebase_dynamic_links_platform_interface 0.2.3+3 [firebase_core flutter meta plugin_platform_interface]
- firebase_remote_config 2.0.8 [firebase_core firebase_core_platform_interface firebase_remote_config_platform_interface firebase_remote_config_web flutter]
- firebase_remote_config_platform_interface 1.1.7 [firebase_core flutter meta plugin_platform_interface]
- firebase_remote_config_web 1.0.13 [firebase_core firebase_core_web firebase_remote_config_platform_interface flutter flutter_web_plugins js]
- fixnum 1.0.1
- flutter_facebook_auth 4.3.4 [flutter flutter_facebook_auth_platform_interface flutter_facebook_auth_web]
- flutter_facebook_auth_platform_interface 3.1.2 [flutter plugin_platform_interface]
- flutter_facebook_auth_web 3.1.2 [flutter flutter_web_plugins js flutter_facebook_auth_platform_interface]
- flutter_web_plugins 0.0.0 [flutter js characters collection material_color_utilities meta vector_math]
- frontend_server_client 2.1.3 [async path]
- glob 2.0.2 [async collection file path string_scanner]
- google_sign_in 5.3.2 [flutter google_sign_in_android google_sign_in_ios google_sign_in_platform_interface google_sign_in_web]
- google_sign_in_android 5.2.8 [flutter google_sign_in_platform_interface]
- google_sign_in_ios 5.3.1 [flutter google_sign_in_platform_interface]
- google_sign_in_platform_interface 2.1.3 [flutter quiver]
- google_sign_in_web 0.10.1+2 [flutter flutter_web_plugins google_sign_in_platform_interface js]
- graphs 2.1.0 [collection]
- http 0.13.4 [async http_parser meta path]
- http_multi_server 3.2.0 [async]
- http_parser 4.0.1 [collection source_span string_scanner typed_data]
- io 1.0.3 [meta path string_scanner]
- js 0.6.4
- logging 1.0.2
- matcher 0.12.11 [stack_trace]
- material_color_utilities 0.1.4
- meta 1.7.0
- mime 1.0.2
- nested 1.0.0 [flutter]
- node_preamble 2.0.1
- package_config 2.0.2 [path]
- path 1.8.1
- plugin_platform_interface 2.1.2 [meta]
- pool 1.5.0 [async stack_trace]
- provider 6.0.3 [collection flutter nested]
- pub_semver 2.1.1 [collection meta]
- pubspec_parse 1.2.0 [checked_yaml collection json_annotation pub_semver yaml]
- quiver 3.1.0 [matcher]
- shelf 1.3.0 [async collection http_parser path stack_trace stream_channel]
- shelf_packages_handler 3.0.0 [path shelf shelf_static]
- shelf_static 1.1.0 [convert http_parser mime path shelf]
- shelf_web_socket 1.0.1 [shelf stream_channel web_socket_channel]
- sign_in_with_apple 4.0.0 [flutter meta sign_in_with_apple_platform_interface sign_in_with_apple_web]
- sign_in_with_apple_platform_interface 1.0.0 [flutter plugin_platform_interface meta]
- sign_in_with_apple_web 1.0.1 [flutter flutter_web_plugins sign_in_with_apple_platform_interface js]
- sky_engine 0.0.99
- source_gen 1.2.2 [analyzer async build dart_style glob meta path source_span yaml]
- source_helper 1.3.2 [analyzer collection source_gen]
- source_map_stack_trace 2.1.0 [path stack_trace source_maps]
- source_maps 0.10.10 [source_span]
- source_span 1.8.2 [collection path term_glyph]
- stack_trace 1.10.0 [path]
- stream_channel 2.1.0 [async]
- stream_transform 2.0.0
- string_scanner 1.1.0 [charcode source_span]
- term_glyph 1.2.0
- test 1.21.1 [analyzer async boolean_selector collection coverage http_multi_server io js node_preamble package_config path pool shelf shelf_packages_handler shelf_static shelf_web_socket source_span stack_trace stream_channel typed_data web_socket_channel webkit_inspection_protocol yaml test_api test_core]
- test_api 0.4.9 [async boolean_selector collection meta source_span stack_trace stream_channel string_scanner term_glyph matcher]
- test_core 0.4.13 [analyzer async args boolean_selector collection coverage frontend_server_client glob io meta package_config path pool source_map_stack_trace source_maps source_span stack_trace stream_channel vm_service yaml matcher test_api]
- timing 1.0.0 [json_annotation]
- twitter_login 4.2.3 [flutter crypto http]
- typed_data 1.3.1 [collection]
- vector_math 2.1.2
- vm_service 8.3.0
- watcher 1.0.1 [async path]
- web_socket_channel 2.2.0 [async crypto stream_channel]
- webkit_inspection_protocol 1.1.0 [logging]
- yaml 3.1.1 [collection source_span string_scanner]
Thanks for the report. Keeping it open and labeling for further insights from the team.
/cc @russellwheatley
Hello. Have you already found a solution? Can I collaborate on something?
Hi @darshankawar Has there been any progress to address this issue? Thank you kindly.
/cc @russellwheatley
Hey @rcjuancarlosuwu, I'd be happy to look into this issue. Could you provide a repro app with the exact setup, please. No need to configure with a Firebase project, I'll use my own for testing. Thanks.
I am also facing the same issue. Its abit urgent on my side because of signing in breaking on my app. Please help
Hello @russellwheatley
This is a very similar issue with https://github.com/firebase/flutterfire/issues/4711
However that is fixes with Firebase_Auth for much earlier version
My issue isn't with getInitialLink() being null. Indeed my issue is also with android not ios.
This issue is with regards of
isSignInWithEmailLink always returning false below:
Click To Expand
Future<bool> isSignInWithEmail({String link}) async {
return _firebaseAuth.isSignInWithEmailLink(link);
}
Debugging process have all been great till calling this api that returns false no matter what.
Please help address this as this is causing my application business login logic to fails
Hello @russellwheatley @darshankawar
Anybody there?
@brijq As requested earlier here, please provide a complete minimal reproducible code sample so that the team can use it and address as applicable.
Function Logic
- Send Link to email upon user activation
Future<bool> sendSignInLinkToEmail(String email) async {
(await SharedPreferences.getInstance()).setString("auth_email", email);
final String packageId = await AppUtils.getPackageIdentifier();
String url;
url = "https://myurl/myurl";
try {
ActionCodeSettings actionCodeSettings = ActionCodeSettings(
url: url,
handleCodeInApp: true,
iOSBundleId: packageId,
androidPackageName: packageId,
androidInstallApp: false,
androidMinimumVersion: "23",
);
await FirebaseAuth.instance.sendSignInLinkToEmail(
email: email, actionCodeSettings: actionCodeSettings);
} catch (e) {
serviceLocator<AnalyticsService>()
.logError(name: "sendSignInLinkToEmail", detail: e.toString());
return false;
}
return true;
}
- Function to check and init Dynamic Link
void initDynamicLinks() async {
final PendingDynamicLinkData data =
await FirebaseDynamicLinks.instance.getInitialLink();
final Uri deepLink = data?.link;
if (deepLink?.toString() != null) {
if (await serviceLocator<AuthService>()
.isSignInWithEmail(link: deepLink.toString())) {
routingLogicDecision(deepLink.toString());
}
}
FirebaseDynamicLinks.instance.onLink.listen((dynamicLinkData) async {
final Uri deepLink = dynamicLinkData?.link;
if (deepLink?.toString() != null) {
var isSignInWithEmail =
await AuthService().isSignInWithEmail(link: deepLink?.toString());
if (isSignInWithEmail) {
routingLogicDecision(deepLink.toString());
} else {
Fluttertoast.showToast(
msg: 'There seems to be some error. Please try again');
}
}
}).onError((error) {
print('onLink error');
print(error.message);
});
}
- Check logic if isSignInWithEmailLink given is true
Future<bool> signInWith({String link}) async {
final String email =
(await SharedPreferences.getInstance()).getString("auth_email");
if (_firebaseAuth.isSignInWithEmailLink(link) && email != null) {
final UserCredential authResult = await _firebaseAuth.signInWithEmailLink(
email: email, emailLink: link);
serviceLocator<DeviceInfoService>().updateDeviceInfo();
return authResult.user != null;
}
return false;
}
- Helper function to check ( Problem now lies here! )
It was previously working ok with these set of versions
dependency_overrides:
firebase_core_platform_interface: 4.5.1
cloud_firestore: ^3.1.17
firebase_core: ^1.17.1
firebase_analytics: ^9.1.9
firebase_auth: ^3.3.19
firebase_crashlytics: ^2.8.1
firebase_messaging: ^11.4.1
firebase_performance: ^0.8.0+13
firebase_storage: ^10.2.17
firebase_dynamic_links: ^4.2.5
firebase_app_check: ^0.0.6+13
Future<bool> isSignInWithEmail({String link}) async {
return _firebaseAuth.isSignInWithEmailLink(link);
}
- Finally route base on outcome
void routingLogicDecision(String deepLink) async {
bool result =
await serviceLocator<AuthService>().signInWith(link: deepLink);
bool isUserProfileCreatedResult = await UserService.isUserProfileCreated();
if (result && !isUserProfileCreatedResult) {
Navigator.pushReplacementNamed(
context, AdditionalRequirementsScreen.routeName);
} else if (result && isUserProfileCreatedResult) {
Navigator.pushReplacementNamed(context, BaseScreen.routeName);
} else {
SnackBarBuilderUtils.buildSnackBar(context, "Failed to sign in");
}
}
Are you planning to resolve this issue? If not say so please.
@russellwheatley and @darshankawar can you please verify this is a real bug, or it's just some tricky setup missed in the parameter? This is one of the popular feature in Firebase and will impact the user experience a lot if it's missing in Flutter. Thanks!
@russellwheatley and @darshankawar can you please verify this is a real bug, or it's just some tricky setup missed in the parameter? This is one of the popular feature in Firebase and will impact the user experience a lot if it's missing in Flutter. Thanks!
To be honest, I have already did a fair share of testing myself. This is something that already specifically mentioned its a flutter auth library issue.
I have did some testing on IOS it seems fine. The problem lies on Android.
In Android, there is this settings > opening links > (your app) > Add link.
This needs to ensure that your firebase link need to be added manually.. Which obviously is still a very bad user experience.
However , that will only work if you use chrome to open up your email. Native email app will still be an issue..
I have already brought this issue more than 2 weeks ago and nobody bother to even respond.
@brijq @russellwheatley has already assigned himself on this issue, so he will come back to it. Usually team comes back to issues when they have finished tasks on which they are working currently and must be of high priority, so please have patience.
Wow.. Have been months and totally never hear a thing. 🤔
Hey @rcjuancarlosuwu, I've tested this and I received an oobCode & mode for android & iOS on both onLink & getInitialLink.
Are you sure you have it set correctly in the Firebase console template? In our template, we pass the code along like so:
https://flutterfire-e2e-tests.firebaseapp.com/__/auth/action?mode=action&oobCode=code
Hey @rcjuancarlosuwu, I've tested this and I received an
oobCode&modefor android & iOS on bothonLink&getInitialLink.Are you sure you have it set correctly in the Firebase console template? In our template, we pass the code along like so:
https://flutterfire-e2e-tests.firebaseapp.com/__/auth/action?mode=action&oobCode=code
Hello @russellwheatley
I have provided an sample below and not sure why is it being ignored.
Hi, @brijq, it isn't being ignored, you just have unnecessary code that won't effect the link in your sample. Here is an article on producing a reproduction: https://stackoverflow.com/help/minimal-reproducible-example. Read the part "Minimal and readable".
Hi, @brijq, it isn't being ignored, you just have unnecessary code that won't effect the link in your sample. Here is an article on producing a reproduction: https://stackoverflow.com/help/minimal-reproducible-example. Read the part "Minimal and readable".
hi @russellwheatley
Wow. Bravo. In case you do not know, that was the first respond in 2-3 months directed to me. As a result, I am not to sure how is that not being ignored?
In addition, bringing out that article is totally not needed.
Here is an article on basic etiquette: https://meta.stackexchange.com/questions/17447/answer-or-comment-whats-the-etiquette. Read the answers portion will be greatly appreciated.
If you do not wish to help out, you may say so. At least we can save each other's time.
I'm only trying to help you. Here is what happened when I copied your first function into my app:

Your sample is incomplete. No maintainer will help you if you don't provide a complete reproduction.
I'm only trying to help you. Here is what happened when I copied your first function into my app:
![]()
Your sample is incomplete. No maintainer will help you if you don't provide a complete reproduction.
Hello @russellwheatley
Apologies, I do not quite get it what do you mean incomplete?
If you are referring to those errors that you showed in your snippet,
await SharedPreferences.getInstance()).setString("auth_email", email) This can be replaced with just hardcoded '[email protected]'
Any email will do
final String packageId = await AppUtils.getPackageIdentifier(); This can be easily replaced with any package id 'com.sampleapp.example'
serviceLocator<AnalyticsService>() .logError(name: "sendSignInLinkToEmail", detail: e.toString()); Just remove this chunk for the time being.
Its just for testing purpose now yeah?
"Complete" just means I can run the code in its entirety without having to do any further work that isn't instructed (e.g. add dependencies).
I've already tested the API and it worked fine. The only difference between my code and yours (aside from the non Firebase APIs you're using), is the property androidInstallApp. In my test, it was set to true.
My sense is, if this was really a problem with the FlutterFire API, we'd have more people upvoting the issue. At this point, I can only presume it is something wrong with how you've set it up.
Hey @rcjuancarlosuwu. We need more information to resolve this issue but there hasn't been an update in 7 weekdays. I'm marking the issue as stale and if there are no new updates in the next 7 days I will close it automatically.
If you have more information that will help us get to the bottom of this, just add a comment!
"Complete" just means I can run the code in its entirety without having to do any further work that isn't instructed (e.g. add dependencies).
I've already tested the API and it worked fine. The only difference between my code and yours (aside from the non Firebase APIs you're using), is the property
androidInstallApp. In my test, it was set totrue.My sense is, if this was really a problem with the FlutterFire API, we'd have more people upvoting the issue. At this point, I can only presume it is something wrong with how you've set it up.
Hello,
Firstly this is topic is not created by me. Even so I let you know now you also seems to be extremely unhelpful.
I do not think this is providing any good experience. Anyway this is not surpising given no response over a month.
My sense is base on the respond you give, its not helping in anyway rather than pushing responsibilities away.
Its ok.
Hey @rcjuancarlosuwu. We need more information to resolve this issue but there hasn't been an update in 7 weekdays. I'm marking the issue as stale and if there are no new updates in the next 7 days I will close it automatically.
If you have more information that will help us get to the bottom of this, just add a comment!
"Complete" just means I can run the code in its entirety without having to do any further work that isn't instructed (e.g. add dependencies).
I've already tested the API and it worked fine. The only difference between my code and yours (aside from the non Firebase APIs you're using), is the property
androidInstallApp. In my test, it was set totrue.My sense is, if this was really a problem with the FlutterFire API, we'd have more people upvoting the issue. At this point, I can only presume it is something wrong with how you've set it up.
Hello,
Firstly this is topic is not created by me. Even so I let you know now you also seems to be extremely unhelpful.
I do not think this is providing any good experience. Anyway this is not surpising given no response over a month.
My sense is base on the respond you give, its not helping in anyway rather than pushing responsibilities away.
Its ok.
Since there haven't been any recent updates here, I am going to close this issue.
@rcjuancarlosuwu if you're still experiencing this problem and want to continue the discussion just leave a comment here and we are happy to re-open this.
I am surprise how this thread can be close without solving it. This is going viral