Как запустить тест Gradle, когда все тесты UP-TO-DATE?
У меня установлен мой скрипт. Когда я выполняю сборку Gradle, все работает, и она запускает тесты jUnit.
После этого, когда я запускаю тест Gradle, я получаю следующее:
C:\Users\..\..\Project>gradle test
:compileJava UP-TO-DATE
:processResources UP-TO-DATE
:classes UP-TO-DATE
:compileTestJava UP-TO-DATE
:processTestResources UP-TO-DATE
:testClasses UP-TO-DATE
:test UP-TO-DATE
Когда я выполняю gradle clean
, то, конечно же, работает Gradle build... Я хочу, чтобы иметь возможность сбросить только те тесты, а не строить весь проект: как мне это сделать?
Ответы
Ответ 1
Один из вариантов будет использовать флаг --rerun-tasks
в командной строке. Это приведет к повторному запуску всей тестовой задачи и всех задач, от которых она зависит.
Если вы заинтересованы только в повторном тестировании, тогда еще один вариант - сделать градулы чистыми результаты тестов перед выполнением тестов. Это можно сделать с cleanTest
задачи cleanTest
.
В некотором роде - плагин Java определяет чистые задачи для каждой из других задач. Согласно документации:
cleanTaskName - Удаляет файлы, созданные указанной задачей. cleanJar удалит JAR файл, созданный задачей jar, и cleanTest удалит результаты теста, созданные тестовой задачей.
Таким образом, все, что вам нужно для повторного запуска ваших тестов, также должно запустить задачу cleanTest
, то есть:
gradle cleanTest test
Ответ 2
Другой вариант - добавить в свой файл build.gradle следующее:
test.outputs.upToDateWhen {false}
Ответ 3
gradle test --rerun-tasks
Указывает, что любая оптимизация задачи игнорируется.
Источник: https://gradle.org/docs/current/userguide/gradle_command_line.html
Ответ 4
Вот решение, использующее файл build.gradle, если вы не хотите изменять свою командную строку:
test {
dependsOn 'cleanTest'
//Your previous task details (if any)
}
И вот выход. Обратите внимание на 2 изменения с вашего предыдущего выхода:
1) На выходе появляется новая задача "cleanTest".
2) "test" всегда очищается (т.е. никогда не "UP-TO-DATE"), поэтому он запускается каждый раз:
$ gradle build
:compileJava UP-TO-DATE
:processResources UP-TO-DATE
:classes UP-TO-DATE
:findMainClass
:jar
:bootRepackage
:assemble
:cleanTest
:compileTestJava UP-TO-DATE
:processTestResources UP-TO-DATE
:testClasses UP-TO-DATE
:test
:check
:build
Ответ 5
Это было недавно темой в блоге Gradle Хватит перезапускать свои тесты. автор показывает пример использования outputs.upToDateWhen { false }
и объясняет, почему это не так:
Это на самом деле не приводит к повторному запуску
Автор этого фрагмента, вероятно, хотел сказать: "Всегда перезапускать мои тесты". Это не то, что делает этот фрагмент, хотя. Это только помечает задачу как устаревшую, заставляя Gradle воссоздать вывод. Но вот в чем дело, если кеш сборки включен, Gradle не нужно запускать задачу, чтобы воссоздать вывод. Он найдет запись в кеше и распакует результат в выходной каталог test.
То же самое относится и к этому фрагменту:
test.dependsOn cleanTest
Gradle распакует результаты теста из кэша сборки после очистки вывода, поэтому ничего не будет перезапущено. Короче говоря, эти фрагменты создают очень дорогое бездействие.
Если вы сейчас думаете: "Хорошо, я тоже деактивирую кеш", позвольте мне сказать вам, почему вы не должны.
Затем автор продолжает объяснять, почему повторный запуск некоторых тестов является пустой тратой времени:
Подавляющее большинство ваших тестов должно быть детерминированным, т.е. при одинаковых входных данных они должны давать тот же результат.
В тех немногих случаях, когда вы хотите повторно запускать тесты, когда код не изменился, вы должны смоделировать их в качестве входных данных. Вот оба примера из поста в блоге, в которых показано добавление входных данных, поэтому задача будет использовать их во время своих текущих проверок.
task randomizedTest(type: Test) {
systemProperty "random.testing.seed", new Random().nextInt()
}
task systemIntegrationTest(type: Test) {
inputs.property "integration.date", LocalDate.now()
}
Я рекомендую прочитать весь пост в блоге.
Ответ 6
Кроме того, необходимость добавления --rerun-tasks
действительно избыточна. Никогда не бывает. Создайте --no-rerun-tasks
--rerun-tasks
и сделайте --rerun-tasks
default, когда cleanTask
Ответ 7
--rerun-tasks
работает, но неэффективно, так как перезапускает все задачи.
cleanTest
само по себе может быть недостаточно из-за кеша сборки.
Итак, лучший способ сделать это:
./gradlew --no-build-cache cleanTest test
Ответ 8
Я думаю, что это правильный вопрос, учитывая, что в Gradle можно запустить этот командный test
, и происходит то, что ничего не происходит!
Но я бы поставил под сомнение необходимость когда-либо делать это, как сказала Джолта в своем комментарии: если код не изменился, почему вам нужно перепроверить? Если у вас есть сомнения в отношении стороннего ввода, я бы сказал, что вам нужно это сделать в коде приложения. Если вы беспокоитесь о том, что ваш код может быть "flaky", то есть он может проходить все тесты в первый раз, но не через секунду (или 100-й раз), вам не нужно думать о том, почему у вас есть эти сомнения и адресовать их?
Лично я думаю, что это (очень незначительная) ошибка дизайна в Gradle: если все полностью обновлено, а не "BUILD SUCCESSFUL", оно должно сказать "NO CHANGE SINCE LAST SUCCESSFUL BUILD: NOTHING DONE".