Pick your app

The examples below will be updated with your app ID.

Authentication and Permissions

Sign In with Apple

Instant supports Sign In with Apple on the Web and in native applications.

#Step 1: Create App ID

  • Navigate to Certificates, Identifiers & Profiles
  • Select Identifiers
  • Click +
  • Register a new identifier → Select App IDs
  • Select a type → Select App
  • CapabilitiesSign In with Apple → Check
  • Fill in Bundle ID and Description
  • Click Register

#Step 2: Create Services ID

  • Navigate to Services IDs
  • Click +
  • Register a new identifier → Select Services IDs
  • Fill in Description and Identifier. You’ll need this Identifier later
  • Click Register

#Step 3: Configure Services ID (React Native flow)

This step is not needed for Expo.

#Step 4: Register your OAuth client with Instant

  • Go to the Instant dashboard and select Auth tab.
  • Select Add Apple Client
  • Select unique clientName (apple by default, will be used in db.auth calls)
  • Fill in Services ID from Step 2
  • Click Add Apple Client

#Step 5: Add Sign In code to your app (React Native flow)

Instant comes with support for Expo AppleAuthentication library.

Add dependency:

npx expo install expo-apple-authentication

Update app.json by adding:

{
"expo": {
"ios": {
"usesAppleSignIn": true
}
}
}

Go to Instant dashboard → Auth tab → Redirect Origins → Add an origin.

Add exp:// for development with Expo.

Authenticate with Apple and then pass identityToken to Instant along with clientName from Step 4:

const [nonce] = useState('' + Math.random());
try {
// sign in with Apple
const credential = await AppleAuthentication.signInAsync({
requestedScopes: [
AppleAuthentication.AppleAuthenticationScope.FULL_NAME,
AppleAuthentication.AppleAuthenticationScope.EMAIL,
],
nonce: nonce,
});
// pass identityToken to Instant
db.auth
.signInWithIdToken({
clientName: '<clientName>',
idToken: credential.identityToken,
nonce: nonce,
})
.catch((err) => {
console.log('Error', err.body?.message, err);
});
} catch (e) {
if (e.code === 'ERR_REQUEST_CANCELED') {
// handle that the user canceled the sign-in flow
} else {
// handle other errors
}
}

Sign out code:

<Button
title="Sign Out"
onPress={async () => {
await db.auth.signOut();
}}
/>

Full example:

import React, { useState } from 'react';
import { Button, View, Text, StyleSheet } from 'react-native';
import { init, tx } from '@instantdb/react-native';
import * as AppleAuthentication from 'expo-apple-authentication';
const APP_ID = '__APP_ID__';
const db = init({ appId: APP_ID });
function App() {
return (
<>
<db.SignedIn>
<UserInfo />
</db.SignedIn>
<db.SignedOut>
<Login />
</db.SignedOut>
</>
);
}
function UserInfo() {
const user = db.useUser();
return (
<View style={styles.container}>
<Text>Hello {user.email}!</Text>
<Button
title="Sign Out"
onPress={async () => {
await db.auth.signOut();
}}
/>
</View>
);
}
function Login() {
const [nonce] = useState('' + Math.random());
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,
],
nonce: nonce,
});
// signed in
db.auth
.signInWithIdToken({
clientName: 'apple',
idToken: credential.identityToken,
nonce: nonce,
})
.catch((err) => {
console.log('Error', err.body?.message, err);
});
} catch (e) {
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,
},
});
export default App;