dimanche 19 janvier 2020

Using room inMemoryDatabase with mockdata for testing android app happy path

I'm trying to populate a mock (inmemory) instance of a room database. I need this mock data to use in a recycler view so I can test if a filter works in my GUI. The problem is, although I think the inmemorydatabase is being created correctly, the populated items aren't showing in the GUI (android emulator) while the androidTest's are running. The app that is launching actually fetches the real data from the network and uses the data from the resulting cache in the room database as if I'm running the app in development..

I was thinking it might have to do with not using the right context when creating the database, so I've tried following things:

val context = activityRule.activity.baseContext

val context = activityRule.activity.applicationContext

val context = InstrumentationRegistry.getInstrumentation().targetContext

val context = activityRule.activity.applicationContext

Here is the complete test class (note that I'm not using any annotation above the class, I've left out the imports):

class MainActivityTest {

    private lateinit var db: QuotesDatabase
    private lateinit var quoteDao: QuoteDao
    private lateinit var authorDao: AuthorDao

    @Rule
    @JvmField
    var activityRule = ActivityTestRule<MainActivity>(
        MainActivity::class.java
    )

    @Test
    fun hostFragment_isDisplayedAtStart() {
        onView(withId(R.id.myNavHostFragment))
            .check(matches(isDisplayed()))
    }

    @Test
    fun readQuotesDisplaysList() {
        clickReadQuotesButton()
        onView(withId(R.id.quoteList))
            .check(matches(isDisplayed()))
    }

    @Test
    fun filterList() {
        createDatabase()
        clickReadQuotesButton()
        filterListOnLincoln()
        selectFirstItemQuoteList()
        onView(withId(R.id.author_name_textView)).check(matches(withText("Abraham Lincoln")))
    }

    @Test
    fun selectQuoteDisplayDetail() {
        clickReadQuotesButton()
        selectFirstItemQuoteList()
        onView(withId(R.id.quoteDetailFragment)).check(matches(isDisplayed()))
    }

    private fun clickReadQuotesButton() {
        onView(withId(R.id.read_quotes_button)).perform(click())
    }

    private fun selectFirstItemQuoteList() {
        onView(withId(R.id.quoteList)).perform(RecyclerViewActions.actionOnItemAtPosition<RecyclerView.ViewHolder>(0, click()))
    }

    private fun filterListOnLincoln() {
        onView(withId(R.id.action_search)).perform(click())
        Thread.sleep(1000)
        onView(withId(R.id.search_src_text)).perform(typeText("lincoln"))
        Thread.sleep(1000)
    }

    private fun createDatabase() {
        val context = InstrumentationRegistry.getInstrumentation().context
        db = Room.inMemoryDatabaseBuilder(context, QuotesDatabase::class.java).allowMainThreadQueries().build()
        quoteDao = db.quoteDao()
        authorDao = db.authorDao()

        val databaseAuthor1 = DatabaseAuthor("Thomas Edison", 1950, 1985, "Geen echte edison")
        val databaseQuote11 = DatabaseQuote("Dit is geen echte quote", "Thomas Edison", "Heb ik geschreven", true)
        val databaseQuote12 = DatabaseQuote("Dit ook niet", "Thomas Edison", "Heb ik geschreven", false)

        val databaseAuthor2 = DatabaseAuthor("Abraham Lincoln", 1950, 1985, "Geen echte lincoln")
        val databaseQuote21 = DatabaseQuote("Weer een valse", "Abraham Lincoln", "Heb ik geschreven", true)

        authorDao.insertAll(databaseAuthor1, databaseAuthor2)
        quoteDao.insertAll(databaseQuote11, databaseQuote12, databaseQuote21)
    }
}

While my code is running, I could see that real quotes were showing. I've thus emptied the cache and storage and turned of data connection so that my app would stop fetching the real data. In my fragment, the recyclerview is populated with room data, network data is cached in room, never used directly

Thank you

Aucun commentaire:

Enregistrer un commentaire