Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Screen Model test Exception #45

Closed
ynsok opened this issue Feb 9, 2022 · 4 comments
Closed

Screen Model test Exception #45

ynsok opened this issue Feb 9, 2022 · 4 comments

Comments

@ynsok
Copy link

ynsok commented Feb 9, 2022


    fun login(email: String, password: String) = coroutineScope.launch {
        val userCredentials = UserCredentials(email, password)
        logInUseCase.invoke(userCredentials)
    }
    @Test
    fun `on login success state is SignIn`() = runTest {
        loginModel.login("email", "password")
        loginModel.state
            .take(1)
            .onEach { assertEquals(it::class.simpleName, AuthState.SignedIn::class.simpleName) }
            .collect()
    }
java.lang.IllegalStateException: ScreenModel not found: ui.login.LoginModel
	at cafe.adriel.voyager.core.model.ScreenModelStore.getDependencyKey(ScreenModelStore.kt:39)
	at com.netguru.common.ScreenExtensionsKt.getModelScope(ScreenExtensions.kt:29)
	at ui.login.LoginModel.login(LoginModel.kt:19)
	at ui.LoginModelTest$on login success state is SignIn$1.invokeSuspend(LoginModelTest.kt:40)
	at ui.LoginModelTest$on login success state is SignIn$1.invoke(LoginModelTest.kt)
	at ui.LoginModelTest$on login success state is SignIn$1.invoke(LoginModelTest.kt)
	at kotlinx.coroutines.test.TestBuildersKt__TestBuildersKt$runTestCoroutine$2.invokeSuspend(TestBuilders.kt:208)
	at kotlinx.coroutines.test.TestBuildersKt__TestBuildersKt$runTestCoroutine$2.invoke(TestBuilders.kt)
	at kotlinx.coroutines.test.TestBuildersKt__TestBuildersKt$runTestCoroutine$2.invoke(TestBuilders.kt)
	at kotlinx.coroutines.intrinsics.UndispatchedKt.startCoroutineUndispatched(Undispatched.kt:55)
	at kotlinx.coroutines.CoroutineStart.invoke(CoroutineStart.kt:112)
	at kotlinx.coroutines.AbstractCoroutine.start(AbstractCoroutine.kt:126)
	at kotlinx.coroutines.test.TestBuildersKt__TestBuildersKt.runTestCoroutine(TestBuilders.kt:207)
	at kotlinx.coroutines.test.TestBuildersKt.runTestCoroutine(Unknown Source)
	at kotlinx.coroutines.test.TestBuildersKt__TestBuildersKt$runTest$1$1.invokeSuspend(TestBuilders.kt:167)
	at kotlinx.coroutines.test.TestBuildersKt__TestBuildersKt$runTest$1$1.invoke(TestBuilders.kt)
	at kotlinx.coroutines.test.TestBuildersKt__TestBuildersKt$runTest$1$1.invoke(TestBuilders.kt)
	at kotlinx.coroutines.test.TestBuildersJvmKt$createTestResult$1.invokeSuspend(TestBuildersJvm.kt:13)
	at kotlin.coroutines.jvm.internal.BaseContinuationImpl.resumeWith(ContinuationImpl.kt:33)
	at kotlinx.coroutines.DispatchedTask.run(DispatchedTask.kt:106)
	at kotlinx.coroutines.EventLoopImplBase.processNextEvent(EventLoop.common.kt:279)
	at kotlinx.coroutines.BlockingCoroutine.joinBlocking(Builders.kt:85)
	at kotlinx.coroutines.BuildersKt__BuildersKt.runBlocking(Builders.kt:59)
	at kotlinx.coroutines.BuildersKt.runBlocking(Unknown Source)
	at kotlinx.coroutines.BuildersKt__BuildersKt.runBlocking$default(Builders.kt:38)
	at kotlinx.coroutines.BuildersKt.runBlocking$default(Unknown Source)
	at kotlinx.coroutines.test.TestBuildersJvmKt.createTestResult(TestBuildersJvm.kt:12)
	at kotlinx.coroutines.test.TestBuildersKt__TestBuildersKt.runTest(TestBuilders.kt:166)
	at kotlinx.coroutines.test.TestBuildersKt.runTest(Unknown Source)
	at kotlinx.coroutines.test.TestBuildersKt__TestBuildersKt.runTest(TestBuilders.kt:154)
	at kotlinx.coroutines.test.TestBuildersKt.runTest(Unknown Source)
	at kotlinx.coroutines.test.TestBuildersKt__TestBuildersKt.runTest$default(TestBuilders.kt:147)
	at kotlinx.coroutines.test.TestBuildersKt.runTest$default(Unknown Source)
	at ui.LoginModelTest.on login success state is SignIn(LoginModelTest.kt:39)
	at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
	at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
	at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
	at java.base/java.lang.reflect.Method.invoke(Method.java:566)
	at org.junit.runners.model.FrameworkMethod$1.runReflectiveCall(FrameworkMethod.java:50)
	at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:12)
	at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:47)
	at org.junit.internal.runners.statements.InvokeMethod.evaluate(InvokeMethod.java:17)
	at org.junit.runners.ParentRunner.runLeaf(ParentRunner.java:325)
	at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:78)
	at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:57)
	at org.junit.runners.ParentRunner$3.run(ParentRunner.java:290)
	at org.junit.runners.ParentRunner$1.schedule(ParentRunner.java:71)
	at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:288)
	at org.junit.runners.ParentRunner.access$000(ParentRunner.java:58)
	at org.junit.runners.ParentRunner$2.evaluate(ParentRunner.java:268)
	at org.junit.runners.ParentRunner.run(ParentRunner.java:363)
	at org.gradle.api.internal.tasks.testing.junit.JUnitTestClassExecutor.runTestClass(JUnitTestClassExecutor.java:110)
	at org.gradle.api.internal.tasks.testing.junit.JUnitTestClassExecutor.execute(JUnitTestClassExecutor.java:58)
	at org.gradle.api.internal.tasks.testing.junit.JUnitTestClassExecutor.execute(JUnitTestClassExecutor.java:38)
	at org.gradle.api.internal.tasks.testing.junit.AbstractJUnitTestClassProcessor.processTestClass(AbstractJUnitTestClassProcessor.java:62)
	at org.gradle.api.internal.tasks.testing.SuiteTestClassProcessor.processTestClass(SuiteTestClassProcessor.java:51)
	at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
	at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
	at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
	at java.base/java.lang.reflect.Method.invoke(Method.java:566)
	at org.gradle.internal.dispatch.ReflectionDispatch.dispatch(ReflectionDispatch.java:36)
	at org.gradle.internal.dispatch.ReflectionDispatch.dispatch(ReflectionDispatch.java:24)
	at org.gradle.internal.dispatch.ContextClassLoaderDispatch.dispatch(ContextClassLoaderDispatch.java:33)
	at org.gradle.internal.dispatch.ProxyDispatchAdapter$DispatchingInvocationHandler.invoke(ProxyDispatchAdapter.java:94)
	at com.sun.proxy.$Proxy2.processTestClass(Unknown Source)
	at org.gradle.api.internal.tasks.testing.worker.TestWorker$2.run(TestWorker.java:176)
	at org.gradle.api.internal.tasks.testing.worker.TestWorker.executeAndMaintainThreadName(TestWorker.java:129)
	at org.gradle.api.internal.tasks.testing.worker.TestWorker.execute(TestWorker.java:100)
	at org.gradle.api.internal.tasks.testing.worker.TestWorker.execute(TestWorker.java:60)
	at org.gradle.process.internal.worker.child.ActionExecutionWorker.execute(ActionExecutionWorker.java:56)
	at org.gradle.process.internal.worker.child.SystemApplicationClassLoaderWorker.call(SystemApplicationClassLoaderWorker.java:133)
	at org.gradle.process.internal.worker.child.SystemApplicationClassLoaderWorker.call(SystemApplicationClassLoaderWorker.java:71)
	at worker.org.gradle.process.internal.worker.GradleWorkerMain.run(GradleWorkerMain.java:69)
	at worker.org.gradle.process.internal.worker.GradleWorkerMain.main(GradleWorkerMain.java:74)

I can't use rememberScreenModel or ScreenModelStore.getOrPut in the test so that's why the error is thrown. Any idea how to work around this? @adrielcafe @terrakok @programadorthi @DevSrSouza

@DevSrSouza
Copy link
Collaborator

Hey @ynsok, how is the implementation that provides the loginModel for your test?

@ynsok
Copy link
Author

ynsok commented Feb 12, 2022

 class LoginViewModel {
     private val authRepository: AuthRepository = AuthRepositoryImpl(AuthServiceMockImpl())
     private val logInUseCase: LogInUseCase = LogInUseCase(authRepository)
     private val observeUserSessionUseCase: ObserveAuthStatusUseCase = ObserveAuthStatusUseCase(authRepository)
     private val loginModel = LoginModel(observeUserSessionUseCase, logInUseCase)
 
     @Test
     fun `on login success state is SignIn`() = runTest {
         loginModel.login("email", "password")
         loginModel.state
             .take(1)
             .onEach { assertEquals(it::class.simpleName, AuthState.SignedIn::class.simpleName) }
             .collect()
     }
 }

@DevSrSouza
Copy link
Collaborator

Okay, the issue here is that coroutineScope extension from ScreenModel. I will try to find a better workaround, but a faster workaround would be creating your own CoroutineScope, and using the onDispose() method from ScreenModel to stop all Jobs running on it.

class LoginModel : ScreenModel {
    val coroutineScope: CoroutineScope = CoroutineScope()
    override fun dispose() {
        coroutineScope.cancel()
    }
}

@adrielcafe
Copy link
Owner

Should be fixed in 1.0.0-beta16, feel free to reopen if the issue persists.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants