Как сообщить о результатах в Sauce Labs, используя Geb/Spock?
Я хочу использовать Java REST API Sauce Labs для отправки статуса Pass/Fail обратно на панель управления SauceLabs. Я использую Geb+Spock, и моя сборка Gradle создает каталог результатов теста, где результаты выводятся в формате XML. Моя проблема в том, что XML-файл результатов не создается, пока не завершится очистка спецификации SpockSpec(). Это заставляет мой код сообщать о результатах предыдущего теста, а не о текущем. Ясно не то, что я хочу!
Есть ли способ получить результаты изнутри cleanupSpec(), не полагаясь на XML? Или способ получить результаты в файл ранее? Или какая-то альтернатива, которая будет намного лучше, чем любая из них?
Некоторый код:
В build.gradle
Я указываю testResultsDir
, Вот где XML-файл записывается после выхода спецификации Spock:
drivers.each { driver ->
task "${driver}Test"(type: Test) {
cleanTest
systemProperty "geb.env", driver
testResultsDir = file("$buildDir/test-results/${driver}")
systemProperty "proj.test.resultsDir", testResultsDir
}
}
Здесь setupSpec()
а также cleanupSpec()
в моем классе LoginSpec:
class LoginSpec extends GebSpec {
@Shared def SauceREST client = new SauceREST("redactedName", "redactedKey")
@Shared def sauceJobID
@Shared def allSpecsPass = true
def setupSpec() {
sauceJobID = driver.getSessionId().toString()
}
def cleanupSpec() {
def String specResultsDir = System.getProperty("proj.test.resultsDir") ?: "./build/test-results"
def String specResultsFile = this.getClass().getName()
def String specResultsXML = "${specResultsDir}/TEST-${specResultsFile}.xml"
def testsuiteResults = new XmlSlurper().parse( new File( specResultsXML ))
// read error and failure counts from the XML
def errors = testsuiteResults.@errors.text()?.toInteger()
def failures = testsuiteResults.@failures.text()?.toInteger()
if ( (errors + failures) > 0 ) { allSpecsPass = false }
if ( allSpecsPass ) {
client.jobPassed(sauceJobID)
} else {
client.jobFailed(sauceJobID)
}
}
}
Остальная часть этого класса содержит спецификации входа, которые не взаимодействуют с SauceLabs. Когда я читаю XML, оказывается, что он был написан в конце предыдущего запуска LoginSpec. Мне нужен способ добраться до значений текущего прогона.
Спасибо!
2 ответа
Отчеты о тестах генерируются после того, как спецификация закончила выполнение, а генерация выполняется системой сборки, как в вашем случае Gradle. Спок не знает об этом, поэтому вы не можете получить эту информацию из теста.
С другой стороны, вы можете легко получить эту информацию от Gradle. Тестовое задание имеет два метода, которые могут вас заинтересовать: addTestListener() и afterSuite(). Кажется, что более чистым решением здесь было бы использовать первый метод, реализовать тестовый слушатель и поместить вашу логику в afterSuite() слушателя (а не в конфигурацию задачи). Возможно, вам потребуется поместить эту реализацию слушателя в buildSrc, так как похоже, что у вас есть зависимость от SauceREST, и вам нужно будет собрать и скомпилировать свой класс слушателя, прежде чем использовать его в качестве аргумента для addTestListener() в build.gradle ваш проект.
Следуя предложению erdi, я создал вспомогательную библиотеку Sauce Gradle, которая предоставляет erdi тестов, который анализирует выходные данные теста XML и вызывает API-интерфейс REST Sauce для установки статуса "пройти / не пройти".
Библиотеку можно включить, добавив в файл build.gradle следующее:
import com.saucelabs.gradle.SauceListener
buildscript {
repositories {
mavenCentral()
maven {
url "https://repository-saucelabs.forge.cloudbees.com/release"
}
}
dependencies {
classpath group: 'com.saucelabs', name: 'saucerest', version: '1.0.2'
classpath group: 'com.saucelabs', name: 'sauce_java_common', version: '1.0.14'
classpath group: 'com.saucelabs.gradle', name: 'sauce-gradle-plugin', version: '0.0.1'
}
}
gradle.addListener(new SauceListener("YOUR_SAUCE_USERNAME", "YOUR_SAUCE_ACCESS_KEY"))
Вам также нужно будет выводить идентификатор сеанса Selenium для каждого теста, чтобы SauceListener мог связать задание Sauce со статусом прохождения / сбоя. Для этого включите следующий вывод в стандартный вывод:
SauceOnDemandSessionID=SELENIUM_SESSION_ID