supabase / supabase-swift

A Swift client for Supabase
https://supabase.com/docs/reference/swift
MIT License
679 stars 100 forks source link

Apple Native Sign In : { "__isAuthError": true, "name": "AuthApiError", "status": 400 } #504

Open agrittiwari opened 4 months ago

agrittiwari commented 4 months ago

Bug report

Describe the bug

IdentityToken is returned by Apple, but supabase.auth.signInwithIdToken breaks and returns the erro

To Reproduce

Steps to reproduce the behavior, please provide code snippets or a repository:

import * as AppleAuthentication from 'expo-apple-authentication';
import {
  Employee,
  GetLoggedInUserDocument,
  useRegisterUserMutation,
} from 'generated/hooks_and_more';
import { Platform } from 'react-native';
import { useMMKVObject, useMMKVString } from 'react-native-mmkv';
import { captureSentryException } from 'sentry_telemetry/sentryLogger';
import { supabase } from '~/utils/supabase';

export default function AppleSignIn() {
  const [accessToken, setAccessToken] = useMMKVString('access_token');
  const [refreshToken, setRefreshToken] = useMMKVString('refresh_token');
  const [mmkvUser, setMMKVUser] = useMMKVObject<Employee>('mmkv_user');
  const [registerUser, { data: userResponse, loading: registerLoading }] =
    useRegisterUserMutation();
  if (Platform.OS === 'ios')
    return (
      <AppleAuthentication.AppleAuthenticationButton
        buttonType={AppleAuthentication.AppleAuthenticationButtonType.SIGN_IN}
        buttonStyle={AppleAuthentication.AppleAuthenticationButtonStyle.BLACK}
        cornerRadius={5}
        style={{ width: 200, height: 64 }}
        onPress={async () => {
          try {
            const credential = await AppleAuthentication.signInAsync({
              requestedScopes: [
                AppleAuthentication.AppleAuthenticationScope.FULL_NAME,
                AppleAuthentication.AppleAuthenticationScope.EMAIL,
              ],
            });
            // Sign in via Supabase Auth.
            console.log(credential);
            if (credential.identityToken) {
              const {
                error,
                data: { user, session },
              } = await supabase.auth.signInWithIdToken({
                provider: 'apple',
                token: credential.identityToken,
              });
              console.log(JSON.stringify({ error, user }, null, 2));
              if (!error) {
                // User is signed in.
                setAccessToken(session?.access_token || '');
                setRefreshToken(session?.refresh_token || '');
                registerUser({
                  refetchQueries: [{ query: GetLoggedInUserDocument }],
                  onCompleted(data, clientOptions) {
                    setMMKVUser(data?.register);
                    //  setUser(data?.register);
                    //Not deprecating this, As it is used in push notifications and Select services as well.
                    console.log('on registerd in Native Apple Login', accessToken);
                    // user && getAccessToken() && navigation.replace('SetupYourOrganization');
                    // Toast.show('User Created Successfully', {
                    //   duration: Toast.durations.SHORT,
                    //   position: Toast.positions.BOTTOM,
                    //   textColor: 'white',
                    //   backgroundColor: colors?.dark?.green,
                    //   shadow: true,
                    //   animation: true,
                    //   hideOnPress: true,
                    //   delay: 0,
                    // });
                  },
                  onError(error, clientOptions) {
                    console.log('error', error);
                    captureSentryException('Error in creating new user', error as any);
                  },
                });
              }
            } else {
              throw new Error('No identityToken.');
            }
          } catch (e) {
            if (e.code === 'ERR_REQUEST_CANCELED') {
              // handle that the user canceled the sign-in flow
            } else {
              // handle other errors
            }
          }
        }}
      />
    );
  return <>{/* Implement Android Auth options. */}</>;
}

Expected behavior

Expected behavior is for supabase to generate the accessToken and refreshToken for the session

Screenshots

If applicable, add screenshots to help explain your problem.

System information

Additional context

I am using Expo, went through every code snippet out there and this issue particularly #Issue1401

agrittiwari commented 4 months ago

This ticket also related to this ticket #1561

Kamsou commented 3 months ago

Same error

dpelletier2017 commented 1 month ago

I seem to have the same error in a native Swift / SwiftUI project. I've had the error since Novembre 2023 AFAIK.

api(Auth.AuthError.APIError(msg: nil, code: nil, error: Optional("invalid request"), errorDescription: Optional("Bad ID token"), weakPassword: nil))

After doing :

let credentials = OpenIDConnectCredentials(provider: .apple, idToken: token)
let session = try await SupabaseDatabase.client.auth.signInWithIdToken(credentials: credentials)