LINUX.ORG.RU

Как правильно тестировать Android приложение?

 , ,


0

1

Дано: модели, использующие внутри okhttp. Как это дело тестировать?

Как вообще правильно тестировать асинхронные приложения? Unit? Как-то еще? Поделитесь своим опытом, товарищи.



Последнее исправление: fman2 (всего исправлений: 1)

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

Deleted
()

Ну во первых, у тебя должно быть DI.
Во вторых, okhttp синхронный, емнип.
А так либо выноси okhttp в интерфейс и его мокай или mockWebserver + кастомные синхронные schedulers/thread pools которые используешь для тестов, что просто при наличии DI.

F457 ★★★★
()
Ответ на: комментарий от fman2

Футуры в дроид не завезли? Тогда создавай тред, делай в нем реалистично-рандомный слип, дергай коллбек.

Deleted
()
Ответ на: комментарий от fman2

Ну посетай ему синхронный диспатчер и будет синхронный https ://github.com/square/retrofit/issues/1259

Я чет думал оно ретрофитовские потоки использует а оказалось наоборот.

F457 ★★★★
()

Можно наверное через espresso, тестируй реальную работу, открыл активити, нажал кнопку, если надо, то ввел в поле данные (и т.д. и т.п.), и дождался результата асинхронного метода... Как то так... Я для этого отдельный эмулятор создал, на нем инструментальные тесты и гоняю

tiroman
()
Ответ на: комментарий от tiroman

Я так и тестирую сейчас. Использую для этих целей Genymotion. Но думал можно как-то это дело автоматизировать.

fman2
() автор топика
Ответ на: комментарий от fman2

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

Deleted
()
Ответ на: комментарий от tiroman

Как тестировать, без запуска эмулятора. У меня все разбито на модели. Ответ от сервера может придти за секунду, а может и за пять. Плюс нужно проверять формат данных, т.е. тут эмулятор не поможет, нужны именно assert, но беда в том, что код асинхронный.

fman2
() автор топика
Ответ на: комментарий от fman2

А чем эмулятор то мешает? Запустил пачку тестов на нем и жди результата, там тебе и ассерты и все что нужно, и асинхронного можно тестить, не понятно что не так... Без автоматизации тестирования юнит тесты тоже вручную запускать нужно

tiroman
()
Ответ на: комментарий от Deleted

Я пишу приложение к стороннему API (нет, это не вкклиент), API может поменяться в любой момент, данные могут быть другими. Хотелось бы просто запускать в AndroidStudio тест раз, скажем в два дня и смотреть, все ли методы получают от сервера то, что должны.

Если бы это можно было бы замокать, я бы замокал давным давно. А модельный код построен таким образом, что данные возвращаются грубо говоря в callback, а не синхронно, т.е. код построен на

client.newCall(request).enqueue(new Callback() {
   someInterface.onSuccess(...);
});

Да, можно было бы это все дело переписать и добавить новый слой в виде AsyncTask или чего-то подобного, тогда модели бы тестировались очень легко, но этого не хотелось бы.

А хотелось бы тестировать данные именно в этих Callback.

fman2
() автор топика
Ответ на: комментарий от tiroman

Можете ткнуть носом в статью, где рассказывается как автоматизировать тестирование приложения в эмуляторе?

fman2
() автор топика
Ответ на: комментарий от fman2

Так выдели все общение с чужим api в отдельный сервис, тудаже сунь маппинг в свои данные, получится независимая либа, вот ее публичный интерфейс и тестируй. Дроид совсем не нужен. Просто писать полноценные интеграционные тесты с automation это оверкилл для твоего сценария.

Deleted
()
Последнее исправление: Deleted (всего исправлений: 1)
Ответ на: комментарий от fman2

Так в AndroidTest все что лежит можно разом запускать из студии, так же как и юнит тесты ))) а чтобы колбэки нормально тестировать, можно же их в ту же rxjava завернуть и тестить... Делов на 5 минут

tiroman
()
Ответ на: комментарий от tiroman

Я к тому что твою асинхронного даже по нажатию какой то кнопки можно с помощью rxjava превратить в синхронизируется и в тестах ждать завершения методов

tiroman
()
Ответ на: комментарий от fman2

так в тестах его используй, в приложении можно код не модифицировать )) а espresso тут именно для того чтобы тестить в боевой обстановке на реальных данных

tiroman
()
Ответ на: комментарий от fman2

в тесте оберни

client.newCall(request).enqueue(new Callback() {
   someInterface.onSuccess(...);
});

в rxjava Single например и жди ответа, можно даже без всчких нажатий кнопок, тупо тест нужного метода

tiroman
()
Ответ на: комментарий от fman2

>тут эмулятор не поможет, нужны именно assert, но беда в том, что код асинхронный.

Посетай в OkHttp кастомный диспатчер в тесте. Я тебе даже ссылку привел откуда код скопипастить. Он тут же станет синхронным.

я бы замокал давным давно. А модельный код построен таким образом, что данные возвращаются грубо говоря в callback, а не синхронно, т.е. код построен на

client.newCall(request).enqueue(new Callback() {
   someInterface.onSuccess(...);
});



Ты програмист хоть?) После того, как мы сделали выполнение синхронным, как я описал вначале создаем тестовый колбек

TestCallback() {
   public Result result;
   public Throwable error;
 
   onSuccess {this.result = result}

   onError {this.error = error}

}


Сетаешь этот колбек в в свой запрос и следующей строкой проверяешь все что хочешь асертами используя поля, хочешь ошибки проверяй, хочешь результат запроса. У тебя синхронный код выполяемый в одном потоке.

Если ты хочешь функциональное тестирование с Espresso то есть okhttp-idle-resource от джека вартона. На гугл девелоперс читаешь что такое espresso idle resource, берешь либу и используешь для синхронизации с еспресо. И все опять работает синхронно.

F457 ★★★★
()
Ответ на: комментарий от tiroman

в rxjava Single например и жди ответа,

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

F457 ★★★★
()
Ответ на: комментарий от F457

например есть метод

public Single<Boolean> someMethod() {
...
}

в тесте пишем

TestObserver<Boolean> subscriber = new TestObserver<>();
someMethod().subscribe(subscriber);
boolean result = = subscriber.values().get(0);
subscriber.assertNoErrors();
subscriber.assertComplete();
assertEquals(result, true);//проверяем результат
tiroman
()
Ответ на: комментарий от tiroman

Упадет на subscriber.assertComplete();
если есть асинхронность. А она есть, ибо okhttp свои шедулеры использует и их надо переопределить для теста. Также надо менять в тестах и рх шедулеры. На trampoline или вроде test scheduled оно называлось, в котором время можно двигать, в зависимости от того, что тестируешь.

F457 ★★★★
()
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.