Espresso和postDelayed

时间:2015-08-21 14:43:24

标签: android android-espresso

我有一个使用postDelayed调用的活动:

public class SplashActivity extends Activity {
    private Handler handler = new Handler();

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(...);
        handler.postDelayed(new Runnable() { 
            public void run() { finish(); }
        }, 3000L);
    }
 }

这在app启动时运行,我需要导航它和我的登录屏幕。但是,UIController的loopMainThreadUntilIdle似乎并未将处理程序中的基础MessageQueue考虑在内。因此,当队列中仍有消息时,此操作立即结束。

onView(withId(R.id.splash_screen)).perform(new ViewAction() {
    @Override
    public Matcher<View> getConstraints() {
        return isAssignableFrom(View.class);
    }

    @Override
    public String getDescription() {
        return "";
    }

    @Override
    public void perform(final UiController uiController, final View view) {
        uiController.loopMainThreadUntilIdle();
    }
});

在队列耗尽之前,我一直无法弄清楚如何阻止。 Android本身阻止我做很多我想尝试的事情(比如扩展Handler并覆盖postDelayed方法等等)。

任何人对如何处理postDelayed都有任何建议?

我宁愿避免使用uiController.loopMainThreadForAtLeast,这看起来很hacky(就像Thread.sleep一样)

2 个答案:

答案 0 :(得分:10)

当Espresso等待时,它实际上会考虑到帐户MessageQueue,但与您的想法不同。要空闲,队列必须为空, 从现在起超过15毫秒才能运行任务

您可以自行检查代码,尤其是loopUntil()中的方法UiControllerImpl.java和文件QueueInterrogator.java。在后一个文件中,您还可以找到Espresso如何检查MessageQueue(方法determineQueueState())的逻辑。

现在,如何解决您的问题?有很多方法:

  1. 使用AsyncTask代替Handler,在后台线程上休眠并执行操作onPostExecute()。这样可以解决问题,因为Espresso将等待AsyncTask完成,但您可能不喜欢另一个线程的开销。

  2. 睡在你的测试代码中,但你不喜欢这种方法。

  3. 编写自定义IdlingResource:这是一种通用机制,让Espresso知道某些内容何时处于空闲状态,以便它可以运行操作和断言。对于这种方法,您可以:

    • 使用Espresso附带的课程CountingIdlingResource

    • 在逻辑运行后发布runnable并在runnable中发布increment()时调用decrement()

    • 在测试设置中注册IdlingResource并在拆卸中取消注册

  4. 另请参阅:docs and sampleanother sample

答案 1 :(得分:0)

据我所知,没有等待活动来完成浓缩咖啡的方法。你可以实现自己的waitForCondition版本,这是robotium所拥有的。这样,您只需等待所需的时间,就可以检测到活动未解决的问题。

你基本上每隔x ms轮询你的情况,比如。

while (!conditionIsMet() && currentTime < timeOut){
    sleep(100);
}

boolean conditionIsMet() {
    return "espresso check for if your splash view exists";
}