firebase-ios-sdk
firebase-ios-sdk copied to clipboard
Auth.auth().canHandleNotification always returns false
Description
Hi,
the issue is Auth.auth().canHandleNotification(...) always returning false and I cannot verify phone auth. I followed the docs and my App Delegate looks as follows:
class AppDelegate: NSObject, UIApplicationDelegate, MessagingDelegate, UNUserNotificationCenterDelegate {
func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey : Any]? = nil) -> Bool {
FirebaseApp.configure()
UNUserNotificationCenter.current().delegate = self
NotificationService().requestAuthorization()
application.registerForRemoteNotifications()
Messaging.messaging().delegate = self
return true
}
func application(_ application: UIApplication, didRegisterForRemoteNotificationsWithDeviceToken deviceToken: Data) {
Messaging.messaging().apnsToken = deviceToken
Auth.auth().setAPNSToken(deviceToken, type: .prod)
}
func application(_ application: UIApplication, didReceiveRemoteNotification userInfo: [AnyHashable : Any], fetchCompletionHandler completionHandler: @escaping (UIBackgroundFetchResult) -> Void) {
let firebaseAuth = Auth.auth()
Messaging.messaging().appDidReceiveMessage(userInfo)
print(userInfo)
if Auth.auth().canHandleNotification(userInfo) {
completionHandler(.noData)
}
completionHandler(.noData)
}
func messaging(_ messaging: Messaging, didReceiveRegistrationToken fcmToken: String?) {
Messaging.messaging().token { token, error in
if let error {
log.error("failed to fetch FCM registration token \(error)")
} else if let token {
print("fcm \(token)")
print(token)
}
}
}
func application(_ app: UIApplication, open url: URL, options: [UIApplication.OpenURLOptionsKey : Any] = [:]) -> Bool {
if Auth.auth().canHandle(url) {
return true
}
return false
}
}
push notifications are enables background refresh and remote notifications enabled sizzling is disabled.
Reproducing the issue
No specific steps needed
Firebase SDK Version
10.29.0
Xcode Version
15.3
Installation Method
Swift Package Manager
Firebase Product(s)
Authentication
Targeted Platforms
iOS
Relevant Log Output
the notification prints out:
[AnyHashable("com.google.firebase.auth"): {
warning = "This fake notification should be forwarded to Firebase Auth.";
}]
Error Domain=FIRAuthErrorDomain Code=17054 "If app delegate swizzling is disabled, remote notifications received by UIApplicationDelegate need to be forwarded to FIRAuth's canHandleNotificaton: method." UserInfo={NSLocalizedDescription=If app delegate swizzling is disabled, remote notifications received by UIApplicationDelegate need to be forwarded to FIRAuth's canHandleNotificaton: method., FIRAuthErrorUserInfoNameKey=ERROR_NOTIFICATION_NOT_FORWARDED}
If using Swift Package Manager, the project's Package.resolved
Expand Package.resolved snippet
Replace this line with the contents of your Package.resolved.
If using CocoaPods, the project's Podfile.lock
Expand Podfile.lock snippet
Replace this line with the contents of your Podfile.lock!
I couldn't figure out how to label this issue, so I've labeled it for a human to triage. Hang tight.
Update: this code sometimes works for test phone numbers, but sometimes does not. Any help?
Hi @lukavujnovac, do you have the Background Modes capability enabled? If so, ensure that the Background fetch and Remote notifications modes are selected.
Hi @lukavujnovac, do you have the Background Modes capability enabled? If so, ensure that the Background fetch and Remote notifications modes are selected.
Hey @ncooke3, yes I do, I have background fetch, remote notifications and background processing all selected under background modes
Hi @lukavujnovac, I tried to reproduce the issue and I got the same behavior. I've raised this to our engineering team to investigate what's causing the issue. Thanks.
Hi @lukavujnovac, I tried to reproduce the issue and I got the same behavior. I've raised this to our engineering team to investigate what's causing the issue. Thanks.
hey @rizafran this code works a few times if I set AuthAPNSTokenType to unknown. After a while I get the same error as above, is it possible it's to prevent spam? I have a paid firebase account which should allow up to 1000 SMSs a day.
Hi @lukavujnovac, the APNS token type should be .unknown. This will allow the SDK to infer whether the APNS token is a production or a sandbox token based on the environment. I'm going to update our docs accordingly.
When making this change, are you seeing any cases where Auth.auth().canHandleNotification is not working correctly or is this part fixed by switching to .unknown?
Unrelated, but I noticed in your shared snippet that there was a path that calls the completion handler twice. I'm not sure if this could have any side effects in Apple's code, but it may be better to add a return after the first one.
if Auth.auth().canHandleNotification(userInfo) { completionHandler(.noData) } completionHandler(.noData)
Hi @lukavujnovac, the APNS token type should be
.unknown. This will allow the SDK to infer whether the APNS token is a production or a sandbox token based on the environment. I'm going to update our docs accordingly.When making this change, are you seeing any cases where
Auth.auth().canHandleNotificationis not working correctly or is this part fixed by switching to.unknown?Unrelated, but I noticed in your shared snippet that there was a path that calls the completion handler twice. I'm not sure if this could have any side effects in Apple's code, but it may be better to add a return after the first one.
if Auth.auth().canHandleNotification(userInfo) {
completionHandler(.noData)}completionHandler(.noData)
hi @ncooke3, that part is partly fixed by using the .unknown. As stated above, code works for a few times before receiving the same error. Could this be some spam protection? I do have a paid firebase account which should allow me up to 1000 SMSs a day. Thanks for the tip!
Could this be some spam protection?
I don't think so. When the quota is reached, I wouldn't expect to see the Error Domain=FIRAuthErrorDomain Code=17054 "If app delegate swizzling is disabled... error, instead you'll see another error like error code 17052.
When you encounter the "If app delegate swizzling is disabled... error, does the reCAPTCHA flow get presented?
When the test notification is fired, it must be intercepted in a certain amount of time. If you are using the debugger and pausing at breakpoints, it's possible that it may the timeout may be reached. Do you happen to be using the debugger when the error occurs?
Could this be some spam protection?
I don't think so. When the quota is reached, I wouldn't expect to see the
Error Domain=FIRAuthErrorDomain Code=17054 "If app delegate swizzling is disabled...error, instead you'll see another error like error code 17052.When you encounter the
"If app delegate swizzling is disabled...error, does the reCAPTCHA flow get presented?When the test notification is fired, it must be intercepted in a certain amount of time. If you are using the debugger and pausing at breakpoints, it's possible that it may the timeout may be reached. Do you happen to be using the debugger when the error occurs?
@ncooke3 reCAPTCHA flow only gets triggered if I test on a simulator, and I am unable to proceed with phone auth on the simulator after that, I don't know if that's a separate issue or intended behavior. Every day this code works about 3-5 times, after that I get the error listed above. There are no other changes in the environment, everything is the same for working and non-working cases, but I could not find any differences. If needed, I can give you more info about the project and the firebase console setup.
Thanks, @lukavujnovac. I was able to reproduce this behavior but I was not able to pinpoint what's going wrong. The first few logins were successful, then I got the "If app delegate swizzling is disabled... error, and when I stopped getting that, I got an error that my device had been blocked temporarily.
Thanks, @lukavujnovac. I was able to reproduce this behavior but I was not able to pinpoint what's going wrong. The first few logins were successful, then I got the
"If app delegate swizzling is disabled...error, and when I stopped getting that, I got an error that my device had been blocked temporarily.
Are there any workarounds for this currently? This is currently a release blocker for me. If you need any additional info from me to help debug lmk.
The only possible workaround may be to enable swizzling, but I understand that may be infeasible depending on your requirements. While setting the APNS type to .unknown is only a partial fix, this remaining problem is hopefully rare in practice since it seems to be only appear after multiple login attempts.
Any update on this issue ?
Any update on this issue ?
@JeremyCorchia no, if you are facing the issue set the APNs environment to .unknown, or setup both development and production APNs in the Firebase console.
Closing due to inactivity. If this remains an issue on the latest major version of Firebase, please let me know and I'm happy to reopen.