Last active
March 17, 2022 02:29
-
-
Save gildor/d371f8dcd17b0d398d698d28ab9fd3f3 to your computer and use it in GitHub Desktop.
Simple implementation of Android Espresso onView with timeout
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import android.view.View | |
import androidx.test.espresso.Espresso | |
import androidx.test.espresso.NoMatchingViewException | |
import androidx.test.espresso.ViewAssertion | |
import androidx.test.espresso.ViewInteraction | |
import androidx.test.espresso.assertion.ViewAssertions.matches | |
import androidx.test.espresso.matcher.ViewMatchers.Visibility | |
import androidx.test.espresso.matcher.ViewMatchers.withEffectiveVisibility | |
import org.hamcrest.Matcher | |
/** | |
* onView with retry logic, it will try to find view using [matcher] | |
* until it passes [retryAssertion] check, if it passed, [ViewInteraction] for | |
* this view will be returned | |
* | |
* Default [retryAssertion] checks that view is at least visible, if it hidden, we will retry attempt | |
* it doesn't check for isDisplayed() because it not related to this check | |
* (that view is displayed to user), the fact that view isDisplayed must be ensured | |
* by test itself, this matcher only retries until view becomes visible. | |
* But this behaviour can be changed if you pass custom [retryAssertion] | |
* | |
* This method should be used only for views which showed asynchronously | |
* and do not have any loading indicator for this asynchronous operation | |
* | |
* So it's better than simple Thread.sleep(SomeRandomDelay), but worse than relying on UI loader | |
*/ | |
fun onViewWithTimeout( | |
retries: Int = 10, | |
retryDelayMs: Long = 500, | |
retryAssertion: ViewAssertion = matches(withEffectiveVisibility(Visibility.VISIBLE)), | |
matcher: Matcher<View> | |
): ViewInteraction { | |
repeat(retries) { i -> | |
try { | |
val viewInteraction = Espresso.onView(matcher) | |
viewInteraction.check(retryAssertion) | |
return viewInteraction | |
} catch (e: NoMatchingViewException) { | |
if (i >= retries) { | |
throw e | |
} else { | |
Thread.sleep(retryDelayMs) | |
} | |
} | |
} | |
throw AssertionError("View matcher is broken for $matcher") | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment