2015-08-21 17 views
9

Mam aktywność, która jest przy użyciu postDelayed połączenia:espresso i 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); 
    } 
} 

To działa na starcie aplikacji, i muszę go i mój ekran logowania nawigacji. Jednak pętla UMontrolThightThntilIdle UIController prawdopodobnie nie uwzględnia bazowego MessageQueue w programie obsługi. W związku z tym ta czynność kończy się natychmiast, gdy w kolejce nadal znajdują się komunikaty.

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(); 
    } 
}); 

Nie potrafiłem ustalić, jak zablokować, dopóki kolejka nie zostanie wyczerpana. Sam system Android uniemożliwia mi robienie wielu rzeczy, których bym próbował (np. Rozszerzenie programu Handler i nadpisanie metody postDelayed, itp.).

Ktoś ma jakieś sugestie dotyczące obsługi postDelayed?

wolałbym uniknąć uiController.loopMainThreadForAtLeast, co wydaje się hacky (jak Thread.Sleep będzie)

Odpowiedz

8

Kiedy espresso czeka, to faktycznie nie uwzględniające MessageQueue, ale w inny sposób niż to, co myślisz. Aby być idle, kolejka musi być pusta, lubmieć zadania, które będą uruchamiane w więcej niż 15 milisekund od teraz.

Możesz sam sprawdzić kod, szczególnie metodę loopUntil() w UiControllerImpl.java i plik QueueInterrogator.java. W tym drugim pliku znajdziesz również sposób, w jaki Espresso sprawdza MessageQueue (metoda determineQueueState()).

Teraz, jak rozwiązać swój problem? Istnieje wiele sposobów:

  1. Zastosowanie AsyncTask zamiast Handler, spanie na wątek tła i wykonywanie czynności onPostExecute(). To działa, ponieważ Espresso będzie czekał na zakończenie operacji AsyncTask, ale możesz nie lubić dodatkowego wątku.

  2. Spij w swoim teście, ale już nie lubisz tego podejścia.

  3. Napisz swój własny IdlingResource: jest to ogólny mechanizm, który informuje Espresso, gdy coś jest bezczynne, aby mógł wykonywać akcje i zapewnienia.W tym podejściu możesz:

    • Użyj klasę CountingIdlingResource że pochodzi z espresso

    • Wezwania increment() kiedy piszesz Twój runnable i decrement() wewnątrz runnable po logika prowadzi

    • Zarejestruj swoje IdlingResource w konfiguracji testowej i wyrejestruj ją podczas odrywania

Zobacz także: docs and sample, another sample

+1

Zastanawiam się, czy mogę po prostu zanalizować wysyłanie wiadomości do kolejki i wstrzyknąć inną implementację, która działa jak IdlingResource. Będę miał domyślną implementację w moim kodzie, która odsyła do programu obsługi, a w kodzie testowym: IdlingResource i icnrements/decrements – Matt

0

O ile wiem, nie ma czekać na działalność do końca sposobu w espresso. Możesz zaimplementować własną wersję waitForCondition, coś, co ma robotium. W ten sposób będziesz tylko czekać tak długo, jak jest to potrzebne, i możesz wykryć problemy z aktywnością nie kończącą się.

Zasadniczo sondujesz swój stan co x ms, coś w stylu.

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

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

Problemem jest to, że Android zapewnia nie sposób naprawdę zajrzeć do kolejki komunikatów, aby sprawdzić, czy wszystko jest w kolejce. Musiałoby to być coś, co zostało przechwycone i zastąpione podczas uruchamiania (co uważam za robota). – Matt

+0

Klasa waitForCondition odpytuje jako warunek, który sam napiszesz. Jeśli chodzi o robotium sprawdzające kolejkę, to nie wydaje mi się, że widziałem takie problemy jak robota. – JohanShogun

+0

W tym przypadku powinieneś być w stanie poczekać na działanie, zamiast patrzeć na kolejkę komunikatów (co jest naprawdę ciekawsze z punktu testowego). – JohanShogun