2016-09-07 3 views
17

Мы просто портировали наши модульные тесты на JUnit5. Понимая, что это все еще довольно раннее принятие с небольшими намеками на google.Gradle Jacoco и JUnit5

Наиболее сложным было получить покрытие кода jacoco для тестов Junit5, которые мы используем для jenkins. Поскольку это заняло у меня почти день, чтобы понять, я думал, что разделяю. Тем не менее, если вы знаете лучшего решения, мне было бы интересно узнать!

buildscript { 

    dependencies { 
     // dependency needed to run junit 5 tests 
     classpath 'org.junit.platform:junit-platform-gradle-plugin:1.0.0-M2' 
    } 
} 

// include the jacoco plugin 
plugins { 
    id 'jacoco' 
} 

dependencies { 
    testCompile "org.junit.jupiter:junit-jupiter-api:5.0.0-M2" 
    runtime "org.junit.jupiter:junit-jupiter-engine:5.0.0-M2" 
    runtime "org.junit.vintage:junit-vintage-engine:4.12.0-M2" 
} 

apply plugin: 'org.junit.platform.gradle.plugin' 

Тогда проблема, кажется, что junitPlatformTest, как это определено в org.junit.platform.gradle.plugin определяется слишком в конце Gradle фазы жизненного цикла и, следовательно, неизвестно, когда скрипт разбирается.

Для дальнейшего определения задачи jacoco, выполняющей задачу junitPlatformTest, необходим следующий хак.

tasks.whenTaskAdded { task -> 
    if (task.name.equals('junitPlatformTest')) { 
     System.out.println("ADDING TASK " + task.getName() + " to the project!") 

    // configure jacoco to analyze the junitPlatformTest task 
    jacoco { 
     // this tool version is compatible with 
     toolVersion = "0.7.6.201602180812" 
     applyTo task 
    } 

    // create junit platform jacoco task 
    project.task(type: JacocoReport, "junitPlatformJacocoReport", 
      { 
       sourceDirectories = files("./src/main") 
       classDirectories = files("$buildDir/classes/main") 
       executionData task 
      }) 
    } 
} 

Наконец, необходимо настроить плагин junitPlatform. Следующий код позволяет конфигурировать командную строку которых JUnit 5 тегов должны выполняться: Вы можете запустить все тесты с «единицами» тегом, запустив:

gradle clean junitPlatformTest -PincludeTags=unit 

Вы можете запустить все тесты, которые отсутствуют как блок и МЭГ тега с использованием

gradle clean junitPlatformTest -PexcludeTags=unit,integ 

Если теги не указаны, все тесты будут выполнены (по умолчанию).

junitPlatform { 

    engines { 
     include 'junit-jupiter' 
     include 'junit-vintage' 
    } 

    reportsDir = file("$buildDir/test-results") 

    tags { 
     if (project.hasProperty('includeTags')) { 
      for (String t : includeTags.split(',')) { 
       include t 
      } 
     } 

     if (project.hasProperty('excludeTags')) { 
      for (String t : excludeTags.split(',')) { 
       exclude t 
      } 
     } 
    } 

    enableStandardTestTask false 
} 
+0

Я голосую, чтобы закрыть этот вопрос не по теме, потому что это скорее решение, а вопрос – Stanislav

+1

Было бы хорошо, если бы это было разделено на вопрос и ответ. –

+0

Я согласен с @PaulHicks, что это должен быть вопрос с ответами на вопрос. Вы можете увидеть документацию [здесь] (https://stackoverflow.com/help/self-answer). Кроме того, проблема «слишком поздно в жизненном цикле Gradle» должна быть [исправлена ​​в M5] (https://github.com/junit-team/junit5/issues/708). – mkobit

ответ

1

Чтобы получить ссылку на junitPlatformTest задачи, другой вариант реализовать afterEvaluate блок в проекте, как это:

afterEvaluate { 
    def junitPlatformTestTask = tasks.getByName('junitPlatformTest') 

    // do something with the junitPlatformTestTask 
} 

Смотрите мои комментарии на GitHub for JUnit 5 для дальнейших примеров.

5

Спасибо, так хак теперь выглядит следующим образом:

project.afterEvaluate { 
    def junitPlatformTestTask = project.tasks.getByName('junitPlatformTest') 

    // configure jacoco to analyze the junitPlatformTest task 
    jacoco { 
     // this tool version is compatible with 
     toolVersion = "0.7.6.201602180812" 
     applyTo junitPlatformTestTask 
    } 

    // create junit platform jacoco task 
    project.task(type: JacocoReport, "junitPlatformJacocoReport", 
      { 
       sourceDirectories = files("./src/main") 
       classDirectories = files("$buildDir/classes/main") 
       executionData junitPlatformTestTask 
      }) 
} 
3

Может быть также решена с непосредственным впрыском агента:

subprojects { 
    apply plugin: 'jacoco' 

    jacoco { 
     toolVersion = "0.7.9" 
    } 

    configurations { 
     testAgent { 
      transitive = false 
     } 
    } 

    dependencies { 
     testAgent("org.jacoco:org.jacoco.agent:0.7.9:runtime") 
    } 

    tasks.withType(JavaExec) { 
     if (it.name == 'junitPlatformTest') { 
      doFirst { 
       jvmArgs "-javaagent:${configurations.testAgent.singleFile}=destfile=${project.buildDir.name}/jacoco/test.exec" 
      } 
     } 
    } 
} 

тогда отчет будет доступен с jacocoTestReport задачи

+0

Спасибо Яну. Он работает для меня – Sean

-2

Вам просто нужно добавить @RunWith (JUnitPlatform.class) в свой пакет

@RunWith(JUnitPlatform.class) 
public class ClassTest { 
}