Merge "Fix data usage when policy has no cycle" into 24D1-dev am: bb90a2c5c8
Original change: https://googleplex-android-review.googlesource.com/c/platform/packages/apps/Settings/+/27209264 Change-Id: Ib349fb3eed75dc0d399d9a07355e170e30d1d985 Signed-off-by: Automerger Merge Worker <android-build-automerger-merge-worker@system.gserviceaccount.com>
This commit is contained in:
@@ -18,11 +18,10 @@ package com.android.settings.datausage.lib
|
|||||||
|
|
||||||
import android.content.Context
|
import android.content.Context
|
||||||
import android.net.NetworkTemplate
|
import android.net.NetworkTemplate
|
||||||
import android.text.format.DateUtils
|
|
||||||
import android.util.Range
|
import android.util.Range
|
||||||
|
import com.android.settings.datausage.lib.NetworkCycleDataRepository.Companion.asFourWeeks
|
||||||
import com.android.settings.datausage.lib.NetworkCycleDataRepository.Companion.bucketRange
|
import com.android.settings.datausage.lib.NetworkCycleDataRepository.Companion.bucketRange
|
||||||
import com.android.settings.datausage.lib.NetworkCycleDataRepository.Companion.getCycles
|
import com.android.settings.datausage.lib.NetworkCycleDataRepository.Companion.getCycles
|
||||||
import com.android.settings.datausage.lib.NetworkCycleDataRepository.Companion.reverseBucketRange
|
|
||||||
import com.android.settings.datausage.lib.NetworkStatsRepository.Companion.Bucket
|
import com.android.settings.datausage.lib.NetworkStatsRepository.Companion.Bucket
|
||||||
import com.android.settings.datausage.lib.NetworkStatsRepository.Companion.aggregate
|
import com.android.settings.datausage.lib.NetworkStatsRepository.Companion.aggregate
|
||||||
import com.android.settings.datausage.lib.NetworkStatsRepository.Companion.filterTime
|
import com.android.settings.datausage.lib.NetworkStatsRepository.Companion.filterTime
|
||||||
@@ -39,16 +38,11 @@ class NetworkCycleBucketRepository(
|
|||||||
getCycles().map { aggregateUsage(it) }.filter { it.usage > 0 }
|
getCycles().map { aggregateUsage(it) }.filter { it.usage > 0 }
|
||||||
|
|
||||||
private fun getCycles(): List<Range<Long>> =
|
private fun getCycles(): List<Range<Long>> =
|
||||||
networkCycleDataRepository.getPolicy()?.getCycles() ?: queryCyclesAsFourWeeks()
|
networkCycleDataRepository.getPolicy()?.getCycles().orEmpty()
|
||||||
|
.ifEmpty { queryCyclesAsFourWeeks() }
|
||||||
|
|
||||||
private fun queryCyclesAsFourWeeks(): List<Range<Long>> {
|
private fun queryCyclesAsFourWeeks(): List<Range<Long>> =
|
||||||
val timeRange = buckets.aggregate()?.timeRange ?: return emptyList()
|
buckets.aggregate()?.timeRange.asFourWeeks()
|
||||||
return reverseBucketRange(
|
|
||||||
startTime = timeRange.lower,
|
|
||||||
endTime = timeRange.upper,
|
|
||||||
step = DateUtils.WEEK_IN_MILLIS * 4,
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
fun queryChartData(usageData: NetworkUsageData) = NetworkCycleChartData(
|
fun queryChartData(usageData: NetworkUsageData) = NetworkCycleChartData(
|
||||||
total = usageData,
|
total = usageData,
|
||||||
|
@@ -42,16 +42,10 @@ class NetworkCycleDataRepository(
|
|||||||
fun loadFirstCycle(): NetworkUsageData? = getCycles().firstOrNull()?.let { queryUsage(it) }
|
fun loadFirstCycle(): NetworkUsageData? = getCycles().firstOrNull()?.let { queryUsage(it) }
|
||||||
|
|
||||||
override fun getCycles(): List<Range<Long>> =
|
override fun getCycles(): List<Range<Long>> =
|
||||||
getPolicy()?.getCycles() ?: queryCyclesAsFourWeeks()
|
getPolicy()?.getCycles().orEmpty().ifEmpty { queryCyclesAsFourWeeks() }
|
||||||
|
|
||||||
private fun queryCyclesAsFourWeeks(): List<Range<Long>> {
|
private fun queryCyclesAsFourWeeks(): List<Range<Long>> =
|
||||||
val timeRange = networkStatsRepository.getTimeRange() ?: return emptyList()
|
networkStatsRepository.getTimeRange().asFourWeeks()
|
||||||
return reverseBucketRange(
|
|
||||||
startTime = timeRange.lower,
|
|
||||||
endTime = timeRange.upper,
|
|
||||||
step = DateUtils.WEEK_IN_MILLIS * 4,
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun getPolicy(): NetworkPolicy? =
|
override fun getPolicy(): NetworkPolicy? =
|
||||||
with(NetworkPolicyEditor(policyManager)) {
|
with(NetworkPolicyEditor(policyManager)) {
|
||||||
@@ -59,7 +53,6 @@ class NetworkCycleDataRepository(
|
|||||||
getPolicy(networkTemplate)
|
getPolicy(networkTemplate)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
override fun queryUsage(range: Range<Long>) = NetworkUsageData(
|
override fun queryUsage(range: Range<Long>) = NetworkUsageData(
|
||||||
startTime = range.lower,
|
startTime = range.lower,
|
||||||
endTime = range.upper,
|
endTime = range.upper,
|
||||||
@@ -71,6 +64,15 @@ class NetworkCycleDataRepository(
|
|||||||
Range(it.lower.toInstant().toEpochMilli(), it.upper.toInstant().toEpochMilli())
|
Range(it.lower.toInstant().toEpochMilli(), it.upper.toInstant().toEpochMilli())
|
||||||
}.toList()
|
}.toList()
|
||||||
|
|
||||||
|
fun Range<Long>?.asFourWeeks(): List<Range<Long>> {
|
||||||
|
val timeRange = this ?: return emptyList()
|
||||||
|
return reverseBucketRange(
|
||||||
|
startTime = timeRange.lower,
|
||||||
|
endTime = timeRange.upper,
|
||||||
|
step = DateUtils.WEEK_IN_MILLIS * 4,
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
fun bucketRange(startTime: Long, endTime: Long, step: Long): List<Range<Long>> =
|
fun bucketRange(startTime: Long, endTime: Long, step: Long): List<Range<Long>> =
|
||||||
(startTime..endTime step step).zipWithNext(::Range)
|
(startTime..endTime step step).zipWithNext(::Range)
|
||||||
|
|
||||||
|
@@ -42,6 +42,13 @@ class NetworkCycleBucketRepositoryTest {
|
|||||||
|
|
||||||
private val mockNetworkCycleDataRepository = mock<NetworkCycleDataRepository>()
|
private val mockNetworkCycleDataRepository = mock<NetworkCycleDataRepository>()
|
||||||
|
|
||||||
|
private fun createRepository(buckets: List<Bucket>) = NetworkCycleBucketRepository(
|
||||||
|
context = context,
|
||||||
|
networkTemplate = template,
|
||||||
|
buckets = buckets,
|
||||||
|
networkCycleDataRepository = mockNetworkCycleDataRepository,
|
||||||
|
)
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
fun loadCycles_byPolicy() {
|
fun loadCycles_byPolicy() {
|
||||||
val policy = mock<NetworkPolicy> {
|
val policy = mock<NetworkPolicy> {
|
||||||
@@ -52,9 +59,7 @@ class NetworkCycleBucketRepositoryTest {
|
|||||||
mockNetworkCycleDataRepository.stub {
|
mockNetworkCycleDataRepository.stub {
|
||||||
on { getPolicy() } doReturn policy
|
on { getPolicy() } doReturn policy
|
||||||
}
|
}
|
||||||
val repository = NetworkCycleBucketRepository(
|
val repository = createRepository(
|
||||||
context = context,
|
|
||||||
networkTemplate = template,
|
|
||||||
buckets = listOf(
|
buckets = listOf(
|
||||||
Bucket(
|
Bucket(
|
||||||
uid = 0,
|
uid = 0,
|
||||||
@@ -62,8 +67,7 @@ class NetworkCycleBucketRepositoryTest {
|
|||||||
startTimeStamp = CYCLE1_START_TIME,
|
startTimeStamp = CYCLE1_START_TIME,
|
||||||
endTimeStamp = CYCLE1_END_TIME,
|
endTimeStamp = CYCLE1_END_TIME,
|
||||||
)
|
)
|
||||||
),
|
)
|
||||||
networkCycleDataRepository = mockNetworkCycleDataRepository,
|
|
||||||
)
|
)
|
||||||
|
|
||||||
val cycles = repository.loadCycles()
|
val cycles = repository.loadCycles()
|
||||||
@@ -78,13 +82,14 @@ class NetworkCycleBucketRepositoryTest {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
fun loadCycles_asFourWeeks() {
|
fun loadCycles_policyHasNoCycle_asFourWeeks() {
|
||||||
mockNetworkCycleDataRepository.stub {
|
val policy = mock<NetworkPolicy> {
|
||||||
on { getPolicy() } doReturn null
|
on { cycleIterator() } doReturn emptyList<Range<ZonedDateTime>>().iterator()
|
||||||
}
|
}
|
||||||
val repository = NetworkCycleBucketRepository(
|
mockNetworkCycleDataRepository.stub {
|
||||||
context = context,
|
on { getPolicy() } doReturn policy
|
||||||
networkTemplate = template,
|
}
|
||||||
|
val repository = createRepository(
|
||||||
buckets = listOf(
|
buckets = listOf(
|
||||||
Bucket(
|
Bucket(
|
||||||
uid = 0,
|
uid = 0,
|
||||||
@@ -92,8 +97,34 @@ class NetworkCycleBucketRepositoryTest {
|
|||||||
startTimeStamp = CYCLE2_START_TIME,
|
startTimeStamp = CYCLE2_START_TIME,
|
||||||
endTimeStamp = CYCLE2_END_TIME,
|
endTimeStamp = CYCLE2_END_TIME,
|
||||||
)
|
)
|
||||||
|
)
|
||||||
|
)
|
||||||
|
|
||||||
|
val cycles = repository.loadCycles()
|
||||||
|
|
||||||
|
assertThat(cycles).containsExactly(
|
||||||
|
NetworkUsageData(
|
||||||
|
startTime = CYCLE2_END_TIME - DateUtils.WEEK_IN_MILLIS * 4,
|
||||||
|
endTime = CYCLE2_END_TIME,
|
||||||
|
usage = CYCLE2_BYTES,
|
||||||
),
|
),
|
||||||
networkCycleDataRepository = mockNetworkCycleDataRepository,
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
fun loadCycles_noPolicy_asFourWeeks() {
|
||||||
|
mockNetworkCycleDataRepository.stub {
|
||||||
|
on { getPolicy() } doReturn null
|
||||||
|
}
|
||||||
|
val repository = createRepository(
|
||||||
|
buckets = listOf(
|
||||||
|
Bucket(
|
||||||
|
uid = 0,
|
||||||
|
bytes = CYCLE2_BYTES,
|
||||||
|
startTimeStamp = CYCLE2_START_TIME,
|
||||||
|
endTimeStamp = CYCLE2_END_TIME,
|
||||||
|
)
|
||||||
|
)
|
||||||
)
|
)
|
||||||
|
|
||||||
val cycles = repository.loadCycles()
|
val cycles = repository.loadCycles()
|
||||||
@@ -114,9 +145,7 @@ class NetworkCycleBucketRepositoryTest {
|
|||||||
endTime = CYCLE4_END_TIME,
|
endTime = CYCLE4_END_TIME,
|
||||||
usage = CYCLE3_BYTES + CYCLE4_BYTES,
|
usage = CYCLE3_BYTES + CYCLE4_BYTES,
|
||||||
)
|
)
|
||||||
val repository = NetworkCycleBucketRepository(
|
val repository = createRepository(
|
||||||
context = context,
|
|
||||||
networkTemplate = template,
|
|
||||||
buckets = listOf(
|
buckets = listOf(
|
||||||
Bucket(
|
Bucket(
|
||||||
uid = 0,
|
uid = 0,
|
||||||
@@ -131,7 +160,6 @@ class NetworkCycleBucketRepositoryTest {
|
|||||||
endTimeStamp = CYCLE4_END_TIME,
|
endTimeStamp = CYCLE4_END_TIME,
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
networkCycleDataRepository = mockNetworkCycleDataRepository,
|
|
||||||
)
|
)
|
||||||
|
|
||||||
val summary = repository.queryChartData(cycle)
|
val summary = repository.queryChartData(cycle)
|
||||||
|
@@ -25,6 +25,7 @@ import androidx.test.core.app.ApplicationProvider
|
|||||||
import androidx.test.ext.junit.runners.AndroidJUnit4
|
import androidx.test.ext.junit.runners.AndroidJUnit4
|
||||||
import com.android.settings.testutils.zonedDateTime
|
import com.android.settings.testutils.zonedDateTime
|
||||||
import com.google.common.truth.Truth.assertThat
|
import com.google.common.truth.Truth.assertThat
|
||||||
|
import java.time.ZonedDateTime
|
||||||
import kotlinx.coroutines.test.runTest
|
import kotlinx.coroutines.test.runTest
|
||||||
import org.junit.Test
|
import org.junit.Test
|
||||||
import org.junit.runner.RunWith
|
import org.junit.runner.RunWith
|
||||||
@@ -77,7 +78,28 @@ class NetworkCycleDataRepositoryTest {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
fun loadFirstCycle_asFourWeeks() = runTest {
|
fun loadFirstCycle_policyHasNoCycle_asFourWeeks() = runTest {
|
||||||
|
val policy = mock<NetworkPolicy> {
|
||||||
|
on { cycleIterator() } doReturn emptyList<Range<ZonedDateTime>>().iterator()
|
||||||
|
}
|
||||||
|
doReturn(policy).whenever(repository).getPolicy()
|
||||||
|
mockNetworkStatsRepository.stub {
|
||||||
|
on { getTimeRange() } doReturn Range(CYCLE2_START_TIME, CYCLE2_END_TIME)
|
||||||
|
}
|
||||||
|
|
||||||
|
val firstCycle = repository.loadFirstCycle()
|
||||||
|
|
||||||
|
assertThat(firstCycle).isEqualTo(
|
||||||
|
NetworkUsageData(
|
||||||
|
startTime = CYCLE2_END_TIME - DateUtils.WEEK_IN_MILLIS * 4,
|
||||||
|
endTime = CYCLE2_END_TIME,
|
||||||
|
usage = CYCLE2_BYTES,
|
||||||
|
),
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
fun loadFirstCycle_noPolicy_asFourWeeks() = runTest {
|
||||||
doReturn(null).whenever(repository).getPolicy()
|
doReturn(null).whenever(repository).getPolicy()
|
||||||
mockNetworkStatsRepository.stub {
|
mockNetworkStatsRepository.stub {
|
||||||
on { getTimeRange() } doReturn Range(CYCLE2_START_TIME, CYCLE2_END_TIME)
|
on { getTimeRange() } doReturn Range(CYCLE2_START_TIME, CYCLE2_END_TIME)
|
||||||
|
Reference in New Issue
Block a user