Тестирование — одна из самых важных этапов при разработке приложения. И приложения на Android не есть исключением. При написании кода обычно нужно его просматривать и задуматься над тем, как же его протестировать потом. Представим ситуацию, когда вам нужно покрыть тестами ваш проект, который полностью написан. Чаще всего, это не так-то просто. Скорее всего, ваш код просто-напросто не был реализован так, чтобы его было легко тестировать. Это означает, что вам придётся делать изменения в нём, чтобы сделать его поддающимся тестированию… не разрушив никакой функциональности (собственно это в наше время и называется рефакторингом (refactoring)). Но, выполняя такие изменения, можно ли быстро и уверенно сказать, что вы ничего не сломали в работающем коде, если в нём не было всесторонних тестов? Вряд ли. Я считаю, что тесты, а именно UNIT-тесты, должны быть написаны самим разработчиком, так как он и только он знает все о том как и что он пишет.
Что касается Android, как и все прочие, компания Google предоставила не плохие инструменты для тестирования, но с их помощью можно сделать далеко не всё. Для тестирования используеться jUnit-фреймворк, который имеет свои плюсы и минусы конечно-же.
jUnit — применяется для модульного тестирования, которое позволяет проверять на правильность отдельные модули исходного кода программы. Преимущество данного подхода заключается в изолировании отдельно взятого модуля от других. При этом, цель такого метода позволяет программисту удостовериться, что модуль, сам по себе, способен работать корректно. jUnit представляет из себя библиотеку классов. Но тот, кто писал тесты с помощью этого фреймворка наверное убедились, что он вовсе неудобен при тестировании GUI. Признаком хорошего тона является код, покрытый тестами и отчётом, который показывает процент покрытия кода тестами. В последнее время, в проектах мне приходиться писать кроме всего прочего и тесты от нагрузочных до GUI и я хотел-бы рассказать об особенностях, которые встречаю я и том, как создать эти отчёты. Но сначала об основных фреймворках:
Примерная картина использования основных фреймворков. По сути, каждый выбор для себя делает сам. Кто-то выбирает Robotium из-за неохоты лезть в исходный код, кто-то Espresso, из-за его интуитивно понятного интерфейса.
Spoon
Spoon – фреймворк, который умеет делать скриншоты с экрана устройства или эмулятора во время выполнения тестов и в результате создаёт из них отчёт. Кроме скриншотов, к отчёту он прикрепляет логирование тест-ранера, и в случае если тест не проходит он выводит полный стек-трейс, что очень удобно. Что-бы получить отчёт, делаем следующее:
- качаем Spoon-client и Spoon-runner;
- копируем Spoon-client впапку libs проекта с тестами;
- в этом же проекте создаем папку (например, spoon);
- копируем Spoon-runner в созданную папку;
- создаем bat-файл с таким скриптом:
call java -jar spoon-runner-1.1.1-jar-with-dependencies.jar
-- apk Pathtoyourproject binproject.apk
-- test-apk Pathtoyourtest-project bintests.apk
В субпараметрах можно указать фильтр для для тестов, например запустить только тесты с аннотацией «Medium» можно добавив к скрипту — size medium.
Теперь скрипт будет выглядеть так:
call java -jar spoon-runner-1.1.1-jar-with-dependencies.jar
-- apk Pathtoyourproject binproject.apk
-- test-apk Pathtoyourtest-project bintests.apk
-- size medium
Полный список субпараметров можно посмотреть на официальной его странице на Github. Всё, теперь при написании тестов просто где нужно вставляете:
Spoon.screenshot(activity, "state_changed"),
где второй аргумент та строка, что будет подсвечиваться над скриншотом. Да, ещё одна особенность — внутри себя он использует regex-ы, и при использовании пробелов в подписях выбрасывает исключение. Запускаем эмулятор или подключаем телефон, открываем наш батник и если всё сделано правильно, в той же папке увидите отчёт:
Официальный пример отчёта от разработчика здесь.
Отчёт из моего проекта можно посмотреть здесь.
Не плохо, не правда-ли? Ещё одним преимуществом «ложки» в том, что он запускает тесты одновременно на всех подключенных девайсах, тоесть соберёт в один отчет результати со всех девайсов. Единственным и наверное существенным минусом есть то, что он не делает скриншотов диалогов и увидеть что было на нем во время теста не есть возможным. Да и отчета о покрытии кода тестами он по прежнему не создаст! Что-же давайте исправим это.
Emma
Согласитесь, отчет выглядит как минимум достойно
Пример покрытого тестами кода:
и соответсвенно частично покрытого:
Полный отчёт во всех форматах.
EMMA — инструментарий с открытым исходным кодом для измерения и отчетности покрытия кода тестами в Java. Этот инструмент встроен в Android SDK и разработчики предоставляют возможность генерации отчёта «с коробки». Основные возможности:
- поддержка инспектирования классов в автономном режиме(перед загрузкой) так и «на лету»;
- поддерживаемые типы покрытия: пакет, класс, метод, линия и основной блок. Также есть возможность обнаружить, когда одна строка исходного кода покрыта лишь частично;
- типы выходных отчетов: текст, HTML, XML;
Сборка проекта с помощью Ant
Apache Ant — инструмент для преобразования структур разработки в конструкцию развертывания приложений. Он является декларативным и все инструкции командной строки, используемые для развертывания приложения, представляются простыми XML-элементами. Более детально можно почитать здесь.
Для описания процедуры сборки проекта нужно: рабочий проект — MyProject и проект с тестами для него — MyProjectTests. О правилах, которых должны придерживаться при создании тестов можно прочитать здесь.
В первую очередь, при сборке проекта с помощью Ant, нужно собрать проекты, которые используются в приложении как библиотеки. Если таковых нет, то этот шаг можно пропустить. Например, проект использует такие библиотеки, как «google_play_service_lib» нужно выполнить следующее:
— в командной строке нужно перейти в папку установленной sdktools(к примеру, D:androidadt-bundlesdktools) и выполнить:
android update lib-project -p MyLibProject
, гдеMyLibProject — путь к библиотеке, используемом в проекте. В результате в корне проекта должен появиться build.xml и в консоли выпадет сообщение:
Updated local.properties
Updated file D:WorkspaceMyProjectbuild.xml
Updated file D:WorkspaceMyProjectTestsproguard-project.txt
После сборки всех библиотек нужно собрать сам рабочий проект. Для этого в той же папке нужно выполнить:
android update project -p MyProject
, где MyProject — путь к рабочей ветке проекта. Естественно, в этой папке должен находиться AndroidManifest.xml. Скрипт снова сгенерирует build.xml и соберёт рабочий проект. Можно ввести имя проекта через субпараметры, чтобы в дальнейшем его удобно использовать:
android update project -p MyProject -n NameForProject
Как же происходит сборка проекта с тестами? Всё аналогично и удобно. Скрипт для сборки проекта с тестами:
android update test-project -m ..MyProject -p MyProjectTests
, где MyProject — путь к рабочему проекту, а MyProjectTests — путь к проекту с тестами.
Всё готово! Кстати, на этом шаге у разработчиков могут возникнуть проблемы из-за использования библиотек! Например, в проекте разные jar-библиотеки могут быть собраны на основе библиотек, которые используются в других ваших библиотеках. Ant не понимает что с ними делать и в итоге возникает ошибка при сборке. То есть, если в проекте внутри себя юзают одну и туже либу, то это уже может привести к ошибке.
Для запуска подсчёта количества покрытия кода тестами в скрипте в субпараметрах нужно прописать emma. Перед запуском нужно запустить эмулятор или подключить девайс. В командной строке на топ-ветке проекта с тестами выполняется скрипт:
ant clean emma debug install test
В ходе выполнения тестов, Emma генерирует файл coverage.em в bin-папке главного проекта(метаданные), после прохождения всех тестов выставляет необходимые пермишины, создает файл coverage.ec в папке установленного проекта, копирует два этих файла в bin-папку тестового проекта и на основе их генерирует отчёт в этой же папке.
Исходники моего проекта с примерами отчётов можно посмотреть на Github.
Подитожим
Посмотрим на тесты, даже если они написаны очень хорошо. Вы можете смотря на них ответить, на сколько они покрывают ваш код? Достаточно-ли вам зелёной полоски, которая показывает результат ваших тестов, как визуального отчета в целом? Думаю, что нет. Использование отчётности, как результата выполнения работы показывает уровень компетентности специалиста, а когда речь идет об автоматизации тестирования, то и подавно. Написание скриптов может конечно отнять у вас некоторое время, но поверьте оно этого стоит!
Автор: oleksiikhorunzhyi