Issues with classloader when using Roboeletric Extension
See original GitHub issueI’m trying to migrate this class to kotest using the simplest available technic:
- Create new class
- extend it from
AnnotationSpec
- Add
RoboelectricExtension
to it - Add
Roboelectric
annotation to this class - Copy-paste code from source class with automatic conversion to kotlin
- Fixing some minor syntax issues
Result is as following:
package org.totschnig.myexpenses.util
import io.kotest.core.spec.style.AnnotationSpec
import io.kotest.experimental.robolectric.RobolectricExtension
import io.kotest.experimental.robolectric.RobolectricTest
import junit.framework.Assert
import org.mockito.ArgumentMatchers
import org.mockito.Mockito
import org.totschnig.myexpenses.model.Account
import org.totschnig.myexpenses.model.AccountType.BANK
import org.totschnig.myexpenses.model.AccountType.CASH
import org.totschnig.myexpenses.preference.PrefHandler
import org.totschnig.myexpenses.preference.PrefKey
import org.totschnig.myexpenses.preference.PrefKey.TRANSACTION_WITH_TIME
import org.totschnig.myexpenses.preference.PrefKey.TRANSACTION_WITH_VALUE_DATE
import org.totschnig.myexpenses.util.UiUtils.DateMode
@RobolectricTest
class UiUtilsDateModeKTest : AnnotationSpec() {
private lateinit var cashAccount: Account
private lateinit var bankAcount: Account
private lateinit var prefHandler: PrefHandler
init {
extensions(RobolectricExtension())
}
@Before
fun setup() {
cashAccount = Mockito.mock(Account::class.java)
bankAcount = Mockito.mock(Account::class.java)
Mockito.`when`(cashAccount.getType()).thenReturn(CASH)
Mockito.`when`(bankAcount.getType()).thenReturn(BANK)
prefHandler = Mockito.mock(PrefHandler::class.java)
}
private fun mockPref(prefKey: PrefKey, value: Boolean) {
Mockito.`when`(prefHandler!!.getBoolean(ArgumentMatchers.eq(prefKey), ArgumentMatchers.anyBoolean())).thenReturn(value)
}
@Test
fun withTimeAndWithValueDate() {
mockPref(TRANSACTION_WITH_TIME, true)
mockPref(TRANSACTION_WITH_VALUE_DATE, true)
Assert.assertEquals(DateMode.DATE_TIME, dateMode(cashAccount))
Assert.assertEquals(DateMode.BOOKING_VALUE, dateMode(bankAcount))
}
@Test
fun withTimeAndWithoutValueDate() {
mockPref(TRANSACTION_WITH_TIME, true)
mockPref(TRANSACTION_WITH_VALUE_DATE, false)
Assert.assertEquals(DateMode.DATE_TIME, dateMode(cashAccount))
Assert.assertEquals(DateMode.DATE_TIME, dateMode(bankAcount))
}
@Test
fun withoutTimeAndWithValueDate() {
mockPref(TRANSACTION_WITH_TIME, false)
mockPref(TRANSACTION_WITH_VALUE_DATE, true)
Assert.assertEquals(DateMode.DATE, dateMode(cashAccount))
Assert.assertEquals(DateMode.BOOKING_VALUE, dateMode(bankAcount))
}
@Test
fun withoutTimeAndWithoutValueDate() {
mockPref(TRANSACTION_WITH_TIME, false)
mockPref(TRANSACTION_WITH_VALUE_DATE, false)
Assert.assertEquals(DateMode.DATE, dateMode(cashAccount))
Assert.assertEquals(DateMode.DATE, dateMode(bankAcount))
}
private fun dateMode(account: Account?): DateMode? {
return UiUtils.getDateMode(account!!.type, prefHandler)
}
}
When I’m trying to run this test I’m getting very strange errors like
ClassCastException occurred while creating the mockito mock :
class to mock : 'org.totschnig.myexpenses.model.Account', loaded by classloader : 'sun.misc.Launcher$AppClassLoader@18b4aac2'
created class : 'org.totschnig.myexpenses.model.Account$MockitoMock$705451427', loaded by classloader : 'net.bytebuddy.dynamic.loading.MultipleParentClassLoader@762afe37'
proxy instance class : 'org.totschnig.myexpenses.model.Account$MockitoMock$705451427', loaded by classloader : 'net.bytebuddy.dynamic.loading.MultipleParentClassLoader@762afe37'
instance creation by : ObjenesisInstantiator
It looks like smth wrong happening in extension, but I don’t know what
Issue Analytics
- State:
- Created 3 years ago
- Comments:21 (21 by maintainers)
Top Results From Across the Web
robolectric test fails in cli with java.lang.RuntimeException
The key issue is here: Caused by: java.lang.ClassNotFoundException: couldn't load android.content.pm.PackageManager$NameNotFoundException.
Read more >Oh it seems like the Kotest robolectric extension doesn t in - Kotlinlang
Oh... it seems like the Kotest robolectric extension doesn't initialize the robolectric classloader and environment when the class is created, so all
Read more >Index - Robolectric
Creates a new builder using the specified ClassLoader for plugin loading. Builder(Config) - Constructor for class org.robolectric.annotation.
Read more >Help understanding class loading - Google Groups
Robolectric, and when it tries to load my class using that classloader ... fix is to extend RobolectricClassLoader so that tests can add...
Read more >Developing Android unit and instrumentation tests - Tutorial
Exercise: Write Android instrumentation test and use mocking ... public Application newApplication(ClassLoader cl, String className, Context context) throws ...
Read more >
Top Related Medium Post
No results found
Top Related StackOverflow Question
No results found
Troubleshoot Live Code
Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start Free
Top Related Reddit Thread
No results found
Top Related Hackernoon Post
No results found
Top Related Tweet
No results found
Top Related Dev.to Post
No results found
Top Related Hashnode Post
No results found
Oh, I know!
Code should be like following:
Oh, I see, thanks!