Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 688f18aa authored by Fabian Kozynski's avatar Fabian Kozynski Committed by Android (Google) Code Review
Browse files

Merge "Check logoutUser handle to determine if we can log out" into main

parents 06312a45 418581d8
Loading
Loading
Loading
Loading
+151 −4
Original line number Diff line number Diff line
@@ -17,8 +17,10 @@

package com.android.systemui.user.data.repository

import android.app.admin.DevicePolicyManager
import android.app.admin.devicePolicyManager
import android.content.Intent
import android.content.applicationContext
import android.content.pm.UserInfo
import android.internal.statusbar.fakeStatusBarService
import android.os.UserHandle
@@ -77,10 +79,7 @@ class UserRepositoryImplTest : SysuiTestCase() {
    fun setUp() {
        MockitoAnnotations.initMocks(this)
        tracker = FakeUserTracker()
        context.orCreateTestableResources.addOverride(
            R.bool.config_userSwitchingMustGoThroughLoginScreen,
            false,
        )
        setUserSwitchingMustGoThroughLoginScreen(false)
    }

    @Test
@@ -308,6 +307,117 @@ class UserRepositoryImplTest : SysuiTestCase() {
            job.cancel()
        }

    @Test
    fun isSecondaryUserLogoutEnabled_secondaryLogoutDisabled_alwaysFalse() =
        testScope.runTest {
            underTest = create(testScope.backgroundScope)
            mockLogoutUser(LogoutUserResult.NON_SYSTEM_CURRENT)
            setSecondaryUserLogoutEnabled(false)
            setUpUsers(count = 2, selectedIndex = 0)
            tracker.onProfileChanged()

            val secondaryUserLogoutEnabled by
                collectLastValue(underTest.isSecondaryUserLogoutEnabled)

            assertThat(secondaryUserLogoutEnabled).isFalse()

            setUpUsers(count = 2, selectedIndex = 1)
            tracker.onProfileChanged()
            assertThat(secondaryUserLogoutEnabled).isFalse()
        }

    @Test
    fun isSecondaryUserLogoutEnabled_secondaryLogoutEnabled_NullLogoutUser_alwaysFalse() =
        testScope.runTest {
            underTest = create(testScope.backgroundScope)
            mockLogoutUser(LogoutUserResult.NONE)
            setSecondaryUserLogoutEnabled(true)
            setUpUsers(count = 2, selectedIndex = 0)
            tracker.onProfileChanged()

            val secondaryUserLogoutEnabled by
                collectLastValue(underTest.isSecondaryUserLogoutEnabled)

            assertThat(secondaryUserLogoutEnabled).isFalse()

            setUpUsers(count = 2, selectedIndex = 1)
            tracker.onProfileChanged()
            assertThat(secondaryUserLogoutEnabled).isFalse()
        }

    @Test
    fun isSecondaryUserLogoutEnabled_secondaryLogoutEnabled_NonSystemLogoutUser_trueWhenNonSystem() =
        testScope.runTest {
            underTest = create(testScope.backgroundScope)
            mockLogoutUser(LogoutUserResult.NON_SYSTEM_CURRENT)
            setSecondaryUserLogoutEnabled(true)
            setUpUsers(count = 2, selectedIndex = 0)
            tracker.onProfileChanged()

            val secondaryUserLogoutEnabled by
                collectLastValue(underTest.isSecondaryUserLogoutEnabled)

            assertThat(secondaryUserLogoutEnabled).isFalse()

            setUpUsers(count = 2, selectedIndex = 1)
            tracker.onProfileChanged()
            assertThat(secondaryUserLogoutEnabled).isTrue()
        }

    @Test
    fun isLogoutToSystemUserEnabled_logoutThroughLoginScreenDisabled_alwaysFalse() =
        testScope.runTest {
            underTest = create(testScope.backgroundScope)
            mockLogoutUser(LogoutUserResult.NON_SYSTEM_CURRENT)
            setUserSwitchingMustGoThroughLoginScreen(false)
            setUpUsers(count = 2, selectedIndex = 0)
            tracker.onProfileChanged()

            val logoutToSystemUserEnabled by collectLastValue(underTest.isLogoutToSystemUserEnabled)

            assertThat(logoutToSystemUserEnabled).isFalse()

            setUpUsers(count = 2, selectedIndex = 1)
            tracker.onProfileChanged()
            assertThat(logoutToSystemUserEnabled).isFalse()
        }

    @Test
    fun isLogoutToSystemUserEnabled_logoutThroughLoginScreenEnabled_NullLogoutUser_alwaysFalse() =
        testScope.runTest {
            underTest = create(testScope.backgroundScope)
            mockLogoutUser(LogoutUserResult.NONE)
            setUserSwitchingMustGoThroughLoginScreen(true)
            setUpUsers(count = 2, selectedIndex = 0)
            tracker.onProfileChanged()

            val logoutToSystemUserEnabled by collectLastValue(underTest.isLogoutToSystemUserEnabled)

            assertThat(logoutToSystemUserEnabled).isFalse()

            setUpUsers(count = 2, selectedIndex = 1)
            tracker.onProfileChanged()
            assertThat(logoutToSystemUserEnabled).isFalse()
        }

    @Test
    fun isLogoutToSystemUserEnabled_logoutThroughLoginScreenEnabled_NonSystemLogoutUser_trueWhenNonSystem() =
        testScope.runTest {
            underTest = create(testScope.backgroundScope)
            mockLogoutUser(LogoutUserResult.NON_SYSTEM_CURRENT)
            setUserSwitchingMustGoThroughLoginScreen(true)
            setUpUsers(count = 2, selectedIndex = 0)
            tracker.onProfileChanged()

            val logoutToSystemUserEnabled by collectLastValue(underTest.isLogoutToSystemUserEnabled)

            assertThat(logoutToSystemUserEnabled).isFalse()

            setUpUsers(count = 2, selectedIndex = 1)
            tracker.onProfileChanged()
            assertThat(logoutToSystemUserEnabled).isTrue()
        }

    private fun createUserInfo(id: Int, isGuest: Boolean): UserInfo {
        val flags = 0
        return UserInfo(
@@ -354,6 +464,38 @@ class UserRepositoryImplTest : SysuiTestCase() {
        assertThat(model.isUserSwitcherEnabled).isEqualTo(expectedUserSwitcherEnabled)
    }

    private fun setSecondaryUserLogoutEnabled(enabled: Boolean) {
        whenever(devicePolicyManager.isLogoutEnabled).thenReturn(enabled)
        broadcastDispatcher.sendIntentToMatchingReceiversOnly(
            kosmos.applicationContext,
            Intent(DevicePolicyManager.ACTION_DEVICE_POLICY_MANAGER_STATE_CHANGED),
        )
    }

    private fun setUserSwitchingMustGoThroughLoginScreen(enabled: Boolean) {
        context.orCreateTestableResources.addOverride(
            R.bool.config_userSwitchingMustGoThroughLoginScreen,
            enabled,
        )
    }

    private fun mockLogoutUser(result: LogoutUserResult) {
        when (result) {
            LogoutUserResult.NONE -> {
                whenever(devicePolicyManager.logoutUser).thenReturn(null)
            }
            LogoutUserResult.NON_SYSTEM_CURRENT -> {
                whenever(devicePolicyManager.logoutUser).thenAnswer {
                    if (tracker.userHandle != UserHandle.SYSTEM) {
                        tracker.userHandle
                    } else {
                        null
                    }
                }
            }
        }
    }

    private fun create(scope: CoroutineScope): UserRepositoryImpl {
        return UserRepositoryImpl(
            appContext = context,
@@ -373,4 +515,9 @@ class UserRepositoryImplTest : SysuiTestCase() {
    companion object {
        @JvmStatic private val IMMEDIATE = Dispatchers.Main.immediate
    }

    private enum class LogoutUserResult {
        NONE,
        NON_SYSTEM_CURRENT,
    }
}
+7 −8
Original line number Diff line number Diff line
@@ -414,16 +414,15 @@ constructor(
        }
    }

    private suspend fun SelectedUserModel.isEligibleForLogout(): Boolean {
        return withContext(backgroundDispatcher) {
            selectionStatus == SelectionStatus.SELECTION_COMPLETE &&
                devicePolicyManager.logoutUser != null
        }
    }

    companion object {
        private const val TAG = "UserRepository"
        @VisibleForTesting const val SETTING_SIMPLE_USER_SWITCHER = "lockscreenSimpleUserSwitcher"
    }
}

fun SelectedUserModel.isEligibleForLogout(): Boolean {
    // TODO(b/206032495): should call mDevicePolicyManager.getLogoutUserId() instead of
    // hardcode it to USER_SYSTEM so it properly supports headless system user mode
    // (and then call mDevicePolicyManager.clearLogoutUser() after switched)
    return selectionStatus == SelectionStatus.SELECTION_COMPLETE &&
        userInfo.id != android.os.UserHandle.USER_SYSTEM
}