Skip to content

Commit

Permalink
Merge pull request #91 from ooni/test-details
Browse files Browse the repository at this point in the history
Test details
  • Loading branch information
sdsantos authored Sep 10, 2024
2 parents 327859e + fac3e5f commit 21d8e08
Show file tree
Hide file tree
Showing 18 changed files with 533 additions and 38 deletions.
Original file line number Diff line number Diff line change
@@ -1,6 +1,9 @@
<resources>
<string name="Dashboard_Tab_Label">Dashboard</string>
<string name="Dashboard_Overview_LatestTest">Last test: %1$s</string>
<string name="Dashboard_Overview_LatestTest">Last test:</string>
<string name="Dashboard_Overview_Estimated">Estimated:</string>
<string name="Dashboard_Overview_LastRun_Never">N/A</string>

<string name="Dashboard_Running_Running">Running:</string>
<string name="Dashboard_Running_EstimatedTimeLeft">Estimated time left:</string>
<string name="Dashboard_Running_Stopping_Title">Stopping test…</string>
Expand Down Expand Up @@ -46,6 +49,7 @@
<string name="Modal_EnableNotifications_Paragraph">Interested in running OONI Probe tests during emergent censorship events? Enable notifications to receive a message when we hear of internet censorship near you.</string>

<string name="Settings_TestOptions_Label">Test options</string>
<string name="Settings_TestOptions_LongRunningTest">Long running test</string>

<string name="Settings_AutomatedTesting_RunAutomatically">Run tests automatically</string>
<string name="Settings_AutomatedTesting_RunAutomatically_Number">Number of automated tests: %1$s.</string>
Expand Down Expand Up @@ -172,6 +176,7 @@
<string name="LoadingScreen_Runv2_Message">Link Loading</string>
<string name="LoadingScreen_Runv2_Failure">Error</string>
<string name="LoadingScreen_Runv2_Canceled">Link installation cancelled</string>

<!-- New Strings -->
<string name="back">Back</string>
<string name="refresh">refresh</string>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -134,7 +134,7 @@ sealed class TestType {
override val iconRes: DrawableResource = Res.drawable.test_websites
override val url: String = "https://ooni.org/nettest/web-connectivity"

override fun runtime(inputs: List<String>?) = 5.seconds * (inputs?.size ?: 1)
override fun runtime(inputs: List<String>?) = 5.seconds * (inputs?.ifEmpty { null }?.size ?: 30)
}

data object Whatsapp : TestType() {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ import androidx.compose.ui.graphics.Color
import kotlinx.datetime.LocalDateTime
import org.jetbrains.compose.resources.DrawableResource
import org.ooni.probe.shared.now
import kotlin.time.Duration.Companion.seconds

data class Descriptor(
val name: String,
Expand Down Expand Up @@ -35,4 +36,9 @@ data class Descriptor(
}

val allTests get() = netTests + longRunningTests

val estimatedDuration
get() = allTests
.sumOf { it.test.runtime(it.inputs).inWholeSeconds }
.seconds
}
Original file line number Diff line number Diff line change
Expand Up @@ -52,6 +52,13 @@ class ResultRepository(
.mapToOneOrNull(backgroundDispatcher)
.map { it?.toModel() }

fun getLatestByDescriptor(descriptorKey: String): Flow<ResultModel?> =
database.resultQueries
.selectLatestByDescriptor(descriptorKey)
.asFlow()
.mapToOneOrNull(backgroundDispatcher)
.map { it?.toModel() }

suspend fun createOrUpdate(model: ResultModel): ResultModel.Id =
withContext(backgroundDispatcher) {
database.transactionWithResult {
Expand Down
15 changes: 15 additions & 0 deletions composeApp/src/commonMain/kotlin/org/ooni/probe/di/Dependencies.kt
Original file line number Diff line number Diff line change
Expand Up @@ -60,6 +60,7 @@ import org.ooni.probe.domain.UploadMissingMeasurements
import org.ooni.probe.shared.PlatformInfo
import org.ooni.probe.ui.dashboard.DashboardViewModel
import org.ooni.probe.ui.descriptor.AddDescriptorViewModel
import org.ooni.probe.ui.descriptor.DescriptorViewModel
import org.ooni.probe.ui.result.ResultViewModel
import org.ooni.probe.ui.results.ResultsViewModel
import org.ooni.probe.ui.run.RunViewModel
Expand Down Expand Up @@ -257,15 +258,29 @@ class Dependencies(
goToResults: () -> Unit,
goToRunningTest: () -> Unit,
goToRunTests: () -> Unit,
goToDescriptor: (String) -> Unit,
) = DashboardViewModel(
goToResults = goToResults,
goToRunningTest = goToRunningTest,
goToRunTests = goToRunTests,
goToDescriptor = goToDescriptor,
getTestDescriptors = getTestDescriptors::invoke,
observeTestRunState = testStateManager.observeState(),
observeTestRunErrors = testStateManager.observeError(),
)

fun descriptorViewModel(
descriptorKey: String,
onBack: () -> Unit,
) = DescriptorViewModel(
descriptorKey = descriptorKey,
onBack = onBack,
getTestDescriptors = getTestDescriptors::invoke,
getDescriptorLastResult = resultRepository::getLatestByDescriptor,
preferenceRepository = preferenceRepository,
launchUrl = { launchUrl(it, null) },
)

fun proxyViewModel(onBack: () -> Unit) = ProxyViewModel(onBack, preferenceRepository)

fun resultsViewModel(
Expand Down
Original file line number Diff line number Diff line change
@@ -1,9 +1,12 @@
package org.ooni.probe.domain

import androidx.compose.runtime.Composable
import kotlinx.coroutines.flow.Flow
import kotlinx.coroutines.flow.asFlow
import kotlinx.coroutines.flow.flatMapLatest
import kotlinx.coroutines.flow.map
import ooniprobe.composeapp.generated.resources.Res
import ooniprobe.composeapp.generated.resources.Settings_TestOptions_LongRunningTest
import org.jetbrains.compose.resources.stringResource
import org.ooni.probe.data.models.DefaultTestDescriptor
import org.ooni.probe.data.models.Descriptor
Expand Down Expand Up @@ -31,7 +34,13 @@ class GetTestDescriptors(
name = label,
title = { stringResource(title) },
shortDescription = { stringResource(shortDescription) },
description = { stringResource(description) },
description = {
if (label == "experimental") {
stringResource(description, experimentalLinks())
} else {
stringResource(description)
}
},
icon = icon,
color = color,
animation = animation,
Expand All @@ -41,4 +50,17 @@ class GetTestDescriptors(
longRunningTests = longRunningTests,
source = Descriptor.Source.Default(this),
)

@Composable
private fun experimentalLinks() =
"""
* [STUN Reachability](https://github.com/ooni/spec/blob/master/nettests/ts-025-stun-reachability.md)
* [DNS Check](https://github.com/ooni/spec/blob/master/nettests/ts-028-dnscheck.md)
* [RiseupVPN](https://ooni.org/nettest/riseupvpn/)
* [ECH Check](https://github.com/ooni/spec/blob/master/nettests/ts-039-echcheck.md)
* [Tor Snowflake](https://ooni.org/nettest/tor-snowflake/) (${stringResource(Res.string.Settings_TestOptions_LongRunningTest)})
* [Vanilla Tor](https://github.com/ooni/spec/blob/master/nettests/ts-016-vanilla-tor.md) (${stringResource(
Res.string.Settings_TestOptions_LongRunningTest,
)})
""".trimIndent()
}
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,6 @@ import org.ooni.probe.data.models.TestRunState
import org.ooni.probe.data.models.UrlModel
import org.ooni.probe.shared.now
import kotlin.time.Duration
import kotlin.time.Duration.Companion.seconds

class RunDescriptors(
private val getTestDescriptorsBySpec: suspend (RunSpecification) -> List<Descriptor>,
Expand Down Expand Up @@ -115,10 +114,7 @@ class RunDescriptors(
private suspend fun List<Descriptor>.getEstimatedRuntime(): List<Duration> {
val maxRuntime = getEnginePreferences().maxRuntime
return map { descriptor ->
descriptor.netTests
.sumOf { it.test.runtime(it.inputs).inWholeSeconds }
.seconds
.coerceAtMost(maxRuntime ?: Duration.INFINITE)
descriptor.estimatedDuration.coerceAtMost(maxRuntime ?: Duration.INFINITE)
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ package org.ooni.probe.ui.dashboard
import androidx.compose.foundation.Image
import androidx.compose.foundation.clickable
import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.PaddingValues
import androidx.compose.foundation.layout.Row
import androidx.compose.foundation.layout.WindowInsets
import androidx.compose.foundation.layout.asPaddingValues
Expand Down Expand Up @@ -69,16 +70,22 @@ fun DashboardScreen(

LazyColumn(
modifier = Modifier.padding(top = 24.dp),
contentPadding = PaddingValues(bottom = 16.dp),
) {
val allSectionsHaveValues = state.tests.entries.all { it.value.any() }
state.tests.forEach { (type, tests) ->
if (allSectionsHaveValues && tests.isNotEmpty()) {
val allSectionsHaveValues = state.descriptors.entries.all { it.value.any() }
state.descriptors.forEach { (type, items) ->
if (allSectionsHaveValues && items.isNotEmpty()) {
item(type) {
TestDescriptorSection(type)
}
}
items(tests, key = { it.key }) { test ->
TestDescriptorItem(test)
items(items, key = { it.key }) { descriptor ->
TestDescriptorItem(
descriptor = descriptor,
onClick = {
onEvent(DashboardViewModel.Event.DescriptorClicked(descriptor))
},
)
}
}
}
Expand Down Expand Up @@ -113,10 +120,8 @@ private fun TestRunStateSection(
}
state.lastTestAt?.let { lastTestAt ->
Text(
text = stringResource(
Res.string.Dashboard_Overview_LatestTest,
lastTestAt.relativeDateTime(),
),
text = stringResource(Res.string.Dashboard_Overview_LatestTest) +
" " + lastTestAt.relativeDateTime(),
style = MaterialTheme.typography.labelLarge,
modifier = Modifier.padding(top = 4.dp),
)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@ class DashboardViewModel(
goToResults: () -> Unit,
goToRunningTest: () -> Unit,
goToRunTests: () -> Unit,
goToDescriptor: (String) -> Unit,
getTestDescriptors: () -> Flow<List<Descriptor>>,
observeTestRunState: Flow<TestRunState>,
observeTestRunErrors: Flow<TestRunError>,
Expand All @@ -31,7 +32,7 @@ class DashboardViewModel(
init {
getTestDescriptors()
.onEach { tests ->
_state.update { it.copy(tests = tests.groupByType()) }
_state.update { it.copy(descriptors = tests.groupByType()) }
}
.launchIn(viewModelScope)

Expand Down Expand Up @@ -68,6 +69,11 @@ class DashboardViewModel(
_state.update { it.copy(testRunErrors = it.testRunErrors - event.error) }
}
.launchIn(viewModelScope)

events
.filterIsInstance<Event.DescriptorClicked>()
.onEach { goToDescriptor(it.descriptor.key) }
.launchIn(viewModelScope)
}

fun onEvent(event: Event) {
Expand All @@ -81,7 +87,7 @@ class DashboardViewModel(
)

data class State(
val tests: Map<DescriptorType, List<Descriptor>> = emptyMap(),
val descriptors: Map<DescriptorType, List<Descriptor>> = emptyMap(),
val testRunState: TestRunState = TestRunState.Idle(),
val testRunErrors: List<TestRunError> = emptyList(),
)
Expand All @@ -94,5 +100,7 @@ class DashboardViewModel(
data object SeeResultsClick : Event

data class ErrorDisplayed(val error: TestRunError) : Event

data class DescriptorClicked(val descriptor: Descriptor) : Event
}
}
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
package org.ooni.probe.ui.dashboard

import androidx.compose.foundation.clickable
import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.Row
import androidx.compose.foundation.layout.fillMaxWidth
Expand All @@ -17,10 +18,14 @@ import org.jetbrains.compose.resources.painterResource
import org.ooni.probe.data.models.Descriptor

@Composable
fun TestDescriptorItem(descriptor: Descriptor) {
fun TestDescriptorItem(
descriptor: Descriptor,
onClick: () -> Unit,
) {
Card(
Modifier
.padding(horizontal = 16.dp, vertical = 4.dp),
.padding(horizontal = 16.dp, vertical = 4.dp)
.clickable { onClick() },
) {
Row(
verticalAlignment = Alignment.CenterVertically,
Expand Down
Loading

0 comments on commit 21d8e08

Please sign in to comment.