2012-04-24 2 views
15

Я пытаюсь написать тест инструментария для Android, который останавливается (onPause(), затем onStop()) и перезапускает текущую активность. Я пробовалКак остановить и перезапустить активность в тесте на андроид?

activity.finish(); 
activity = getActivity(); 

... но это не работает должным образом.

Целью теста является утверждение, что данные формы хранятся во время метода onPause() и перечитываются во время метода onStart(). Он работает при выполнении этого вручную, но тест терпит неудачу, из чего я делаю вывод, что activity.finish() представляется неправильным способом остановки и перезапуска активности.


Edit: Моя главная проблема, кажется, была проблема синхронизации. После перезапуска действия тестовый бегун не дождался завершения всех обработчиков событий. Следующая строка останавливает выполнение теста, пока деятельность не находится в режиме ожидания:

getInstrumentation().waitForIdleSync() 

Кроме того, обратите внимание на принятый ответ на более ценную информацию о жизненном цикле.

+0

Что именно не работает должным образом? – yorkw

+0

@yorkw Я обновил вопрос, спасибо за комментарий. –

+0

Что вы имеете в виду, когда говорите «делать это вручную?». –

ответ

13

Позвонив (или вызвать изменение ориентации экрана):

activity.finish(); // old activity instance is destroyed and shut down. 
activity = getActivity(); // new activity instance is launched and created. 

Причинение деятельность пройти полный отдых жизненного цикла:

onPause() -> onStop() -> onDestroy() -> onCreate() 

Что вам нужно:

onPause() -> onStop() -> onRestart() 

Недавно я выставил Instrumentation API и нашел много интересного цикла активности жизни Метод электронного триггера callActivityOnXXX(), следующая строка кода должна сделать сложнее:

MyActivity myActivity = getActivity(); 
// make activity falling into restart phase: 
getInstrumentation().callActivityOnRestart(myActivity); 

Диаграмма деятельности жизненного цикла цитаты из официального руководства Dev: enter image description here

+1

На самом деле, я уже дал первое решение попробовать, и он не работал, как вы можете видеть в моем вопросе. Но, возможно, вы правы, и проблема не связана ... Повторите свое второе предложение, я попробую это позже ... –

+0

@ DaniloBargen, проверьте мое обновление. – yorkw

+0

что на самом деле это сделал, спасибо очень! :) Не могли бы вы отложить это в верхней части вашего ответа, чтобы другие могли найти более легко? –

0

Может быть, у может попытаться сохранить название вашей деятельности, закончить его ... и использовать отражение, чтобы получить новый экземпляр .class для нового намерения создать ...

2

Хороший способ для тестирования событий жизненного цикла происходит изменение ориентации экрана. По моему опыту, это удобный способ бомбардировки шаблона onPause/onStart.

+0

Интересная идея. Проблема заключается в том, что Android сохраняет данные формы по умолчанию при изменении ориентации экрана, поэтому на самом деле не покрывает этот тестовый случай ... –

+0

Изменение ориентации экрана, итоговое завершение Жизненный цикл операции: ... -> onPause () -> onStop() -> onDestroy() -> onCreate() -> onStart() -> ..., который имеет такое же поведение вызова activity.finish(); activity = getActivity(); – yorkw

+0

@ DaniloBargen Я не считаю, что данные формы сохраняются по умолчанию, когда действие уничтожается. –

10

Я пытался дозвониться .finish(), setActivity (нуль), getActivity() и он перезапускает активность, но для меня это не восстанавливает состояние. Я опробовал все остальные ответы на SO, и каждый другой способ сделать это я мог найти в Интернете, и никто из них не работал для меня.После долгих экспериментов я нашел следующие работы (Примечание: требуется уровень API 11+):

getInstrumentation().runOnMainSync(new Runnable() { 
     @Override 
     public void run() { 
      activity.recreate(); 
     } 
    }); 
    setActivity(null); 
    activity = getActivity(); 

Когда я делаю это новый экземпляр деятельности создается, и создается новый экземпляр фрагмента я прикрепил к деятельности ранее в тесте также создается, и как активность, так и фрагмент восстанавливают свое состояние ожидаемым образом.

Я не знаю, как это работает или почему это работает, я достиг этого решения с помощью проб и ошибок, и я только протестировал его на Nexus 4, работающем с KitKat. Я не могу гарантировать, что он правильно имитирует активный отдых, но он работал для моих целей.

Редактировать: Позднее я выяснил, как это работает. getActivity() работает через регистрацию перехватчиков, которые получают новые Создаваемые действия, которые захватывают новую активность, созданную activity.recreate(). setActivity(null) должен был очистить внутреннюю поддержку кеша getActivity, иначе он вернет старый и не будет искать новый.

Вы можете видеть, как это работает при изучении исходного кода для различных классов тестовых примеров, из которых один распространяется.

Смежные вопросы