#android #gradle #android-studio #android-testing
#Android #gradle #android-studio #android-тестирование
Вопрос:
У меня есть пара AndroidTestCase
подклассов в отдельных пакетах моего проекта:
Однако всякий раз, когда я запускаю Android Tests
конфигурацию из Android Studio, я вижу, что мое обычное приложение также запускается. Я вижу, что onCreate
метод запускается внутри моего класса приложения (что действительно плохо, поскольку я загружаю туда некоторые дополнительные ресурсы).
Почему Android Studio / gradle также запускает мое приложение?
Могу ли я программно определить, нахожусь ли я в тестовой или обычной конфигурации?
Могу ли я остановить загрузку моего обычного приложения перед запуском тестов?
Кроме того, когда я запускаю тесты в режиме отладки, он не останавливается на точках останова, размещенных внутри метода приложения onCreate
. Почему это происходит?
Редактировать:
Тело тестового класса на самом деле не имеет значения, это может быть что-то вроде:
public class SimpleTest extends AndroidTestCase {
public void testSample()
{
assertEquals(true, false);
}
}
Выполнение только этого простого теста запускает onCreate
метод внутри класса приложения.
Консоль Gradle выводит:
Executing tasks: [:app:assembleDebug, :app:assembleDebugTest]
Я предполагаю, что первая задача создает экземпляр моего Application
класса — это ожидаемое поведение?
Комментарии:
1. Это помогло бы увидеть тесты, о которых вы говорите. С информацией, которую вы нам предоставили, я могу только догадываться, что может быть не так. И что вы имеете в виду, когда говорите «мое обычное приложение тоже запускается»? И для отладки теста вы должны запустить тест в режиме отладки, как если бы вы хотели отладить приложение.
2. @XaverKapeller — Я добавил некоторую дополнительную информацию. Я был смущен тем, что мои ресурсы из метода onCreate все еще загружаются во время выполнения тестов, поэтому я поместил точку останова внутри этого метода и попытался запустить режим отладки. Удивительно, но на этом дело не остановилось. Я мог быть уверен в этом только путем добавления некоторых журналов.
Ответ №1:
Почему Android Studio / gradle также запускает мое приложение?
Могу ли я остановить загрузку моего обычного приложения перед запуском тестов?
AndroidTestCase
это расширение JUnit TestCase
, которое знает о вашем приложении для Android. Если вам не нужно тестировать свое приложение для Android и вы хотите протестировать только обычную java, вам следует использовать JUnit framework. Создайте обычные тесты JUnit, не используйте там классы Android и запустите конфигурацию тестирования JUnit следующим образом:
Вы должны рассматривать AndroidTestCase
как инструментальные тесты, которые будут создавать приложение для Android и запускать на нем эти тесты. Это полезно при сочетании Espresso и Robotium. Оба работают поверх базовых тестовых классов Android, и оба будут создавать и запускать ваше приложение перед его тестированием. Требуется реальное устройство или эмулятор.
Используйте простые тесты JUnit или Robolectric для тестирования java на настольной JVM.
Могу ли я программно определить, нахожусь ли я в тестовой или обычной конфигурации?
Вы можете использовать возможности gradle для предоставления такой информации в автоматически сгенерированном BuildConfig
файле.
На вашем build.gradle
android {
defaultConfig {
testPackageName "com.foo.test"
}
}
В вашем коде:
BuildConfig.PACKAGE_NAME.equals("com.foo.test")
Комментарии:
1. Не могли бы вы подробнее рассказать о «инструментирующих тестах, которые будут создавать приложение для Android и запускать на нем эти тесты». Почему он должен запускать приложение после его сборки? И используя ваш BuildConfig. PACKAGE_NAM не позволит мне обнаруживать тестовую конфигурацию при проверке ее внутри метода onCreate приложения, верно?
2. Тесты инструментария предназначены для тестирования пользовательского интерфейса. Итак, InstrumentationRunner запускает приложение, нажимает на текст, проверяет, виден ли вид и т. Д. . Вы могли бы описать его как бота, который использует приложение, чтобы проверить, работают ли определенные вещи для ваших пользователей. Поэтому приложение должно быть запущено. Для прямых тестов ваших классов вместо этого используйте Unittests. Я думаю, вам следует кое-что прочитать о unittests и инструментированных тестах
3. Я думал, что Robotium и Espresso нуждаются в методе getActivity(), и поэтому они зависят от класса AndroidInstrumentationTestCase2?
4.Вы не можете просто создать свой экземпляр
Activity
и протестировать его. ПотомуonCreate
что,onResume
и другие не являются частью конструктора класса Java и, как ожидается, будут управляться системой жизненного цикла Android. Другими словами, чтобы создатьActivity
экземпляр, вам нужно запустить приложение с ним и запуститьApplication
onCreate
, потому что оно вызывается перед любымActivity
методом как часть жизненного цикла Android. Переместите свою логику из базовых классов Android, таких как application, activity, fragment и т. Д., И протестируйте ее через JUnit, если вы не хотите иметь дело с запущенным приложением.5. @SergiiPechenizkyi на самом деле я не тестирую действия, и у меня есть бизнес-логика, не связанная с ними. Мне просто нужен экземпляр контекста для тестирования таких материалов, как база данных, или некоторые классы должны загружать ресурсы из XML-файлов. Значит, невозможно протестировать такие классы (используя контекст) без предварительного запуска приложения?
Ответ №2:
Это AndroidTestCase
модульный тест, который, к сожалению, выполняется на устройстве (виртуальном или реальном).
Я думаю, что вы хотите иметь UnitTestFramework, который выполняется в JVM (локально на вашем компьютере). Это может сделать Robolectric TestFramework.
Я запустил проект на GitHub, чтобы показать, как настроить тестовый файл gradle и структуру проекта, если вы хотите, чтобы UnitTests и InstrumentationTests были параллельными. Если вы хотите посмотреть его тесты AndroidGradleTests