Skip to content

Commit 0886953

Browse files
committed
fix: prevent rotation from canceling auth, clear stale pending results on new flow start, make pending fields internal for direct test access
1 parent ec02d07 commit 0886953

File tree

3 files changed

+15
-24
lines changed

3 files changed

+15
-24
lines changed

auth0/src/main/java/com/auth0/android/provider/AuthenticationActivity.kt

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -57,12 +57,14 @@ public open class AuthenticationActivity : Activity() {
5757
launchAuthenticationIntent()
5858
return
5959
}
60+
// Only deliver result if intent.data is present (user returned from browser).
61+
// If data is null, the Activity resumed due to rotation or other config change
62+
// while the CustomTab is still open — don't finish, let the browser continue.
6063
val resultMissing = authenticationIntent.data == null
61-
if (resultMissing) {
62-
setResult(RESULT_CANCELED)
64+
if (!resultMissing) {
65+
deliverAuthenticationResult(authenticationIntent)
66+
finish()
6367
}
64-
deliverAuthenticationResult(authenticationIntent)
65-
finish()
6668
}
6769

6870
override fun onDestroy() {

auth0/src/main/java/com/auth0/android/provider/WebAuthProvider.kt

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -50,9 +50,9 @@ public object WebAuthProvider {
5050
data class Failure(val error: AuthenticationException) : PendingResult<Nothing>()
5151
}
5252

53-
private val pendingLoginResult = AtomicReference<PendingResult<Credentials>?>(null)
53+
internal val pendingLoginResult = AtomicReference<PendingResult<Credentials>?>(null)
5454

55-
private val pendingLogoutResult = AtomicReference<PendingResult<Void?>?>(null)
55+
internal val pendingLogoutResult = AtomicReference<PendingResult<Void?>?>(null)
5656

5757
/**
5858
* Registers login (and optionally logout) callbacks for the duration of the given
@@ -332,6 +332,7 @@ public object WebAuthProvider {
332332
*/
333333
public fun start(context: Context, callback: Callback<Void?, AuthenticationException>) {
334334
pendingLogoutResult.set(null)
335+
pendingLoginResult.set(null)
335336

336337
val effectiveCallback = if (context is LifecycleOwner) {
337338
LifecycleAwareCallback<Void?>(
@@ -703,6 +704,7 @@ public object WebAuthProvider {
703704
callback: Callback<Credentials, AuthenticationException>
704705
) {
705706
pendingLoginResult.set(null)
707+
pendingLogoutResult.set(null)
706708
val effectiveCallback = if (context is LifecycleOwner) {
707709
LifecycleAwareCallback<Credentials>(
708710
delegateCallback = callback,

auth0/src/test/java/com/auth0/android/provider/WebAuthProviderTest.kt

Lines changed: 5 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -65,7 +65,6 @@ import java.io.InputStream
6565
import java.nio.file.Files
6666
import java.nio.file.Paths
6767
import java.util.*
68-
import java.util.concurrent.atomic.AtomicReference
6968

7069
@RunWith(RobolectricTestRunner::class)
7170
@Config(shadows = [ThreadSwitcherShadow::class])
@@ -3418,33 +3417,21 @@ public class WebAuthProviderTest {
34183417
Assert.assertNotNull(getPendingLogoutResult())
34193418
}
34203419

3421-
// Reflection helpers — pendingLoginResult/pendingLogoutResult are private in WebAuthProvider
3422-
@Suppress("UNCHECKED_CAST")
3420+
// Direct access — pendingLoginResult/pendingLogoutResult are internal in WebAuthProvider
34233421
private fun setPendingLoginResult(result: WebAuthProvider.PendingResult<Credentials>?) {
3424-
val field = WebAuthProvider::class.java.getDeclaredField("pendingLoginResult")
3425-
field.isAccessible = true
3426-
(field.get(WebAuthProvider) as AtomicReference<WebAuthProvider.PendingResult<Credentials>?>).set(result)
3422+
WebAuthProvider.pendingLoginResult.set(result)
34273423
}
34283424

3429-
@Suppress("UNCHECKED_CAST")
34303425
private fun getPendingLoginResult(): WebAuthProvider.PendingResult<Credentials>? {
3431-
val field = WebAuthProvider::class.java.getDeclaredField("pendingLoginResult")
3432-
field.isAccessible = true
3433-
return (field.get(WebAuthProvider) as AtomicReference<WebAuthProvider.PendingResult<Credentials>?>).get()
3426+
return WebAuthProvider.pendingLoginResult.get()
34343427
}
34353428

3436-
@Suppress("UNCHECKED_CAST")
34373429
private fun setPendingLogoutResult(result: WebAuthProvider.PendingResult<Void?>?) {
3438-
val field = WebAuthProvider::class.java.getDeclaredField("pendingLogoutResult")
3439-
field.isAccessible = true
3440-
(field.get(WebAuthProvider) as AtomicReference<WebAuthProvider.PendingResult<Void?>?>).set(result)
3430+
WebAuthProvider.pendingLogoutResult.set(result)
34413431
}
34423432

3443-
@Suppress("UNCHECKED_CAST")
34443433
private fun getPendingLogoutResult(): WebAuthProvider.PendingResult<Void?>? {
3445-
val field = WebAuthProvider::class.java.getDeclaredField("pendingLogoutResult")
3446-
field.isAccessible = true
3447-
return (field.get(WebAuthProvider) as AtomicReference<WebAuthProvider.PendingResult<Void?>?>).get()
3434+
return WebAuthProvider.pendingLogoutResult.get()
34483435
}
34493436

34503437
private companion object {

0 commit comments

Comments
 (0)