The Complete Guide to Firebase Phone Auth for iOS

Oliver Bevan
Firebase Developers
4 min readAug 3, 2022

Firebase’s iOS SDK is typically well documented, however I realised that it was lacking for Phone Auth after a large struggle implementing it myself.

I decided to write this guide to help future developers and save them from the reading around, and trial and error I had to endure!

Prerequisites

All you will need is a Firebase and Xcode project ready to go!

Make sure you have Firebase, Firebase Auth, and Firebase Messaging added as package dependencies in Xcode.

Stage One: Setup Firebase and the APN service

Step One

The first step is simple: enable Phone Auth in the Firebase Console:

Enabling Phone Auth in Firebase

You can also add some testing phone numbers and verification codes here.

Step Two: Enabling slient notifications (APN Key setup)

Firebase requires either reCAPTCHA or a silent push notification (notifications sent through Apple’s servers, but not appearing to the user) to authorise the request to send an OTP code (for spam prevention).

I would recommend ensuring both work for a smooth user experience and for a fallback in case the push notification is not received.

We will also implement user facing notification handling for Firebase Cloud Messaging at the same time.

First, head over to Apple Developer > Keys, Certificates, and Identities

Apple Developer portal

Add a key, give it a name, and check the box for Apple Push Notifications service. Download the key and save it securely on your computer.

Now, head over to the Firebase console.

Adding the APN Key in Firebase

and upload the APN key here, under Project Settings (gear icon) > Cloud Messaging.

Step Three: Enabling silent notifications (continued!)

Now head over to Xcode:

Adding capabilities in Xcode

Add capabilities for Background Modes (check Remote Notifications), and Push Notifications.

Finally, head back to the Project Info page:

Adding URL scheme in Xcode

And add a URL scheme. Copy the URL from the GoogleService-Info.plist. You want the one under REVERSED_CLIENT_ID.

Stage Two: Adding callbacks for Remote Notification

Step One: Disabling method swizzling

Firebase usually hooks into these callbacks in the App Delegate automatically, however I have found that it does not work with SwiftUI lifecycle apps. Therefore we will implement the callbacks ourselves.

Disabling Firebase Method Swizzing in Xcode

Head into the Custom Target Properties under Info and add a key for FirebaseAppDelegateProxyEnabled, with type Boolean, and value false or 0.

Step Two: Setting up AppDelegateAdaptor

Now it’s time to get into the meat of this task. The following code snippets are based around a SwiftUI lifecycle app but can easily be adapted for UIKit.

  1. Create a class subclassing UIApplicationDelegate, and call FirebaseApp.configure() as required.
  2. Then, pipe the class through to SwiftUI with a @UIApplicationDelegateAdaptor as shown.

Step 3: Implement App Delegate callbacks

Head into your AppDelegate and:

  1. Set the delegates for the UNUserNotificationCenter and Firebase Messaging client as shown (you may get compiler errors, we will deal with these shortly)
  2. Request notification access (not necessary for silent notifications in recent versions of iOS, so feel free to not implement this)
  3. Implement the didRecieveNotification handler as shown. If the notification is for Firebase Auth, do not pass on to Messaging. (Although not strictly necessary, doing this will allow you to use Cloud Messaging outside of Firebase Auth)

Step 4: Implement App Delegate Delegates

The UNNotificationCenterDelegate and Messaging Delegate are implemented through extensions to help separate the code.

  1. Add the extension for the UNUserNotificationCenterDelegate and implement the callbacks for presenting and receiving notifications
  2. Add the callback for didRegisterForRemoteNotificationsWithDeviceToken and pass the APNS token to Firebase Auth and Messaging. This is to verify that the notification recieved was intended for this device. Make sure to choose type: .unknown otherwise you may get some unexpected errors as the type will be different for debug and release builds.
  3. Finally, add the extension for the Firebase MessagingDelegate and the function e to share the token throughout the app.

Stage 3: Sign in users

We are now ready to sign in users. I like to implement the following methods in an ObservableObject injected via .environmentObject at the root view, but feel free to implement these as you please.

  1. Implement the sendSMS function. Call .verifyPhoneNumber and pass the error through with an escaping closure. Remember to store the verificationID somewhere (UserDefaults is appropriate) so that the request can be authenticated.
  2. Implement the signIn function. Grab the verificationID we saved earlier and create the Firebase credential with this and the OTP code provided by the user. Call auth().signIn and pass the error through in an escapting closure.

Congratulations!

That is all the code required to implement Firebase Phone Auth on iOS. A bit of an involved process, but one rightfully so to prevent scam.

I hope this guide has cleared things up and made your journey implementing Firebase that little bit easier. Thanks for checking it out!

Please check out the Firebase Docs on Phone Auth and Cloud Messaging for more information:

— Oliver.

--

--