diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index ed1bced..c5b3ece 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -22,7 +22,7 @@ concurrency: jobs: build-and-test: name: Build and test - runs-on: ubuntu-latest + runs-on: ubuntu-24.04 steps: - name: Check out repository @@ -38,7 +38,7 @@ jobs: - name: Set up Android SDK uses: android-actions/setup-android@v4 with: - packages: 'platforms;android-37 build-tools;36.0.0' + packages: 'platforms;android-37.0 build-tools;36.0.0' - name: Set up Gradle uses: gradle/actions/setup-gradle@v6 diff --git a/.idea/shelf/Default.xml b/.idea/shelf/Default.xml new file mode 100644 index 0000000..469c9ad --- /dev/null +++ b/.idea/shelf/Default.xml @@ -0,0 +1,4 @@ + + \ No newline at end of file diff --git a/.idea/shelf/Default/shelved.patch b/.idea/shelf/Default/shelved.patch new file mode 100644 index 0000000..8f3c1d3 --- /dev/null +++ b/.idea/shelf/Default/shelved.patch @@ -0,0 +1,1112 @@ +Index: app/src/test/java/ru/svolf/convertx/data/entity/PaletteTest.kt +IDEA additional info: +Subsystem: com.intellij.openapi.diff.impl.patch.CharsetEP +<+>UTF-8 +=================================================================== +diff --git a/app/src/test/java/ru/svolf/convertx/data/entity/PaletteTest.kt b/app/src/test/java/ru/svolf/convertx/data/entity/PaletteTest.kt +new file mode 100644 +--- /dev/null (date 1789822410874) ++++ b/app/src/test/java/ru/svolf/convertx/data/entity/PaletteTest.kt (date 1789822410874) +@@ -0,0 +1,29 @@ ++package ru.svolf.convertx.data.entity ++ ++import kotlinx.serialization.json.Json ++import org.junit.jupiter.api.Assertions.assertEquals ++import org.junit.jupiter.api.Assertions.assertNotEquals ++import org.junit.jupiter.api.Test ++ ++class PaletteTest { ++ @Test ++ fun `palette json is decoded into colors`() { ++ val squash = Json.decodeFromString( ++ """{"palettes":[{"name":"Ocean","colors":[{"accent":"blue","hex":"#0000ff"}]}]}""" ++ ) ++ ++ assertEquals("Ocean", squash.palettes.single().name) ++ assertEquals(Color("blue", "#0000ff"), squash.palettes.single().colors.single()) ++ } ++ ++ @Test ++ fun `palette equality compares array contents`() { ++ val first = Palette("One", arrayOf(Color("a", "#111111"))) ++ val sameColors = Palette("Two", arrayOf(Color("a", "#111111"))) ++ val differentColors = Palette("One", arrayOf(Color("b", "#222222"))) ++ ++ assertEquals(first, sameColors) ++ assertNotEquals(first, differentColors) ++ assertEquals(first.hashCode(), sameColors.hashCode()) ++ } ++} +Index: app/src/test/java/ru/svolf/convertx/TestDoubles.kt +IDEA additional info: +Subsystem: com.intellij.openapi.diff.impl.patch.CharsetEP +<+>UTF-8 +=================================================================== +diff --git a/app/src/test/java/ru/svolf/convertx/TestDoubles.kt b/app/src/test/java/ru/svolf/convertx/TestDoubles.kt +new file mode 100644 +--- /dev/null (date 1789822460468) ++++ b/app/src/test/java/ru/svolf/convertx/TestDoubles.kt (date 1789822460468) +@@ -0,0 +1,66 @@ ++package ru.svolf.convertx ++ ++import androidx.datastore.core.DataStore ++import androidx.datastore.preferences.core.Preferences ++import androidx.datastore.preferences.core.emptyPreferences ++import kotlinx.coroutines.Dispatchers ++import kotlinx.coroutines.flow.Flow ++import kotlinx.coroutines.flow.MutableStateFlow ++import kotlinx.coroutines.test.StandardTestDispatcher ++import kotlinx.coroutines.test.TestScope ++import kotlinx.coroutines.test.advanceUntilIdle ++import kotlinx.coroutines.test.runTest ++import kotlinx.coroutines.test.resetMain ++import kotlinx.coroutines.test.setMain ++import ru.svolf.convertx.data.dao.HistoryDao ++import ru.svolf.convertx.data.entity.HistoryEntity ++ ++internal class InMemoryDataStore( ++ initial: Preferences = emptyPreferences() ++) : DataStore { ++ private val values = MutableStateFlow(initial) ++ ++ override val data: Flow = values ++ ++ override suspend fun updateData(transform: suspend (Preferences) -> Preferences): Preferences { ++ val updated = transform(values.value) ++ values.value = updated ++ return updated ++ } ++} ++ ++internal class InMemoryHistoryDao : HistoryDao { ++ private val rows = MutableStateFlow>(emptyList()) ++ ++ override fun observeAll(): Flow> = rows ++ ++ override suspend fun findById(id: Long): HistoryEntity? = rows.value.firstOrNull { it.id == id } ++ ++ override suspend fun upsert(entity: HistoryEntity) { ++ rows.value = (rows.value.filterNot { it.id == entity.id } + entity) ++ .sortedByDescending { it.id } ++ } ++ ++ override suspend fun deleteById(id: Long) { ++ rows.value = rows.value.filterNot { it.id == id } ++ } ++ ++ override suspend fun deleteAll() { ++ rows.value = emptyList() ++ } ++ ++ suspend fun seed(vararg entities: HistoryEntity) { ++ entities.forEach { upsert(it) } ++ } ++} ++ ++@OptIn(kotlinx.coroutines.ExperimentalCoroutinesApi::class) ++internal fun runViewModelTest(block: suspend TestScope.() -> Unit) = runTest { ++ Dispatchers.setMain(StandardTestDispatcher(testScheduler)) ++ try { ++ block() ++ advanceUntilIdle() ++ } finally { ++ Dispatchers.resetMain() ++ } ++} +Index: .idea/workspace.xml +IDEA additional info: +Subsystem: com.intellij.openapi.diff.impl.patch.BaseRevisionTextPatchEP +<+>\n\n \n \n \n android-25\n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n