EXPO AuthSession returns dismiss on Android device

Viewed 1842

I'm using Expo AuthSession to login in my app through my IdentityServer4 implementation.

I have the problem only in ANDROID when I try to log in my IdentityServer with my Google account.

The AuthSession open the browser in my device and I'm able to log in but after, when I answer YES to the notification that ask me if I want to allow the access I receive dismiss in my React Native App.

I noticed that if I register before my google account in the browser the problem disappear and I'm able to log in.

The code that I'm using is like this:

import * as AuthSession from "expo-auth-session";
import jwtDecode from "jwt-decode";
import * as React from "react";
import { Alert, Button, Platform, StyleSheet, Text, View } from "react-native";

// You need to swap out the Auth0 client id and domain with the one from your Auth0 client.
// In your Auth0 client, you need to also add a url to your authorized redirect urls.
//
// For this application, I added https://auth.expo.io/@arielweinberger/with-auth0 because I am
// signed in as the "arielweinberger" account on Expo and the name/slug for this app is "with-auth0".
//
// You can open this app in the Expo client and check your logs to find out your redirect URL.

const auth0ClientId = "ppSP6KhARumIUKQl5J02GTABifmBdDGy";
const auth0Domain = "expo-auth0.us.auth0.com"
const authorizationEndpoint = `https://${auth0Domain}/authorize`;

const useProxy = Platform.select({ default: false });
const redirectUri = AuthSession.makeRedirectUri({ useProxy, native:"myapp://" });

export default function App() {
  const [name, setName] = React.useState(null);

  const [request, result, promptAsync] = AuthSession.useAuthRequest(
    {
      redirectUri,
      clientId: auth0ClientId,
      // id_token will return a JWT token
      responseType: "id_token",
      // retrieve the user's profile
      scopes: ["openid", "profile"],
      extraParams: {
        // ideally, this will be a random value
        nonce: "nonce",
      },
    },
    { authorizationEndpoint }
  );

  // Retrieve the redirect URL, add this to the callback URL list
  // of your Auth0 application.
  console.log(`Redirect URL: ${redirectUri}`);

  React.useEffect(() => {
    if (result) {
      if (result.error) {
        Alert.alert(
          "Authentication error",
          result.params.error_description || "something went wrong"
        );
        return;
      }
      if (result.type === "success") {
        // Retrieve the JWT token and decode it
        const jwtToken = result.params.id_token;
        const decoded = jwtDecode(jwtToken);

        const { name } = decoded;
        setName(name);
      }
    }
  }, [result]);

  return (
    <View style={styles.container}>
      {name ? (
        <Text style={styles.title}>You are logged in, {name}!</Text>
      ) : (
        <Button
          disabled={!request}
          title="Log in with Auth0"
          onPress={() => promptAsync({ useProxy })}
        />
      )}
    </View>
  );
}

const styles = StyleSheet.create({
  container: {
    flex: 1,
    backgroundColor: "#fff",
    alignItems: "center",
    justifyContent: "center",
  },
  title: {
    fontSize: 20,
    textAlign: "center",
    marginTop: 40,
  },
});
2 Answers

I solved. When I call promptAsync I can add some options and one of these is showInRecents (Should browsed website be shown as a separate entry in Android multitasker) the default is false. Setting this to true solved my problem.

promptAsync(discovery, { useProxy, showInRecents:true });

I had a similar error on android. Whenever you minimize the web browser (to get a two-factor code and so forth) the browser would close. Worked perfectly on iOS. Checking the documentation doesn't help, as the solution isn't listed there.

The answer by Christian Cascone is correct here as well:

promptAsync(discovery, { useProxy, showInRecents:true });
Related