Authentication Flow Diagaram
User → App Frontend → Provider (Apple/Google) → App Frontend → Backend Authentication Service → Database → App Frontend (Authenticated)
Note: A paid Apple Developer account is required to implement Sign In with Apple.
Installation
We will start with iOS
implementation and then continue with android
later
Create a new expo app if you haven’t had existing project
Resetting the project is optional, but we’ll do it for simplicity in this guide.
bun create expo
cd app
bun reset-project
git commit -m "feat: reset project template"
This implementation doesn’t work with expo go, therefore we need to install development builds.
First install expo-dev-client
bunx expo add expo-dev-client
Since we are opting in to native development builds and we want to use continuous native integration, we will add ios and android folders to .gitignore
echo "ios/" >> .gitignore
echo "android/" >> .gitignore
Run prebuild to generate native folder and its code
bunx expo prebuild -p ios
Configure bundleIdentifier
for iOS
I usually use a format based on domain name.
-
Say the domain ends with .com for example
book.com
I will usecom.book.mobile
-
And if the domain ends with .app for example
book.app
I will usecom.app.book
This will matter when registering the app to the store, and we need to make sure that it is unique or hasn’t been registered before
Next We will be using package from expo called expo-apple-authentication
Install the package
bunx expo add expo-apple-authentication
Configure the package
On app.json
add usesAppleSignIn
to true and add the plugin.
{
"expo": {
"ios": {
"usesAppleSignIn": true
},
"plugins": ["expo-apple-authentication"]
}
}
After adding all those configuration, run prebuild again
bunx expo prebuild -p ios
At this point we should commit our changes
git commit -m "feat: setup development builds and authentication packages"
Run the app
Now we need to make sure everything configured correctly by running the app and make sure there is no error.
When first time running the app, it will ask for paid apple developer team for signing the app. Make sure to choose the correct one if you have more than one.
Testing on both iOS Simulator and real physical device is encouraged
Run on iOS Simulator
bunx expo run:ios
Run on physical device
Try run this command
bunx expo run:ios --device
This will throw error if you haven’t setup your iPhone and Signing on XCode. Therefore open XCode for this project first.
cd ios/
open [project-name].xcodeproj
Let the indexing of the project done, make sure you select your iPhone device, Go to Signing & Capabilities, make sure automatic signing already configured with the correct account and try running the command again
bunx expo run:ios --device
If this is your first time using your iPhone device, it will register it automatically
Check all listed device here. https://developer.apple.com/account/resources/devices/list
Running above step correctly will also register a new identifier here https://developer.apple.com/account/resources/identifiers/list
Check in the list, there should be a new identified called XC [your.bundle.identifier], with Sign In With Apple capability.
It will also add your “appleTeamId”: “[YOUR_APPLE_TEAM_ID]” to app.json
If you have never configure certificates, it will also create one here https://developer.apple.com/account/resources/certificates/list, note that it will create certificate based on env, development or production
Usage
Code from expo doc
Apply this code to your root app
import * as AppleAuthentication from 'expo-apple-authentication';
import { View, StyleSheet } from 'react-native';
export default function App() {
return (
<View style={styles.container}>
<AppleAuthentication.AppleAuthenticationButton
buttonType={AppleAuthentication.AppleAuthenticationButtonType.SIGN_IN}
buttonStyle={AppleAuthentication.AppleAuthenticationButtonStyle.BLACK}
cornerRadius={5}
style={styles.button}
onPress={async () => {
try {
const credential = await AppleAuthentication.signInAsync({
requestedScopes: [
AppleAuthentication.AppleAuthenticationScope.FULL_NAME,
AppleAuthentication.AppleAuthenticationScope.EMAIL,
],
});
console.log(credential);
// signed in
// FROM THIS PART
// WE NEED TO USE `credential` returned AND INTEGRATE IT TO OUR BACKEND OF CHOICE
// AND THEN MANAGE THE SESSION USING OUR BACKEND
} catch (e: any) {
if (e.code === 'ERR_REQUEST_CANCELED') {
// handle that the user canceled the sign-in flow
} else {
// handle other errors
}
}
}}
/>
</View>
);
}
const styles = StyleSheet.create({
container: {
flex: 1,
alignItems: 'center',
justifyContent: 'center',
},
button: {
width: 200,
height: 44,
},
});
If everything working as expected, you should see Sign in with Apple
button and if you click it, it will open a native modal to sign in using your apple id.
Try signing in and check your console log to check the credential
For more configuration details, check https://docs.expo.dev/versions/latest/sdk/apple-authentication