IntelliJ JUnit 5 测试 运行 可以作为 Gradle 任务。当 运行 作为单独的测试时,有时会出现异常:NoClassDefFoundError .../TestExecutionListener

IntelliJ JUnit 5 test run fine as Gradle task. When run as individual test sometimes get exception: NoClassDefFoundError .../TestExecutionListener

在 Windows10 上使用 IntelliJ IDEA 2018.2.5 版(社区版),并从 JUnit 团队学习如何使用 JUnit 5 parameterized tests with Gradle 4.8 based on JUnit 5 samples

测试运行如预期gradle任务测试但有时运行宁个人测试得到

Exception in thread "main" java.lang.NoClassDefFoundError:  
   org/junit/platform/launcher/TestExecutionListener

如何在仍然使用 IntelliJ 2018.2.5(社区版)、带有参数测试的 JUnit 5 并使用 Gradle 的情况下修复此异常?

我一直在努力寻找这个问题的答案,但我 运行 的大部分内容都是注意到 IntellJ 与 JUnit 5 一起使用的答案在很多 t运行 中所以不确定该相信什么。

详情

我知道细节和屏幕截图比正常情况或超出正常情况多得多,但是当您学习新事物并需要帮助并开始寻找信息时,您会厌倦看到遗漏一些重要细节的答案.因此,对于那些在同一条船上并且需要看到丢失的细节的人,希望我已经把它包含在这里。虽然这个问题可能不是您要找的问题,但此处的详细信息可能会对您有所帮助。

异常堆栈跟踪

Exception in thread "main" java.lang.NoClassDefFoundError: org/junit/platform/launcher/TestExecutionListener
at java.base/java.lang.ClassLoader.defineClass1(Native Method)
at java.base/java.lang.ClassLoader.defineClass(ClassLoader.java:1016)
at java.base/java.security.SecureClassLoader.defineClass(SecureClassLoader.java:174)
at java.base/jdk.internal.loader.BuiltinClassLoader.defineClass(BuiltinClassLoader.java:802)
at java.base/jdk.internal.loader.BuiltinClassLoader.findClassOnClassPathOrNull(BuiltinClassLoader.java:700)
at java.base/jdk.internal.loader.BuiltinClassLoader.loadClassOrNull(BuiltinClassLoader.java:623)
at java.base/jdk.internal.loader.BuiltinClassLoader.loadClass(BuiltinClassLoader.java:581)
at java.base/jdk.internal.loader.ClassLoaders$AppClassLoader.loadClass(ClassLoaders.java:178)
at java.base/java.lang.ClassLoader.loadClass(ClassLoader.java:521)
at com.intellij.junit5.JUnit5IdeaTestRunner.createListeners(JUnit5IdeaTestRunner.java:39)
at com.intellij.rt.execution.junit.IdeaTestRunner$Repeater.startRunnerWithArgs(IdeaTestRunner.java:45)
at com.intellij.rt.execution.junit.JUnitStarter.prepareStreamsAndStart(JUnitStarter.java:242)
at com.intellij.rt.execution.junit.JUnitStarter.main(JUnitStarter.java:70)
Caused by: java.lang.ClassNotFoundException: org.junit.platform.launcher.TestExecutionListener
at java.base/jdk.internal.loader.BuiltinClassLoader.loadClass(BuiltinClassLoader.java:583)
at java.base/jdk.internal.loader.ClassLoaders$AppClassLoader.loadClass(ClassLoaders.java:178)
at java.base/java.lang.ClassLoader.loadClass(ClassLoader.java:521)
... 13 more

软件版本

微软 Windows 版本 10.0.171314.345

IntelliJ IDEA 2018.2.5(社区版)
构建 #IC-182.4892.20,构建于 2018 年 10 月 16 日 JRE: 1.8.0_152-release-1248-b19 amd64
JVM:JetBrains 的 OpenJDK 64 位服务器虚拟机 s.r.o
项目 SDK:11(java 版本“11.0.1”) IntelliJ 是为此示例安装的干净版本。

使用的特定 JUnit 示例:junit5-jupiter-starter-gradle

Gradle: 4.8

build.gradle - 与演示中的完全相同

plugins {
    id 'java'
    id 'eclipse' // optional (to generate Eclipse project files)
    id 'idea' // optional (to generate IntelliJ IDEA project files)
}

repositories {
    mavenCentral()
}

dependencies {
    testCompile('org.junit.jupiter:junit-jupiter-api:5.3.1')
    testCompile('org.junit.jupiter:junit-jupiter-params:5.3.1')
    testRuntime('org.junit.jupiter:junit-jupiter-engine:5.3.1')
}

test {
    useJUnitPlatform()
    testLogging {
        events "passed", "skipped", "failed"
    }
}

wrapper {
    gradleVersion = '4.8'
}

Gradle 运行纳尔:Platform Test Runner

用于构建项目的步骤

已下载junit5-samples
未压缩文件
在目录 junit5-samples-r5.3.1 下复制 junit5-jupiter-starter-gradleC:\Users\Eric\IdeaProjects

在欢迎屏幕上使用 IntelliJ 导入项目 加载项目。

采用导入项目对话框选项的默认选项,例如单击所有 Import Project 个对话框页面的 'Next' 或 'Finish'。

C:.
|   .gitignore
|   build-JITPACK.gradle
|   build-SNAPSHOT.gradle
|   build.gradle
|   gradlew
|   gradlew.bat
|   README.md
|
+---.idea
|   |   misc.xml
|   |   modules.xml
|   |   workspace.xml
|   |
|   \---libraries
|           gradle_wrapper.xml
|
+---gradle
|   \---wrapper
|           gradle-wrapper.jar
|           gradle-wrapper.properties
|
\---src
    +---main
    |   |   main.iml
    |   |
    |   \---java
    |       \---com
    |           \---example
    |               \---project
    |                       Calculator.java
    |
    \---test
        |   test.iml
        |
        \---java
            \---com
                \---example
                    \---project
                            CalculatorTests.java

项目打开时收到关于 Unlinked Gradle project 的事件日志并单击 Import Gradle project

C:.
|   .gitignore
|   build-JITPACK.gradle
|   build-SNAPSHOT.gradle
|   build.gradle
|   gradlew
|   gradlew.bat
|   README.md
|
+---.gradle
|   +---4.8
|   |   +---fileChanges
|   |   |       last-build.bin
|   |   |
|   |   \---fileHashes
|   |           fileHashes.lock
|   |
|   \---vcsWorkingDirs
|           gc.properties
|
+---.idea
|   |   compiler.xml
|   |   gradle.xml
|   |   misc.xml
|   |   modules.xml
|   |   workspace.xml
|   |
|   +---libraries
|   |       gradle_wrapper.xml
|   |       Gradle__org_apiguardian_apiguardian_api_1_0_0.xml
|   |       Gradle__org_junit_jupiter_junit_jupiter_api_5_3_1.xml
|   |       Gradle__org_junit_jupiter_junit_jupiter_engine_5_3_1.xml
|   |       Gradle__org_junit_jupiter_junit_jupiter_params_5_3_1.xml
|   |       Gradle__org_junit_platform_junit_platform_commons_1_3_1.xml
|   |       Gradle__org_junit_platform_junit_platform_engine_1_3_1.xml
|   |       Gradle__org_opentest4j_opentest4j_1_1_1.xml
|   |
|   \---modules
|           junit5-jupiter-starter-gradle.iml
|           junit5-jupiter-starter-gradle_main.iml
|           junit5-jupiter-starter-gradle_test.iml
|
+---gradle
|   \---wrapper
|           gradle-wrapper.jar
|           gradle-wrapper.properties
|
\---src
    +---main
    |   |   main.iml
    |   |
    |   \---java
    |       \---com
    |           \---example
    |               \---project
    |                       Calculator.java
    |
    \---test
        |   test.iml
        |
        \---java
            \---com
                \---example
                    \---project
                            CalculatorTests.java

使用 Gradle 任务构建项目:build

C:.
|   .gitignore
|   build-JITPACK.gradle
|   build-SNAPSHOT.gradle
|   build.gradle
|   gradlew
|   gradlew.bat
|   README.md
|
+---.gradle
|   +---4.8
|   |   +---fileChanges
|   |   |       last-build.bin
|   |   |
|   |   +---fileContent
|   |   |       annotation-processors.bin
|   |   |       fileContent.lock
|   |   |
|   |   +---fileHashes
|   |   |       fileHashes.bin
|   |   |       fileHashes.lock
|   |   |       resourceHashesCache.bin
|   |   |
|   |   \---taskHistory
|   |           taskHistory.bin
|   |           taskHistory.lock
|   |
|   +---buildOutputCleanup
|   |       buildOutputCleanup.lock
|   |       cache.properties
|   |       outputFiles.bin
|   |
|   \---vcsWorkingDirs
|           gc.properties
|
+---.idea
|   |   compiler.xml
|   |   gradle.xml
|   |   misc.xml
|   |   modules.xml
|   |   workspace.xml
|   |
|   +---libraries
|   |       gradle_wrapper.xml
|   |       Gradle__org_apiguardian_apiguardian_api_1_0_0.xml
|   |       Gradle__org_junit_jupiter_junit_jupiter_api_5_3_1.xml
|   |       Gradle__org_junit_jupiter_junit_jupiter_engine_5_3_1.xml
|   |       Gradle__org_junit_jupiter_junit_jupiter_params_5_3_1.xml
|   |       Gradle__org_junit_platform_junit_platform_commons_1_3_1.xml
|   |       Gradle__org_junit_platform_junit_platform_engine_1_3_1.xml
|   |       Gradle__org_opentest4j_opentest4j_1_1_1.xml
|   |
|   \---modules
|           junit5-jupiter-starter-gradle.iml
|           junit5-jupiter-starter-gradle_main.iml
|           junit5-jupiter-starter-gradle_test.iml
|
+---build
|   +---classes
|   |   \---java
|   |       +---main
|   |       |   \---com
|   |       |       \---example
|   |       |           \---project
|   |       |                   Calculator.class
|   |       |
|   |       \---test
|   |           \---com
|   |               \---example
|   |                   \---project
|   |                           CalculatorTests.class
|   |
|   +---libs
|   |       junit5-jupiter-starter-gradle.jar
|   |
|   +---reports
|   |   \---tests
|   |       \---test
|   |           |   index.html
|   |           |
|   |           +---classes
|   |           |       com.example.project.CalculatorTests.html
|   |           |
|   |           +---css
|   |           |       base-style.css
|   |           |       style.css
|   |           |
|   |           +---js
|   |           |       report.js
|   |           |
|   |           \---packages
|   |                   com.example.project.html
|   |
|   +---test-results
|   |   \---test
|   |       |   TEST-com.example.project.CalculatorTests.xml
|   |       |
|   |       \---binary
|   |               output.bin
|   |               output.bin.idx
|   |               results.bin
|   |
|   \---tmp
|       +---compileJava
|       +---compileTestJava
|       \---jar
|               MANIFEST.MF
|
+---gradle
|   \---wrapper
|           gradle-wrapper.jar
|           gradle-wrapper.properties
|
\---src
    +---main
    |   |   main.iml
    |   |
    |   \---java
    |       \---com
    |           \---example
    |               \---project
    |                       Calculator.java
    |
    \---test
        |   test.iml
        |
        \---java
            \---com
                \---example
                    \---project
                            CalculatorTests.java

Gradle

缓存的文件
C:\Users\Eric\.gradle\caches>tree modules-2 /A /F

C:\USERS\ERIC\.GRADLE\CACHES\MODULES-2
|   modules-2.lock
|
+---files-2.1
|   +---org.apiguardian
|   |   \---apiguardian-api
|   |       \---1.0.0
|   |           +---2c4e5835b7580f2696be7ee1402f4309b3665cf4
|   |           |       apiguardian-api-1.0.0.pom
|   |           |
|   |           +---3ef5276905e36f4d8055fe3cb0bdcc7503ffc85d
|   |           |       apiguardian-api-1.0.0.jar
|   |           |
|   |           \---777508fa9f3e03cafb3c1fb2eba3dca317f4b1ee
|   |                   apiguardian-api-1.0.0-sources.jar
|   |
|   +---org.junit.jupiter
|   |   +---junit-jupiter-api
|   |   |   \---5.3.1
|   |   |       +---39e68334cdee95898567f54d7358a6926262dde6
|   |   |       |       junit-jupiter-api-5.3.1.pom
|   |   |       |
|   |   |       +---a7e97eac2784395cb991403f9641b042ad972941
|   |   |       |       junit-jupiter-api-5.3.1.jar
|   |   |       |
|   |   |       \---b03f607c0822a283c972e37eaeacb00dc3a3c2e7
|   |   |               junit-jupiter-api-5.3.1-sources.jar
|   |   |
|   |   +---junit-jupiter-engine
|   |   |   \---5.3.1
|   |   |       +---c769957170b2240854d6da6c6706dcc2a281542f
|   |   |       |       junit-jupiter-engine-5.3.1-sources.jar
|   |   |       |
|   |   |       +---e0b10da40cae904d69b805021bc1f5d64994aa93
|   |   |       |       junit-jupiter-engine-5.3.1.pom
|   |   |       |
|   |   |       \---e2676b1786c57a80eb98f5bebd51a3d05e228c40
|   |   |               junit-jupiter-engine-5.3.1.jar
|   |   |
|   |   \---junit-jupiter-params
|   |       \---5.3.1
|   |           +---9dfac3fbd6768974fc0c142304a3e90ba713b2a8
|   |           |       junit-jupiter-params-5.3.1.jar
|   |           |
|   |           +---bc4eb2ef307286fcd45551d4da397518c2e15394
|   |           |       junit-jupiter-params-5.3.1-sources.jar
|   |           |
|   |           \---cf0c573f1a0446afb8d544a5fd53dae4bb433b79
|   |                   junit-jupiter-params-5.3.1.pom
|   |
|   +---org.junit.platform
|   |   +---junit-platform-commons
|   |   |   \---1.3.1
|   |   |       +---297bb35bca3d229c5e6edbffd22de7b5ad4cf430
|   |   |       |       junit-platform-commons-1.3.1-sources.jar
|   |   |       |
|   |   |       +---67b7edddfac1935e6e6d9b58d7c7df6db59b1d39
|   |   |       |       junit-platform-commons-1.3.1.jar
|   |   |       |
|   |   |       \---c47714600308339d4b5e203974ebd2ce50eb2109
|   |   |               junit-platform-commons-1.3.1.pom
|   |   |
|   |   \---junit-platform-engine
|   |       \---1.3.1
|   |           +---3ee68a06bbdab157dd260e2095c356481d6cd172
|   |           |       junit-platform-engine-1.3.1.jar
|   |           |
|   |           +---db2bf7e793fec08aed5c588eb495595e4acc9fc7
|   |           |       junit-platform-engine-1.3.1.pom
|   |           |
|   |           \---effe038ffcf21f6988e78b12119ca456d7d144fd
|   |                   junit-platform-engine-1.3.1-sources.jar
|   |
|   \---org.opentest4j
|       \---opentest4j
|           \---1.1.1
|               +---6554a839d3c3f1c77c593498a3ae4b692878946a
|               |       opentest4j-1.1.1.pom
|               |
|               +---88a3a2cb15c413565462cea99f201b67bc6d2f10
|               |       opentest4j-1.1.1-sources.jar
|               |
|               \---efd9f971e91074491ea55b19f67b13470cf4fcdd
|                       opentest4j-1.1.1.jar
|
\---metadata-2.58
    |   module-artifact.bin
    |   module-artifacts.bin
    |   module-metadata.bin
    |   resource-at-url.bin
    |
    \---descriptors
        +---org.apiguardian
        |   \---apiguardian-api
        |       \---1.0.0
        |           \---f8e6315c37eb56998f7a5ba08e30db71
        |                   descriptor.bin
        |
        +---org.junit.jupiter
        |   +---junit-jupiter-api
        |   |   \---5.3.1
        |   |       \---f8e6315c37eb56998f7a5ba08e30db71
        |   |               descriptor.bin
        |   |
        |   +---junit-jupiter-engine
        |   |   \---5.3.1
        |   |       \---f8e6315c37eb56998f7a5ba08e30db71
        |   |               descriptor.bin
        |   |
        |   \---junit-jupiter-params
        |       \---5.3.1
        |           \---f8e6315c37eb56998f7a5ba08e30db71
        |                   descriptor.bin
        |
        +---org.junit.platform
        |   +---junit-platform-commons
        |   |   \---1.3.1
        |   |       \---f8e6315c37eb56998f7a5ba08e30db71
        |   |               descriptor.bin
        |   |
        |   \---junit-platform-engine
        |       \---1.3.1
        |           \---f8e6315c37eb56998f7a5ba08e30db71
        |                   descriptor.bin
        |
        \---org.opentest4j
            \---opentest4j
                \---1.1.1
                    \---f8e6315c37eb56998f7a5ba08e30db71
                            descriptor.bin

右侧面板已关闭
使用左侧的 Project 面板
展开目录以显示 test/java/com.example.project/CalculatorTests.java
双击 CalculatorTests.java

要修复第一个错误,请将光标放在第 13 行的 Assertions 上,然后按 ALT+Enter
单击第一个选项

Add library 'Gradle: org.junit.jupiter:junit-jupiter-api:5.3.1' to classpath  

要修复第二个错误,请将光标放在第 17 行的 ParameterizedTest 上,然后按 ALT+Enter
单击第一个选项

Add library 'Gradle: org.junit.jupiter:junit-jupiter-params:5.3.1' to classpath  

要修复第三个错误,请将光标放在第 26 行的 Calculator 上,然后按 ALT+Enter
单击第一个选项

Add dependency on module 'main' 

然后在Gradle选项卡下运行verification->test成功返回预期结果

Testing started at 2:56 PM ...
2:56:07 PM: Executing task 'test'...

> Task :compileJava
> Task :processResources NO-SOURCE
> Task :classes
> Task :compileTestJava
> Task :processTestResources NO-SOURCE
> Task :testClasses
> Task :test
com.example.project.CalculatorTests > addsTwoNumbers() PASSED
com.example.project.CalculatorTests > add(int, int, int)[1] PASSED
com.example.project.CalculatorTests > add(int, int, int)[2] PASSED
com.example.project.CalculatorTests > add(int, int, int)[3] PASSED
com.example.project.CalculatorTests > add(int, int, int)[4] PASSED
BUILD SUCCESSFUL in 6s
3 actionable tasks: 3 executed
2:56:13 PM: Task execution finished 'test'.

然后当 运行在 CalculatorTest.java 中通过单击左边的绿色箭头并选择 Run 'addsTowNumbers()' 进行单独测试时收到:

Exception in thread "main" java.lang.NoClassDefFoundError:  
   org/junit/platform/launcher/TestExecutionListener

编辑

现在个人测试工作

昨天我保存了项目然后加载了同样失败的Maven sample。当我今天醒来时,我决定再修改 Gradle 样本。当我单击左边距中的箭头进行一次测试时,这次它起作用了。目前我能想到的唯一原因是它现在工作的原因是 运行 在 Maven 示例中发生了一些变化,或者在关闭和重新打开项目时发生了一些变化。

CalculatorTest.java

/*
 * Copyright 2015-2018 the original author or authors.
 *
 * All rights reserved. This program and the accompanying materials are
 * made available under the terms of the Eclipse Public License v2.0 which
 * accompanies this distribution and is available at
 *
 * http://www.eclipse.org/legal/epl-v20.html
 */

package com.example.project;

import static org.junit.jupiter.api.Assertions.assertEquals;

import org.junit.jupiter.api.DisplayName;
import org.junit.jupiter.api.Test;
import org.junit.jupiter.params.ParameterizedTest;
import org.junit.jupiter.params.provider.CsvSource;

class CalculatorTests {

    @Test
    @DisplayName("1 + 1 = 2")
    void addsTwoNumbers() {
        Calculator calculator = new Calculator();
        assertEquals(2, calculator.add(1, 1), "1 + 1 should equal 2");
    }

    @ParameterizedTest(name = "{0} + {1} = {2}")
    @CsvSource({
            "0,    1,   1",
            "1,    2,   3",
            "49,  51, 100",
            "1,  100, 101"
    })
    void add(int first, int second, int expectedResult) {
        Calculator calculator = new Calculator();
        assertEquals(expectedResult, calculator.add(first, second),
                () -> first + " + " + second + " should equal " + expectedResult);
    }
}

第 20 行的 运行ning 测试结果:class CalculatorTests {

第 24 行的 运行ning 测试结果:void addsTwoNumbers() {

第 36 行的 运行ning 测试结果:void add(int first, int second, int expectedResult) {

运行ning Gradle 任务的结果:test

选择的考试很重要

CalculatorTests

创建了两个Run/Debug Configurations
  1. CalculatorTestsUse classpath of module:test 并抛出异常。
  2. CalculatorTests (1)Use classpath of module:junit5-jupiter-starter-gradle_test 并成功完成。

IntelliJ IDEA(针对此问题社区 2018.2)有时会为 JUnit5 测试生成无效配置。

要从菜单中查看 运行 配置,请选择:运行 -> 编辑配置...

两个不同的结果

在此示例中,IntelliJ IDEA 为 Class CalculatorTests 生成了两个 运行 配置。

1.

第一个配置产生异常:

Exception in thread "main" java.lang.NoClassDefFoundError:   
  org/junit/platform/launcher/TestExecutionListener

2.

第二个配置运行正确

总结

因此,当 运行 通过单击左边距中的绿色箭头进行单独测试时,测试结果出现异常。检查哪个配置实际上是 运行ning

然后检查测试的配置详细信息

确保 Use classpath or module 设置正确。