typescript - Firebase getRedirectResult() løser seg ikke på onInit (Angular)


I mitt Angular-prosjekt prøver jeg å implementere Firebase loginWithRedirect() via Google Sign-In. Det rare er at noen ganger returnerer ikke getRedirectResult()-metoden noe etter omdirigering fra en vellykket Google-innlogging. Enda mer merkelig: på mobilen løses det aldri. I de tilfellene mottar jeg bare: { "credential": null, "user": null }

Min påloggingsmetode:

  async onLogin(isGoogleLogin) {
    const loading = await this.loadingController.create();
    await loading.present();
    let user;
    if (isGoogleLogin) {
      await this.authService.loginWithGoogle(); 
      // The upper method just calls: await this.angularFireAuth.signInWithRedirect(new   GoogleAuthProvider());
    } else {
      user = await this.authService.login(this.credentials.value);
    }
    await loading.dismiss();

    if (user) {
      this.buildNavPathAndNav();
    } else {
      this.utilService.showErrorToast('Login error', 'Login failed, please try again');
    }
  }

Min onInit-funksjon på påloggingsskjermen:

  async ngOnInit() {
    // Get user if logged in via redirect (e.g. google)
    const user = await this.authService.getRedirectLoginResult();

    // Navigate to home screen
    if (user) { this.buildNavPathAndNav(); };
  }

Min getRedirectLoginResult-funksjon:

  async getRedirectLoginResult() {
    const loading = await this.loadingController.create();
    await loading.present();

    const userObj = await this.afAuth.getRedirectResult();
    if (!userObj.user) {
      await loading.dismiss();
      return;
    };

    await this.dataService.setCurrentUser(userObj.user);
    await loading.dismiss();
    return userObj.user;
  }

Jeg vil virkelig sette pris på litt hjelp. Takk!

Svar #1

Problemet er relatert til blokkeringen av tilgang til tredjeparts lagring

Påloggingsalternativet med viderekobling i Firebase er implementert ved bruk av en skjult iframe. Problemet med moderne nettlesere er at tilgangen til denne skjulte iframen for å lese innholdet fra et tredjepartsdomene er begrenset, så påloggingsprosessen med viderekobling avsluttes stille uten å gi noen ledetråder til den forvirrede programmereren.

Dette ser ut til å være problemet (du kan lese mer om emnet her), fordi i det øyeblikket jeg deployerte nettstedet mitt på Firebase-webhosting, ble problemet løst automagisk. Med andre ord, sjekk Firebase-konfigurasjonen din:

export const environment = {
  production: false, 
  firebaseConfig: {
    apiKey: "--secret-things-go-here",
    authDomain: "MYAUTHDOMAIN.firebaseapp.com", << HERE!!!! CHECK THIS OUT
    projectId: "---blah-blah-blah----",
    storageBucket: "--more-secret-stuff-goes-here--",
    messagingSenderId: "--and-here--",
    appId: "--and-of-course-here--"
    
  }
};

Hvis du får tilgang til applikasjonen din ved å bruke domenet som er gitt i authDomain-feltet, er problemet løst. I det forrige eksemplet må denne URL-en være: https://MYAUTHDOMAIN.firebaseapp.com.

I den forrige artikkelen er noen andre løsninger for dette problemet lagt ut.

Hvordan kan jeg teste applikasjonen lokalt

Så vidt jeg vet, kan du ikke. For å teste autentiseringsprosessen lokalt, må du emulere den. For å gjøre det, må du koble applikasjonen til emulatoren. Sett inn denne koden:

connectAuthEmulator( this.auth, "http://localhost:9099" );

I appen din, der this.auth må være et angular.fire.auth.Auth-objekt.

Når du distribuerer nettstedet ditt til verten, må du fjerne denne linjen, så jeg har lagt til litt konfigurasjon i min environment.ts-fil for å gjøre det automatisk.

Og, ikke glem å starte Firebase Auth-emulatoren:

firebase emulators:start --only auth

Svar #2

Hvis signInWithRedirect() mislykkes på mobile enheter på grunn av nettleserbegrensninger eller tredjeparts informasjonskapselbegrensninger, kan du bruke signInWithPopup() som et alternativ for skrivebordsbrukere. Her er hva jeg tror vil fungere

try {
  const provider = new GoogleAuthProvider();
  if (this.isMobile()) {
    await this.angularFireAuth.signInWithRedirect(provider); // Mobile fallback
  } else {
    const result = await this.angularFireAuth.signInWithPopup(provider); // Desktop experience
    if (result.user) {
      // Handle successful login
    }
  }
} catch (error) {
  console.error('Login error:', error);
}

Relaterte artikler