При тестировании пользовательского интерфейса Android, как правильно ждать готовности пользовательского интерфейса? - PullRequest
9 голосов
/ 22 февраля 2012

Тест выглядит так (это ActivityInstrumentationTestCase2):

public void testItShowsThreeRows() {
  activity = getActivity();

  activity.runOnUiThread(new Runnable() {
    public void run() {
      AccountsList accountsList = new AccountsList(activity, accounts);
      list.show();
    }
  });

  ListView listView = (ListView)activity.findViewById(R.id.list);
  assertEquals(3, listView.getChildCount());
}

Код, который я пытаюсь проверить, работает. Но тест не пройден, потому что activity.runOnUiThread возвращается немедленно. Я могу вставить Thread.sleep, и тест станет зеленым, но для меня это выглядит немного неуклюже. Нужно ли использовать какую-то синхронизацию потоков или может быть готов опросить некоторый элемент пользовательского интерфейса?

Я пытался аннотировать его @UiThreadTest, но это тоже не работает. Код в list.show() заполняет ListView через пользовательский адаптер, и getView вызывается в другом потоке (не тот, на котором выполняется тест - и я не имею к этому никакого отношения, у меня нет ни потоков, ни асинхронных задач, ни ничего) , Тест снова не пройден, поскольку он возвращается до того, как пользовательский интерфейс будет готов к проверке.

Ответы [ 3 ]

14 голосов
/ 27 апреля 2014

Вызов waitForIdleSync () лучше, чем спать в течение фиксированного времени.

3 голосов
/ 23 февраля 2012

Вы должны сделать Thread.sleep. Я не думаю, что есть способ обойти это. Я не понимаю, почему это "неуклюжий"; вы делаете тест, поэтому вам нужно подождать, пока система покажет элемент пользовательского интерфейса, который вы хотите протестировать.

Однако мне кажется, что вы действительно пытаетесь проверить AccountsList или список. Нет особых причин проверять ListView или findViewById, если вы не параноик.

Вы должны сосредоточиться на тестировании AccountsList и вашего пользовательского адаптера. Вам не нужно использовать пользовательский интерфейс для этого.

0 голосов
/ 31 августа 2018

Следуя документации, «Одна из ключевых частей Espresso - это его способность синхронизировать все тестовые действия. Espresso ждет, пока пользовательский интерфейс простаивает, прежде чем перейти к следующей операции. Аналогично, он ожидает завершения фоновых операций AsyncTask.В общем, это должно касаться большинства тестовых синхронизаций в вашем приложении. Если вы ранее писали тесты пользовательского интерфейса, вы оцените эту функцию - нет необходимости добавлять точки ожидания или точки синхронизации в ваше приложение!

Однако иногданевозможно полагаться на автоматическую синхронизацию, например, когда ваше приложение выполняет фоновые операции с использованием нестандартных средств (непосредственное управление потоками или использование пользовательских служб). Если вы столкнулись с ситуацией, когда вы не можете полагаться на Espresso для автоматической обработкиДля синхронизации вы можете использовать ресурсы холостого хода и по-прежнему полагаться на Espresso для синхронизации. "

Вы можете прочитать полный пример на тестовой кодовой метке , вы можететакже получите исходный код примера в github .

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...