Firebase-ios-sdk: Auth crash -[FIRAuth fetchSignInMethodsForEmail:completion:]

Created on 28 Dec 2019  路  10Comments  路  Source: firebase/firebase-ios-sdk

  • Xcode version: 11.3
  • Firebase SDK version: 6.13.0
  • Firebase Component: Auth
  • Component version: 6.4.0 (per Podfile.lock)

[REQUIRED] Step 3: Describe the problem

Crash on iOS when calling fetchSignMethodsForEmail

Seen on

  • 13.1.3 (17A878) iPhone XR
  • 12.4.0 (16G77) iPhone 8 Plus
Fatal Exception: NSInvalidArgumentException
0  CoreFoundation                 0x1a9f01c30 __exceptionPreprocess
1  libobjc.A.dylib                0x1a9c1c0c8 objc_exception_throw
2  CoreFoundation                 0x1a9f5a5f4 -[__NSCFString characterAtIndex:].cold.1
3  CoreFoundation                 0x1a9f64414 -[__NSPlaceholderDictionary initWithObjects:forKeys:count:].cold.5
4  CoreFoundation                 0x1a9de85f0 -[__NSPlaceholderDictionary initWithObjects:forKeys:count:]
5  CoreFoundation                 0x1a9dd9e9c +[NSDictionary dictionaryWithObjects:forKeys:count:]
6  KScoreApp                      0x104fae4e8 -[FIRCreateAuthURIRequest unencodedHTTPRequestBodyWithError:] + 75 (FIRCreateAuthURIRequest.m:75)
7  KScoreApp                      0x104fa4ac4 -[FIRAuthBackendRPCImplementation postWithRequest:response:callback:] + 833 (FIRAuthBackend.m:833)
8  KScoreApp                      0x104fa3600 -[FIRAuthBackendRPCImplementation createAuthURI:callback:] + 600 (FIRAuthBackend.m:600)
9  KScoreApp                      0x104fa2778 +[FIRAuthBackend createAuthURI:callback:] + 441 (FIRAuthBackend.m:441)
10 KScoreApp                      0x104f99068 __49-[FIRAuth fetchSignInMethodsForEmail:completion:]_block_invoke + 530 (FIRAuth.m:530)
11 libdispatch.dylib              0x1a9ba7bb0 _dispatch_call_block_and_release
12 libdispatch.dylib              0x1a9ba900c _dispatch_client_callout
13 libdispatch.dylib              0x1a9baf484 _dispatch_lane_serial_drain
14 libdispatch.dylib              0x1a9bafeb0 _dispatch_lane_invoke
15 libdispatch.dylib              0x1a9bb8f20 _dispatch_workloop_worker_thread
16 libsystem_pthread.dylib        0x1a9c0eaa0 _pthread_wqthread
17 libsystem_pthread.dylib        0x1a9c14c78 start_wqthread

Steps to reproduce:

What happened? How can we make the problem occur?

Hard to say, it appears to be medium-rare. But during my social auth sign-in flow, if it is the first time this account has been seen I first check if the email returned by the social auth sign-in is in use already before auto-registering.

It appears this can crash

Relevant Code:

It's using react-native-firebase (I'm a maintainer there) so the code won't appear relevant, but I don't believe a native crash should be possible under any circumstances, so hopefully not necessary? I am happy to assist in troubleshooting or providing any necessary follow-up information, please don't hesitate to ask.

Thanks!

auth

Most helpful comment

I'm afraid I will provide no future logs as my fix of simply null/empty checking prior to calling the method was sufficient, I have no new crash reports here. (and worth saying if an real email does go in there, the functionality is working, so apart from having to do a client-side check, the API is working)

Thanks

All 10 comments

Not sure if this is relevant, but the auth methods I have enabled are phone, email, facebook, google, and apple. If I understand correctly apple is in beta so perhaps the code is newer and the issue lurks in there.

Hi @mikehardy, thanks for reporting the issue. Could you provide detailed steps in order to reproduce it on my end? You may also provide a minimal repro that I can run locally to see if it's reproducible.

I understand the desire for both a minimal repro and exact reproduction

However:

The error isn't at a frequency yet where I can provide exact reproduction however in my app flow, this is potentially the first Firebase Auth SDK call made.

It would work out like this:

  • in an app with social auth (apple, google, facebook) enabled;
  • attempt to login to one of those social providers using their SDKs
  • use the email provided by the social provider SDK in FIRAUth.fetchSignInMethodsForEmail
  • crash, sometimes, with this trace

Note that Apple Sign-in does not provide the email address all the time, and sometimes they provide an anonymous one. Perhaps the code is not correctly handling the case where I attempt to send in an empty or null email address. I can't tell myself because the auth module is not open sourced here

Reported Warfalamei for spam.

@renkelvin from what I understand Sign in with Apple sometimes causes _identifier to be nil on this line.

@mikehardy if you're able to reproduce the crash, can you put a breakpoint on that line and print out the values of _identifier and _continueURI?

Oo - didn't realize auth was open source, I should have looked myself. It does stand to reason that one of those two items is nil though.

Unfortunately I've not been able to reproduce it myself so I'm not sure I'll ever have a result but I will put that breakpoint on. It's much more likely that I could integrate a patch against the Pod source that logged the values via crashlytics such that they were available in any future crash trace

As mentioned above I'm consuming this API from react-native which has the unfortunate implication my Obj-C skills are weak, but I'm good at handling source if you could suggest the appropriate crashlytics API calls to log the same - I think it would just be one or two lines to patch in there?

You can use this method and set a bool to true if the email exists and false if it's nil.

I haven't done a production build with any augmented logging in it yet, but this is a strong indication that my code is feeding something unexpected to the SDK layer - this is Java but I thought it was interesting as it's a crash that just recently started popping up:

Fatal Exception: java.lang.IllegalArgumentException: Given String is empty or null
       at com.google.android.gms.common.internal.Preconditions.b(Preconditions.java:11)
       at com.google.firebase.auth.FirebaseAuth.fetchSignInMethodsForEmail(FirebaseAuth.java)
       at io.invertase.firebase.auth.RNFirebaseAuth.fetchSignInMethodsForEmail(RNFirebaseAuth.java:15)
       at java.lang.reflect.Method.invoke(Method.java)
       at com.facebook.react.bridge.JavaMethodWrapper.invoke(JavaMethodWrapper.java:149)
       at com.facebook.react.bridge.JavaModuleWrapper.invoke(JavaModuleWrapper.java:21)
       at com.facebook.react.bridge.queue.NativeRunnable.run(NativeRunnable.java)
       at android.os.Handler.handleCallback(Handler.java:873)
       at android.os.Handler.dispatchMessage(Handler.java:99)
       at com.facebook.react.bridge.queue.MessageQueueThreadHandler.dispatchMessage(MessageQueueThreadHandler.java)
       at android.os.Looper.loop(Looper.java:214)
       at com.facebook.react.bridge.queue.MessageQueueThreadImpl$4.run(MessageQueueThreadImpl.java:37)
       at java.lang.Thread.run(Thread.java:764)

Here is that chunk of code, for what it's worth (though with a single-argument method this isn't the most complicated thing to reason through): https://github.com/invertase/react-native-firebase/blob/v5.x.x/android/src/main/java/io/invertase/firebase/auth/RNFirebaseAuth.java#L1595

The easiest thing to do for me is to check for empty or null prior to calling in to these methods (java and ios) but similar to the ios one, it would be nice if the documented exception was returned in a promise rejection vs a crash (https://firebase.google.com/docs/reference/android/com/google/firebase/auth/FirebaseAuth.html#public-tasksigninmethodqueryresult-fetchsigninmethodsforemail-string-email) - I mean that nicely by the way, I'm aware this is a gigantic pile of code+complexity and I'm happy with the way it works in general

Cheers!

Potentially a similar report here: https://github.com/firebase/FirebaseUI-iOS/issues/830

I'm afraid I will provide no future logs as my fix of simply null/empty checking prior to calling the method was sufficient, I have no new crash reports here. (and worth saying if an real email does go in there, the functionality is working, so apart from having to do a client-side check, the API is working)

Thanks

Was this page helpful?
0 / 5 - 0 ratings