tech-tracker-expo/components/auth/AppleSignIniOS.tsx

106 lines
3.5 KiB
TypeScript

import React, { useState, useEffect } from 'react';
import { supabase } from '@/lib/supabase';
import * as AppleAuthentication from 'expo-apple-authentication';
import { useColorScheme } from '@/hooks/useColorScheme';
import { ThemedView } from '@/components/theme';
import { StyleSheet, Platform } from 'react-native';
import Constants from 'expo-constants';
import * as Notifications from 'expo-notifications';
import type { updateUser } from '@/constants/Types';
const AppleSignInButton = () => {
const scheme = useColorScheme() ?? 'dark';
const signInWithApple = async () => {
try {
const credential = await AppleAuthentication.signInAsync({
requestedScopes: [
AppleAuthentication.AppleAuthenticationScope.FULL_NAME,
AppleAuthentication.AppleAuthenticationScope.EMAIL,
],
});
//const projectId = Constants.expoConfig?.extra?.projectId;
//if (!projectId) throw new Error('No projectId found in expo.config.json');
//const pushToken = await Notifications.getExpoPushTokenAsync({
//projectId,
//});
if (credential.identityToken) {
const email = credential.email;
const full_name =
credential.fullName && credential.fullName.givenName && credential.fullName.familyName
? `${credential.fullName.givenName} ${credential.fullName.familyName}`
: null;
const {
error,
data: { user, session },
} = await supabase.auth.signInWithIdToken({
provider: 'apple',
token: credential.identityToken,
});
console.log(JSON.stringify({ error, user }, null, 2));
if (!error && session) {
if (email) {
const data: updateUser = {
email,
full_name: full_name ?? '',
};
const { error: authUpdateError } = await supabase.auth.updateUser({
data,
})
const { error: updateError } = await supabase
.from('profiles')
.upsert({
id: session.user.id,
full_name,
email,
provider: 'apple',
updated_at: new Date(),
});
if (updateError) {
console.error('Error updating user metadata:', updateError);
}
}
}
} else {
throw new Error('No identityToken.');
}
} catch (e: any) {
if (e.code === 'ERR_REQUEST_CANCELED') {
// handle that the user canceled the sign-in flow
console.log('User canceled sign-in flow');
} else {
// handle other errors
console.log('Error signing in with Apple:', e);
}
}
};
if (Platform.OS !== 'ios') return <ThemedView />;
else
return (
<ThemedView style={styles.verticallySpaced}>
<AppleAuthentication.AppleAuthenticationButton
buttonType={AppleAuthentication.AppleAuthenticationButtonType.SIGN_IN}
buttonStyle={
scheme === 'light'
? AppleAuthentication.AppleAuthenticationButtonStyle.BLACK
: AppleAuthentication.AppleAuthenticationButtonStyle.WHITE
}
cornerRadius={5}
style={{ width: 200, height: 64 }}
onPress={signInWithApple}
/>
</ThemedView>
);
};
export default AppleSignInButton;
const styles = StyleSheet.create({
verticallySpaced: {
paddingTop: 4,
paddingBottom: 4,
alignItems: 'center',
marginTop: 20,
},
});