Skip to content

Commit 0a9e5c3

Browse files
fix: ensure that when selecting phone or email, it routes straight to screen
1 parent c5461b6 commit 0a9e5c3

2 files changed

Lines changed: 124 additions & 3 deletions

File tree

auth/src/main/java/com/firebase/ui/auth/ui/screens/FirebaseAuthScreen.kt

Lines changed: 23 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -125,6 +125,10 @@ fun FirebaseAuthScreen(
125125
val emailLinkFromDifferentDevice = remember { mutableStateOf<String?>(null) }
126126
val lastSignInPreference =
127127
remember { mutableStateOf<SignInPreferenceManager.SignInPreference?>(null) }
128+
val startRoute = remember(configuration.providers, configuration.isProviderChoiceAlwaysShown) {
129+
getStartRoute(configuration)
130+
}
131+
val skipsMethodPicker = startRoute != AuthRoute.MethodPicker
128132

129133
// Load last sign-in preference on launch
130134
LaunchedEffect(authState) {
@@ -236,7 +240,7 @@ fun FirebaseAuthScreen(
236240
) {
237241
NavHost(
238242
navController = navController,
239-
startDestination = AuthRoute.MethodPicker.route,
243+
startDestination = startRoute.route,
240244
enterTransition = configuration.transitions?.enterTransition ?: {
241245
fadeIn(animationSpec = tween(700))
242246
},
@@ -319,7 +323,9 @@ fun FirebaseAuthScreen(
319323
},
320324
onCancel = {
321325
pendingLinkingCredential.value = null
322-
if (!navController.popBackStack()) {
326+
if (skipsMethodPicker) {
327+
onSignInCancelled()
328+
} else if (!navController.popBackStack()) {
323329
navController.navigate(AuthRoute.MethodPicker.route) {
324330
popUpTo(AuthRoute.MethodPicker.route) { inclusive = true }
325331
launchSingleTop = true
@@ -339,7 +345,9 @@ fun FirebaseAuthScreen(
339345
onSignInFailure(exception)
340346
},
341347
onCancel = {
342-
if (!navController.popBackStack()) {
348+
if (skipsMethodPicker) {
349+
onSignInCancelled()
350+
} else if (!navController.popBackStack()) {
343351
navController.navigate(AuthRoute.MethodPicker.route) {
344352
popUpTo(AuthRoute.MethodPicker.route) { inclusive = true }
345353
launchSingleTop = true
@@ -667,6 +675,18 @@ sealed class AuthRoute(val route: String) {
667675
object MfaChallenge : AuthRoute("auth_mfa_challenge")
668676
}
669677

678+
internal fun getStartRoute(configuration: AuthUIConfiguration): AuthRoute {
679+
if (configuration.isProviderChoiceAlwaysShown || configuration.providers.size != 1) {
680+
return AuthRoute.MethodPicker
681+
}
682+
683+
return when (configuration.providers.single()) {
684+
is AuthProvider.Email -> AuthRoute.Email
685+
is AuthProvider.Phone -> AuthRoute.Phone
686+
else -> AuthRoute.MethodPicker
687+
}
688+
}
689+
670690
data class AuthSuccessUiContext(
671691
val authUI: FirebaseAuthUI,
672692
val stringProvider: AuthUIStringProvider,
Lines changed: 101 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,101 @@
1+
package com.firebase.ui.auth.ui.screens
2+
3+
import android.content.Context
4+
import androidx.test.core.app.ApplicationProvider
5+
import com.firebase.ui.auth.configuration.authUIConfiguration
6+
import com.firebase.ui.auth.configuration.auth_provider.AuthProvider
7+
import com.google.common.truth.Truth.assertThat
8+
import org.junit.Before
9+
import org.junit.Test
10+
import org.junit.runner.RunWith
11+
import org.robolectric.RobolectricTestRunner
12+
import org.robolectric.annotation.Config
13+
14+
@RunWith(RobolectricTestRunner::class)
15+
@Config(manifest = Config.NONE)
16+
class FirebaseAuthScreenRouteTest {
17+
18+
private lateinit var applicationContext: Context
19+
20+
@Before
21+
fun setUp() {
22+
applicationContext = ApplicationProvider.getApplicationContext()
23+
}
24+
25+
@Test
26+
fun `single email provider starts at email route`() {
27+
val configuration = authUIConfiguration {
28+
context = applicationContext
29+
providers {
30+
provider(
31+
AuthProvider.Email(
32+
emailLinkActionCodeSettings = null,
33+
passwordValidationRules = emptyList()
34+
)
35+
)
36+
}
37+
}
38+
39+
assertThat(getStartRoute(configuration)).isEqualTo(AuthRoute.Email)
40+
}
41+
42+
@Test
43+
fun `single phone provider starts at phone route`() {
44+
val configuration = authUIConfiguration {
45+
context = applicationContext
46+
providers {
47+
provider(
48+
AuthProvider.Phone(
49+
defaultNumber = null,
50+
defaultCountryCode = null,
51+
allowedCountries = null
52+
)
53+
)
54+
}
55+
}
56+
57+
assertThat(getStartRoute(configuration)).isEqualTo(AuthRoute.Phone)
58+
}
59+
60+
@Test
61+
fun `single email provider shows picker when always shown is enabled`() {
62+
val configuration = authUIConfiguration {
63+
context = applicationContext
64+
providers {
65+
provider(
66+
AuthProvider.Email(
67+
emailLinkActionCodeSettings = null,
68+
passwordValidationRules = emptyList()
69+
)
70+
)
71+
}
72+
isProviderChoiceAlwaysShown = true
73+
}
74+
75+
assertThat(getStartRoute(configuration)).isEqualTo(AuthRoute.MethodPicker)
76+
}
77+
78+
@Test
79+
fun `multiple providers start at method picker`() {
80+
val configuration = authUIConfiguration {
81+
context = applicationContext
82+
providers {
83+
provider(
84+
AuthProvider.Email(
85+
emailLinkActionCodeSettings = null,
86+
passwordValidationRules = emptyList()
87+
)
88+
)
89+
provider(
90+
AuthProvider.Phone(
91+
defaultNumber = null,
92+
defaultCountryCode = null,
93+
allowedCountries = null
94+
)
95+
)
96+
}
97+
}
98+
99+
assertThat(getStartRoute(configuration)).isEqualTo(AuthRoute.MethodPicker)
100+
}
101+
}

0 commit comments

Comments
 (0)