From cdaae5279e3f53c146df2500a8d7a1d4eae2f674 Mon Sep 17 00:00:00 2001 From: Joffrey Bion Date: Thu, 6 Jul 2023 00:16:45 +0200 Subject: Convert sw-ui module to Kotlin Multiplatform gradle plugin --- .../ui/redux/sagas/SagasFrameworkTest.kt | 89 ++++++++++++++++++++++ .../sevenwonders/ui/utils/CoroutineUtilsTest.kt | 24 ++++++ 2 files changed, 113 insertions(+) create mode 100644 sw-ui/src/jsTest/kotlin/org/luxons/sevenwonders/ui/redux/sagas/SagasFrameworkTest.kt create mode 100644 sw-ui/src/jsTest/kotlin/org/luxons/sevenwonders/ui/utils/CoroutineUtilsTest.kt (limited to 'sw-ui/src/jsTest/kotlin/org/luxons/sevenwonders') diff --git a/sw-ui/src/jsTest/kotlin/org/luxons/sevenwonders/ui/redux/sagas/SagasFrameworkTest.kt b/sw-ui/src/jsTest/kotlin/org/luxons/sevenwonders/ui/redux/sagas/SagasFrameworkTest.kt new file mode 100644 index 00000000..f810c8b9 --- /dev/null +++ b/sw-ui/src/jsTest/kotlin/org/luxons/sevenwonders/ui/redux/sagas/SagasFrameworkTest.kt @@ -0,0 +1,89 @@ +package org.luxons.sevenwonders.ui.redux.sagas + +import kotlinx.coroutines.* +import kotlinx.coroutines.test.* +import redux.RAction +import redux.Store +import redux.WrapperAction +import redux.applyMiddleware +import redux.compose +import redux.createStore +import redux.rEnhancer +import kotlin.test.Test +import kotlin.test.assertEquals + +private data class State(val data: String) + +private data class UpdateData(val newData: String) : RAction +private class DuplicateData : RAction +private class SideEffectAction(val data: String) : RAction + +private fun reduce(state: State, action: RAction): State = when (action) { + is UpdateData -> State(action.newData) + is DuplicateData -> State(state.data + state.data) + else -> state +} + +private fun configureTestStore(initialState: State): TestRedux { + val sagaMiddlewareFactory = SagaManager() + val sagaMiddleware = sagaMiddlewareFactory.createMiddleware() + val enhancers = compose(applyMiddleware(sagaMiddleware), rEnhancer()) + val store = createStore(::reduce, initialState, enhancers) + return TestRedux(store, sagaMiddlewareFactory) +} + +private data class TestRedux( + val store: Store, + val sagas: SagaManager, +) + +@OptIn(ExperimentalCoroutinesApi::class) // for runTest +class SagaContextTest { + + @Test + fun dispatch_dispatchesToStore() = runTest { + val redux = configureTestStore(State("initial")) + + redux.sagas.runSaga { + dispatch(UpdateData("Bob")) + } + + assertEquals(State("Bob"), redux.store.getState(), "state is not as expected") + } + + @Test + fun next_waitsForNextAction() = runTest { + val redux = configureTestStore(State("initial")) + + val job = redux.sagas.launchSaga(this) { + val action = next() + dispatch(UpdateData("effect-${action.data}")) + } + advanceUntilIdle() // make sure the saga is launched + + assertEquals(State("initial"), redux.store.getState()) + + redux.store.dispatch(SideEffectAction("data")) + job.join() + assertEquals(State("effect-data"), redux.store.getState()) + } + + @Test + fun onEach() = runTest { + val redux = configureTestStore(State("initial")) + + val job = redux.sagas.launchSaga(this) { + onEach { + dispatch(UpdateData("effect-${it.data}")) + } + } + advanceUntilIdle() // make sure the saga is launched + + assertEquals(State("initial"), redux.store.getState()) + + redux.store.dispatch(SideEffectAction("data")) + yield() + assertEquals(State("effect-data"), redux.store.getState()) + job.cancel() + } +} diff --git a/sw-ui/src/jsTest/kotlin/org/luxons/sevenwonders/ui/utils/CoroutineUtilsTest.kt b/sw-ui/src/jsTest/kotlin/org/luxons/sevenwonders/ui/utils/CoroutineUtilsTest.kt new file mode 100644 index 00000000..ef8dfb62 --- /dev/null +++ b/sw-ui/src/jsTest/kotlin/org/luxons/sevenwonders/ui/utils/CoroutineUtilsTest.kt @@ -0,0 +1,24 @@ +package org.luxons.sevenwonders.ui.utils + +import kotlinx.coroutines.* +import kotlinx.coroutines.test.* +import kotlin.test.Test +import kotlin.test.assertEquals + +class CoroutineUtilsTest { + + @OptIn(ExperimentalCoroutinesApi::class) // for runTest + @Test + fun awaitFirstTest() = runTest { + val s = awaitFirst( + { delay(100); "1" }, + { delay(200); "2" }, + ) + assertEquals("1", s) + val s2 = awaitFirst( + { delay(150); "1" }, + { delay(50); "2" }, + ) + assertEquals("2", s2) + } +} -- cgit