gpt4 book ai didi

android - 如何在没有 IdlingResource 的情况下在 Espresso 中等待异步任务

转载 作者:行者123 更新时间:2023-12-05 00:20:23 28 4
gpt4 key购买 nike

我有以下 Espresso 代码:

@Test
fun backgroundWorkDisplaysTextAfterLoading() {
onView(withId(R.id.btn_next_fragment)).perform(click())
onView(withId(R.id.btn_background_work)).perform(click())

onView(withId(R.id.hiddenTextView)).check(matches(isDisplayed()))
}

单击 btn_background_work 时,有一个服务调用会在 2 秒内返回响应,然后 hiddenTextview 将变得可见。

如何让 Espresso 等待执行 ViewAssertion ( check(matches(isDisplayed)) ),直到该服务调用返回一个值?服务调用通过 Retrofit 完成,服务调用在 Schedulers.io() 线程上完成。

我无法触及生产代码,因此在生产代码中实现 IdlingResources 是不可能的。

任何帮助表示赞赏!

最佳答案

您仍然可以实现 IdlingResource无需接触生产代码。您只需要创建一个IdlingResource监听 ViewTreeObserver.OnDrawListener 的回调:

private class ViewPropertyChangeCallback(private val matcher: Matcher<View>, private val view: View) : IdlingResource, ViewTreeObserver.OnDrawListener {

private lateinit var callback: IdlingResource.ResourceCallback
private var matched = false

override fun getName() = "View property change callback"

override fun isIdleNow() = matched

override fun registerIdleTransitionCallback(callback: IdlingResource.ResourceCallback) {
this.callback = callback
}

override fun onDraw() {
matched = matcher.matches(view)
callback.onTransitionToIdle()
}
}

然后创建自定义 ViewAction等待比赛:
fun waitUntil(matcher: Matcher<View>): ViewAction = object : ViewAction {

override fun getConstraints(): Matcher<View> {
return any(View::class.java)
}

override fun getDescription(): String {
return StringDescription().let {
matcher.describeTo(it)
"wait until: $it"
}
}

override fun perform(uiController: UiController, view: View) {
if (!matcher.matches(view)) {
ViewPropertyChangeCallback(matcher, view).run {
try {
IdlingRegistry.getInstance().register(this)
view.viewTreeObserver.addOnDrawListener(this)
uiController.loopMainThreadUntilIdle()
} finally {
view.viewTreeObserver.removeOnDrawListener(this)
IdlingRegistry.getInstance().unregister(this)
}
}
}
}
}

并更新您的测试以使用该操作:
onView(withId(R.id.hiddenTextView)).perform(waitUntil(isDisplayed()))
// or
onView(withId(R.id.hiddenTextView)).perform(waitUntil(withEffectiveVisibility(VISIBLE)))
.check(matches(isDisplayed()))

没有 IdlingResource , Thread.sleep(...)可能是您的下一个选择,但它会不稳定或效率低下。

关于android - 如何在没有 IdlingResource 的情况下在 Espresso 中等待异步任务,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/59689109/

28 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com