Loading src/com/android/settings/datausage/DataUsageSummaryPreferenceController.kt +19 −20 Original line number Diff line number Diff line Loading @@ -21,20 +21,18 @@ import android.net.NetworkPolicy import android.net.NetworkTemplate import android.text.TextUtils import android.util.Log import androidx.lifecycle.Lifecycle import androidx.lifecycle.LifecycleOwner import androidx.lifecycle.lifecycleScope import androidx.lifecycle.repeatOnLifecycle import androidx.preference.PreferenceScreen import com.android.settings.R import com.android.settings.datausage.lib.DataUsageLib.getMobileTemplate import com.android.settings.datausage.lib.INetworkCycleDataRepository import com.android.settings.datausage.lib.NetworkCycleDataRepository import com.android.settings.network.ProxySubscriptionManager import com.android.settings.network.policy.NetworkPolicyRepository import com.android.settings.network.telephony.TelephonyBasePreferenceController import com.android.settingslib.spa.framework.util.collectLatestWithLifecycle import kotlin.math.max import kotlinx.coroutines.Dispatchers import kotlinx.coroutines.launch import kotlinx.coroutines.withContext /** Loading @@ -47,6 +45,7 @@ open class DataUsageSummaryPreferenceController @JvmOverloads constructor( subId: Int, private val proxySubscriptionManager: ProxySubscriptionManager = ProxySubscriptionManager.getInstance(context), private val networkPolicyRepository: NetworkPolicyRepository = NetworkPolicyRepository(context), private val networkCycleDataRepositoryFactory: ( template: NetworkTemplate, ) -> INetworkCycleDataRepository = { NetworkCycleDataRepository(context, it) }, Loading @@ -64,37 +63,37 @@ open class DataUsageSummaryPreferenceController @JvmOverloads constructor( proxySubscriptionManager.getAccessibleSubscriptionInfo(mSubId) } else null } private val networkTemplate by lazy { getMobileTemplate(mContext, mSubId) } private val networkCycleDataRepository by lazy { networkCycleDataRepositoryFactory(getMobileTemplate(mContext, mSubId)) networkCycleDataRepositoryFactory(networkTemplate) } private val policy by lazy { networkCycleDataRepository.getPolicy() } private lateinit var preference: DataUsageSummaryPreference override fun getAvailabilityStatus(subId: Int) = if (subInfo != null && policy != null) AVAILABLE else CONDITIONALLY_UNAVAILABLE if (subInfo != null) AVAILABLE else CONDITIONALLY_UNAVAILABLE override fun displayPreference(screen: PreferenceScreen) { super.displayPreference(screen) preference = screen.findPreference(preferenceKey)!! policy?.let { preference.setLimitInfo(it.getLimitInfo()) val dataBarSize = max(it.limitBytes, it.warningBytes) if (dataBarSize > NetworkPolicy.WARNING_DISABLED) { setDataBarSize(dataBarSize) } } } override fun onViewCreated(viewLifecycleOwner: LifecycleOwner) { viewLifecycleOwner.lifecycleScope.launch { viewLifecycleOwner.repeatOnLifecycle(Lifecycle.State.STARTED) { update() } networkPolicyRepository.networkPolicyFlow(networkTemplate) .collectLatestWithLifecycle(viewLifecycleOwner) { policy -> preference.isVisible = subInfo != null && policy != null if (policy != null) update(policy) } } private suspend fun update() { val policy = policy ?: return private suspend fun update(policy: NetworkPolicy) { preference.setLimitInfo(policy.getLimitInfo()) val dataBarSize = max(policy.limitBytes, policy.warningBytes) if (dataBarSize > NetworkPolicy.WARNING_DISABLED) { setDataBarSize(dataBarSize) } val dataPlanInfo = withContext(Dispatchers.Default) { dataPlanRepositoryFactory(networkCycleDataRepository).getDataPlanInfo( policy = policy, Loading src/com/android/settings/network/policy/NetworkPolicyRepository.kt 0 → 100644 +37 −0 Original line number Diff line number Diff line /* * Copyright (C) 2024 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package com.android.settings.network.policy import android.content.Context import android.net.NetworkPolicy import android.net.NetworkPolicyManager import android.net.NetworkTemplate import kotlinx.coroutines.Dispatchers import kotlinx.coroutines.flow.Flow import kotlinx.coroutines.flow.flow import kotlinx.coroutines.flow.flowOn class NetworkPolicyRepository(context: Context) { private val networkPolicyManager = context.getSystemService(NetworkPolicyManager::class.java)!! fun getNetworkPolicy(networkTemplate: NetworkTemplate): NetworkPolicy? = networkPolicyManager.networkPolicies.find { policy -> policy.template == networkTemplate } fun networkPolicyFlow(networkTemplate: NetworkTemplate): Flow<NetworkPolicy?> = flow { emit(getNetworkPolicy(networkTemplate)) }.flowOn(Dispatchers.Default) } tests/spa_unit/src/com/android/settings/datausage/DataUsageSummaryPreferenceControllerTest.kt +31 −14 Original line number Diff line number Diff line Loading @@ -32,8 +32,10 @@ import com.android.settings.core.BasePreferenceController.CONDITIONALLY_UNAVAILA import com.android.settings.datausage.lib.INetworkCycleDataRepository import com.android.settings.datausage.lib.NetworkUsageData import com.android.settings.network.ProxySubscriptionManager import com.android.settings.network.policy.NetworkPolicyRepository import com.google.common.truth.Truth.assertThat import kotlinx.coroutines.delay import kotlinx.coroutines.flow.flowOf import kotlinx.coroutines.runBlocking import org.junit.Before import org.junit.Test Loading @@ -41,6 +43,7 @@ import org.junit.runner.RunWith import org.mockito.kotlin.any import org.mockito.kotlin.argumentCaptor import org.mockito.kotlin.clearInvocations import org.mockito.kotlin.doAnswer import org.mockito.kotlin.doReturn import org.mockito.kotlin.mock import org.mockito.kotlin.never Loading Loading @@ -69,6 +72,10 @@ class DataUsageSummaryPreferenceControllerTest { on { get() } doReturn mockSubscriptionManager } private val mockNetworkPolicyRepository = mock<NetworkPolicyRepository> { on { networkPolicyFlow(any()) } doAnswer { flowOf(policy) } } private val fakeNetworkCycleDataRepository = object : INetworkCycleDataRepository { override fun getCycles(): List<Range<Long>> = emptyList() override fun getPolicy() = policy Loading @@ -86,6 +93,7 @@ class DataUsageSummaryPreferenceControllerTest { context = context, subId = SUB_ID, proxySubscriptionManager = mockProxySubscriptionManager, networkPolicyRepository = mockNetworkPolicyRepository, networkCycleDataRepositoryFactory = { fakeNetworkCycleDataRepository }, dataPlanRepositoryFactory = { fakeDataPlanRepository }, ) Loading @@ -112,7 +120,7 @@ class DataUsageSummaryPreferenceControllerTest { } @Test fun getAvailabilityStatus_hasSubInfoAndPolicy_available() { fun getAvailabilityStatus_hasSubInfo_available() { mockProxySubscriptionManager.stub { on { getAccessibleSubscriptionInfo(SUB_ID) } doReturn SubscriptionInfo.Builder().build() } Loading @@ -134,36 +142,43 @@ class DataUsageSummaryPreferenceControllerTest { } @Test fun getAvailabilityStatus_noPolicy_conditionallyUnavailable() { fun onViewCreated_noPolicy_setInvisible() = runBlocking { policy = null controller.displayPreference(preferenceScreen) clearInvocations(preference) val availabilityStatus = controller.getAvailabilityStatus(SUB_ID) controller.onViewCreated(TestLifecycleOwner()) delay(100) assertThat(availabilityStatus).isEqualTo(CONDITIONALLY_UNAVAILABLE) verify(preference).isVisible = false } @Test fun displayPreference_policyHasNoLimitInfo() { fun onViewCreated_policyHasNoLimitInfo() = runBlocking { policy = mock<NetworkPolicy>().apply { warningBytes = NetworkPolicy.WARNING_DISABLED limitBytes = NetworkPolicy.LIMIT_DISABLED } controller.displayPreference(preferenceScreen) controller.onViewCreated(TestLifecycleOwner()) delay(100) verify(preference).setLimitInfo(null) verify(preference, never()).setLabels(any(), any()) } @Test fun displayPreference_policyWarningOnly() { fun onViewCreated_policyWarningOnly() = runBlocking { policy = mock<NetworkPolicy>().apply { warningBytes = 1L limitBytes = NetworkPolicy.LIMIT_DISABLED } controller.displayPreference(preferenceScreen) controller.onViewCreated(TestLifecycleOwner()) delay(100) val limitInfo = argumentCaptor { verify(preference).setLimitInfo(capture()) }.firstValue.toString() Loading @@ -172,14 +187,16 @@ class DataUsageSummaryPreferenceControllerTest { } @Test fun displayPreference_policyLimitOnly() { fun onViewCreated_policyLimitOnly() = runBlocking { policy = mock<NetworkPolicy>().apply { warningBytes = NetworkPolicy.WARNING_DISABLED limitBytes = 1L } controller.displayPreference(preferenceScreen) controller.onViewCreated(TestLifecycleOwner()) delay(100) val limitInfo = argumentCaptor { verify(preference).setLimitInfo(capture()) }.firstValue.toString() Loading @@ -188,14 +205,16 @@ class DataUsageSummaryPreferenceControllerTest { } @Test fun displayPreference_policyHasWarningAndLimit() { fun onViewCreated_policyHasWarningAndLimit() = runBlocking { policy = mock<NetworkPolicy>().apply { warningBytes = BillingCycleSettings.GIB_IN_BYTES / 2 limitBytes = BillingCycleSettings.GIB_IN_BYTES } controller.displayPreference(preferenceScreen) controller.onViewCreated(TestLifecycleOwner()) delay(100) val limitInfo = argumentCaptor { verify(preference).setLimitInfo(capture()) }.firstValue.toString() Loading @@ -207,7 +226,6 @@ class DataUsageSummaryPreferenceControllerTest { fun onViewCreated_emptyDataPlanInfo() = runBlocking { dataPlanInfo = EMPTY_DATA_PLAN_INFO controller.displayPreference(preferenceScreen) clearInvocations(preference) controller.onViewCreated(TestLifecycleOwner()) delay(100) Loading @@ -229,7 +247,6 @@ class DataUsageSummaryPreferenceControllerTest { fun onViewCreated_positiveDataPlanInfo() = runBlocking { dataPlanInfo = POSITIVE_DATA_PLAN_INFO controller.displayPreference(preferenceScreen) clearInvocations(preference) controller.onViewCreated(TestLifecycleOwner()) delay(100) Loading tests/spa_unit/src/com/android/settings/network/policy/NetworkPolicyRepositoryTest.kt 0 → 100644 +72 −0 Original line number Diff line number Diff line /* * Copyright (C) 2024 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package com.android.settings.network.policy import android.content.Context import android.net.NetworkPolicy import android.net.NetworkPolicyManager import android.net.NetworkTemplate import androidx.test.core.app.ApplicationProvider import androidx.test.ext.junit.runners.AndroidJUnit4 import com.android.settingslib.spa.testutils.firstWithTimeoutOrNull import com.google.common.truth.Truth.assertThat import kotlinx.coroutines.runBlocking import org.junit.Test import org.junit.runner.RunWith import org.mockito.kotlin.doReturn import org.mockito.kotlin.mock import org.mockito.kotlin.spy @RunWith(AndroidJUnit4::class) class NetworkPolicyRepositoryTest { private val mockNetworkPolicyManager = mock<NetworkPolicyManager> { on { networkPolicies } doReturn arrayOf(Policy1, Policy2) } private val context: Context = spy(ApplicationProvider.getApplicationContext()) { on { getSystemService(NetworkPolicyManager::class.java) } doReturn mockNetworkPolicyManager } private val repository = NetworkPolicyRepository(context) @Test fun getNetworkPolicy() { val networkPolicy = repository.getNetworkPolicy(Template1) assertThat(networkPolicy).isSameInstanceAs(Policy1) } @Test fun networkPolicyFlow() = runBlocking { val networkPolicy = repository.networkPolicyFlow(Template2).firstWithTimeoutOrNull() assertThat(networkPolicy).isSameInstanceAs(Policy2) } private companion object { val Template1: NetworkTemplate = NetworkTemplate.Builder(NetworkTemplate.MATCH_MOBILE).build() val Template2: NetworkTemplate = NetworkTemplate.Builder(NetworkTemplate.MATCH_WIFI).build() val Policy1 = mock<NetworkPolicy>().apply { template = Template1 } val Policy2 = mock<NetworkPolicy>().apply { template = Template2 } } } Loading
src/com/android/settings/datausage/DataUsageSummaryPreferenceController.kt +19 −20 Original line number Diff line number Diff line Loading @@ -21,20 +21,18 @@ import android.net.NetworkPolicy import android.net.NetworkTemplate import android.text.TextUtils import android.util.Log import androidx.lifecycle.Lifecycle import androidx.lifecycle.LifecycleOwner import androidx.lifecycle.lifecycleScope import androidx.lifecycle.repeatOnLifecycle import androidx.preference.PreferenceScreen import com.android.settings.R import com.android.settings.datausage.lib.DataUsageLib.getMobileTemplate import com.android.settings.datausage.lib.INetworkCycleDataRepository import com.android.settings.datausage.lib.NetworkCycleDataRepository import com.android.settings.network.ProxySubscriptionManager import com.android.settings.network.policy.NetworkPolicyRepository import com.android.settings.network.telephony.TelephonyBasePreferenceController import com.android.settingslib.spa.framework.util.collectLatestWithLifecycle import kotlin.math.max import kotlinx.coroutines.Dispatchers import kotlinx.coroutines.launch import kotlinx.coroutines.withContext /** Loading @@ -47,6 +45,7 @@ open class DataUsageSummaryPreferenceController @JvmOverloads constructor( subId: Int, private val proxySubscriptionManager: ProxySubscriptionManager = ProxySubscriptionManager.getInstance(context), private val networkPolicyRepository: NetworkPolicyRepository = NetworkPolicyRepository(context), private val networkCycleDataRepositoryFactory: ( template: NetworkTemplate, ) -> INetworkCycleDataRepository = { NetworkCycleDataRepository(context, it) }, Loading @@ -64,37 +63,37 @@ open class DataUsageSummaryPreferenceController @JvmOverloads constructor( proxySubscriptionManager.getAccessibleSubscriptionInfo(mSubId) } else null } private val networkTemplate by lazy { getMobileTemplate(mContext, mSubId) } private val networkCycleDataRepository by lazy { networkCycleDataRepositoryFactory(getMobileTemplate(mContext, mSubId)) networkCycleDataRepositoryFactory(networkTemplate) } private val policy by lazy { networkCycleDataRepository.getPolicy() } private lateinit var preference: DataUsageSummaryPreference override fun getAvailabilityStatus(subId: Int) = if (subInfo != null && policy != null) AVAILABLE else CONDITIONALLY_UNAVAILABLE if (subInfo != null) AVAILABLE else CONDITIONALLY_UNAVAILABLE override fun displayPreference(screen: PreferenceScreen) { super.displayPreference(screen) preference = screen.findPreference(preferenceKey)!! policy?.let { preference.setLimitInfo(it.getLimitInfo()) val dataBarSize = max(it.limitBytes, it.warningBytes) if (dataBarSize > NetworkPolicy.WARNING_DISABLED) { setDataBarSize(dataBarSize) } } } override fun onViewCreated(viewLifecycleOwner: LifecycleOwner) { viewLifecycleOwner.lifecycleScope.launch { viewLifecycleOwner.repeatOnLifecycle(Lifecycle.State.STARTED) { update() } networkPolicyRepository.networkPolicyFlow(networkTemplate) .collectLatestWithLifecycle(viewLifecycleOwner) { policy -> preference.isVisible = subInfo != null && policy != null if (policy != null) update(policy) } } private suspend fun update() { val policy = policy ?: return private suspend fun update(policy: NetworkPolicy) { preference.setLimitInfo(policy.getLimitInfo()) val dataBarSize = max(policy.limitBytes, policy.warningBytes) if (dataBarSize > NetworkPolicy.WARNING_DISABLED) { setDataBarSize(dataBarSize) } val dataPlanInfo = withContext(Dispatchers.Default) { dataPlanRepositoryFactory(networkCycleDataRepository).getDataPlanInfo( policy = policy, Loading
src/com/android/settings/network/policy/NetworkPolicyRepository.kt 0 → 100644 +37 −0 Original line number Diff line number Diff line /* * Copyright (C) 2024 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package com.android.settings.network.policy import android.content.Context import android.net.NetworkPolicy import android.net.NetworkPolicyManager import android.net.NetworkTemplate import kotlinx.coroutines.Dispatchers import kotlinx.coroutines.flow.Flow import kotlinx.coroutines.flow.flow import kotlinx.coroutines.flow.flowOn class NetworkPolicyRepository(context: Context) { private val networkPolicyManager = context.getSystemService(NetworkPolicyManager::class.java)!! fun getNetworkPolicy(networkTemplate: NetworkTemplate): NetworkPolicy? = networkPolicyManager.networkPolicies.find { policy -> policy.template == networkTemplate } fun networkPolicyFlow(networkTemplate: NetworkTemplate): Flow<NetworkPolicy?> = flow { emit(getNetworkPolicy(networkTemplate)) }.flowOn(Dispatchers.Default) }
tests/spa_unit/src/com/android/settings/datausage/DataUsageSummaryPreferenceControllerTest.kt +31 −14 Original line number Diff line number Diff line Loading @@ -32,8 +32,10 @@ import com.android.settings.core.BasePreferenceController.CONDITIONALLY_UNAVAILA import com.android.settings.datausage.lib.INetworkCycleDataRepository import com.android.settings.datausage.lib.NetworkUsageData import com.android.settings.network.ProxySubscriptionManager import com.android.settings.network.policy.NetworkPolicyRepository import com.google.common.truth.Truth.assertThat import kotlinx.coroutines.delay import kotlinx.coroutines.flow.flowOf import kotlinx.coroutines.runBlocking import org.junit.Before import org.junit.Test Loading @@ -41,6 +43,7 @@ import org.junit.runner.RunWith import org.mockito.kotlin.any import org.mockito.kotlin.argumentCaptor import org.mockito.kotlin.clearInvocations import org.mockito.kotlin.doAnswer import org.mockito.kotlin.doReturn import org.mockito.kotlin.mock import org.mockito.kotlin.never Loading Loading @@ -69,6 +72,10 @@ class DataUsageSummaryPreferenceControllerTest { on { get() } doReturn mockSubscriptionManager } private val mockNetworkPolicyRepository = mock<NetworkPolicyRepository> { on { networkPolicyFlow(any()) } doAnswer { flowOf(policy) } } private val fakeNetworkCycleDataRepository = object : INetworkCycleDataRepository { override fun getCycles(): List<Range<Long>> = emptyList() override fun getPolicy() = policy Loading @@ -86,6 +93,7 @@ class DataUsageSummaryPreferenceControllerTest { context = context, subId = SUB_ID, proxySubscriptionManager = mockProxySubscriptionManager, networkPolicyRepository = mockNetworkPolicyRepository, networkCycleDataRepositoryFactory = { fakeNetworkCycleDataRepository }, dataPlanRepositoryFactory = { fakeDataPlanRepository }, ) Loading @@ -112,7 +120,7 @@ class DataUsageSummaryPreferenceControllerTest { } @Test fun getAvailabilityStatus_hasSubInfoAndPolicy_available() { fun getAvailabilityStatus_hasSubInfo_available() { mockProxySubscriptionManager.stub { on { getAccessibleSubscriptionInfo(SUB_ID) } doReturn SubscriptionInfo.Builder().build() } Loading @@ -134,36 +142,43 @@ class DataUsageSummaryPreferenceControllerTest { } @Test fun getAvailabilityStatus_noPolicy_conditionallyUnavailable() { fun onViewCreated_noPolicy_setInvisible() = runBlocking { policy = null controller.displayPreference(preferenceScreen) clearInvocations(preference) val availabilityStatus = controller.getAvailabilityStatus(SUB_ID) controller.onViewCreated(TestLifecycleOwner()) delay(100) assertThat(availabilityStatus).isEqualTo(CONDITIONALLY_UNAVAILABLE) verify(preference).isVisible = false } @Test fun displayPreference_policyHasNoLimitInfo() { fun onViewCreated_policyHasNoLimitInfo() = runBlocking { policy = mock<NetworkPolicy>().apply { warningBytes = NetworkPolicy.WARNING_DISABLED limitBytes = NetworkPolicy.LIMIT_DISABLED } controller.displayPreference(preferenceScreen) controller.onViewCreated(TestLifecycleOwner()) delay(100) verify(preference).setLimitInfo(null) verify(preference, never()).setLabels(any(), any()) } @Test fun displayPreference_policyWarningOnly() { fun onViewCreated_policyWarningOnly() = runBlocking { policy = mock<NetworkPolicy>().apply { warningBytes = 1L limitBytes = NetworkPolicy.LIMIT_DISABLED } controller.displayPreference(preferenceScreen) controller.onViewCreated(TestLifecycleOwner()) delay(100) val limitInfo = argumentCaptor { verify(preference).setLimitInfo(capture()) }.firstValue.toString() Loading @@ -172,14 +187,16 @@ class DataUsageSummaryPreferenceControllerTest { } @Test fun displayPreference_policyLimitOnly() { fun onViewCreated_policyLimitOnly() = runBlocking { policy = mock<NetworkPolicy>().apply { warningBytes = NetworkPolicy.WARNING_DISABLED limitBytes = 1L } controller.displayPreference(preferenceScreen) controller.onViewCreated(TestLifecycleOwner()) delay(100) val limitInfo = argumentCaptor { verify(preference).setLimitInfo(capture()) }.firstValue.toString() Loading @@ -188,14 +205,16 @@ class DataUsageSummaryPreferenceControllerTest { } @Test fun displayPreference_policyHasWarningAndLimit() { fun onViewCreated_policyHasWarningAndLimit() = runBlocking { policy = mock<NetworkPolicy>().apply { warningBytes = BillingCycleSettings.GIB_IN_BYTES / 2 limitBytes = BillingCycleSettings.GIB_IN_BYTES } controller.displayPreference(preferenceScreen) controller.onViewCreated(TestLifecycleOwner()) delay(100) val limitInfo = argumentCaptor { verify(preference).setLimitInfo(capture()) }.firstValue.toString() Loading @@ -207,7 +226,6 @@ class DataUsageSummaryPreferenceControllerTest { fun onViewCreated_emptyDataPlanInfo() = runBlocking { dataPlanInfo = EMPTY_DATA_PLAN_INFO controller.displayPreference(preferenceScreen) clearInvocations(preference) controller.onViewCreated(TestLifecycleOwner()) delay(100) Loading @@ -229,7 +247,6 @@ class DataUsageSummaryPreferenceControllerTest { fun onViewCreated_positiveDataPlanInfo() = runBlocking { dataPlanInfo = POSITIVE_DATA_PLAN_INFO controller.displayPreference(preferenceScreen) clearInvocations(preference) controller.onViewCreated(TestLifecycleOwner()) delay(100) Loading
tests/spa_unit/src/com/android/settings/network/policy/NetworkPolicyRepositoryTest.kt 0 → 100644 +72 −0 Original line number Diff line number Diff line /* * Copyright (C) 2024 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package com.android.settings.network.policy import android.content.Context import android.net.NetworkPolicy import android.net.NetworkPolicyManager import android.net.NetworkTemplate import androidx.test.core.app.ApplicationProvider import androidx.test.ext.junit.runners.AndroidJUnit4 import com.android.settingslib.spa.testutils.firstWithTimeoutOrNull import com.google.common.truth.Truth.assertThat import kotlinx.coroutines.runBlocking import org.junit.Test import org.junit.runner.RunWith import org.mockito.kotlin.doReturn import org.mockito.kotlin.mock import org.mockito.kotlin.spy @RunWith(AndroidJUnit4::class) class NetworkPolicyRepositoryTest { private val mockNetworkPolicyManager = mock<NetworkPolicyManager> { on { networkPolicies } doReturn arrayOf(Policy1, Policy2) } private val context: Context = spy(ApplicationProvider.getApplicationContext()) { on { getSystemService(NetworkPolicyManager::class.java) } doReturn mockNetworkPolicyManager } private val repository = NetworkPolicyRepository(context) @Test fun getNetworkPolicy() { val networkPolicy = repository.getNetworkPolicy(Template1) assertThat(networkPolicy).isSameInstanceAs(Policy1) } @Test fun networkPolicyFlow() = runBlocking { val networkPolicy = repository.networkPolicyFlow(Template2).firstWithTimeoutOrNull() assertThat(networkPolicy).isSameInstanceAs(Policy2) } private companion object { val Template1: NetworkTemplate = NetworkTemplate.Builder(NetworkTemplate.MATCH_MOBILE).build() val Template2: NetworkTemplate = NetworkTemplate.Builder(NetworkTemplate.MATCH_WIFI).build() val Policy1 = mock<NetworkPolicy>().apply { template = Template1 } val Policy2 = mock<NetworkPolicy>().apply { template = Template2 } } }