【问题标题】:Tycho tests failing due to java.lang.NoClassDefFoundError: junit/framework/AssertionFailedErrorTycho 测试因 java.lang.NoClassDefFoundError 失败:junit/framework/AssertionFailedError
【发布时间】:2012-07-07 08:45:14
【问题描述】:

我完全被这个弄糊涂了。据我了解,它应该有效,但我不知道为什么。

我有一个 tycho 构建,它只在 eclipse 工作台上运行一些测试。但是,我的所有测试都因这种异常而失败:

java.lang.NoClassDefFoundError: junit/framework/AssertionFailedError
at org.grails.ide.eclipse.commands.test.AbstractCommandTest.tearDown(AbstractCommandTest.java:112)
at junit.framework.TestCase.runBare(TestCase.java:140)
at junit.framework.TestResult$1.protect(TestResult.java:110)
at junit.framework.TestResult.runProtected(TestResult.java:128)
at junit.framework.TestResult.run(TestResult.java:113)
at junit.framework.TestCase.run(TestCase.java:124)
at junit.framework.TestSuite.runTest(TestSuite.java:243)
at junit.framework.TestSuite.run(TestSuite.java:238)
at junit.framework.TestSuite.runTest(TestSuite.java:243)
at junit.framework.TestSuite.run(TestSuite.java:238)
at org.springsource.ide.eclipse.commons.tests.util.ManagedTestSuite.run(ManagedTestSuite.java:231)
at org.junit.internal.runners.JUnit38ClassRunner.run(JUnit38ClassRunner.java:83)
at org.apache.maven.surefire.junit4.JUnit4TestSet.execute(JUnit4TestSet.java:53)
at org.apache.maven.surefire.junit4.JUnit4Provider.executeTestSet(JUnit4Provider.java:123)
at org.apache.maven.surefire.junit4.JUnit4Provider.invoke(JUnit4Provider.java:104)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
at java.lang.reflect.Method.invoke(Method.java:597)
at org.apache.maven.surefire.util.ReflectionUtils.invokeMethodWithArray(ReflectionUtils.java:164)
at org.apache.maven.surefire.booter.ProviderFactory$ProviderProxy.invoke(ProviderFactory.java:110)
at org.apache.maven.surefire.booter.SurefireStarter.invokeProvider(SurefireStarter.java:175)
at org.apache.maven.surefire.booter.SurefireStarter.runSuitesInProcess(SurefireStarter.java:123)
at org.eclipse.tycho.surefire.osgibooter.OsgiSurefireBooter.run(OsgiSurefireBooter.java:84)
at org.eclipse.tycho.surefire.osgibooter.AbstractUITestApplication$1.run(AbstractUITestApplication.java:35)
at org.eclipse.swt.widgets.RunnableLock.run(RunnableLock.java:35)
at org.eclipse.swt.widgets.Synchronizer.runAsyncMessages(Synchronizer.java:135)
at org.eclipse.swt.widgets.Display.runAsyncMessages(Display.java:3529)
at org.eclipse.swt.widgets.Display.readAndDispatch(Display.java:3182)
at org.eclipse.e4.ui.internal.workbench.swt.PartRenderingEngine$9.run(PartRenderingEngine.java:1022)
at org.eclipse.core.databinding.observable.Realm.runWithDefault(Realm.java:332)
at org.eclipse.e4.ui.internal.workbench.swt.PartRenderingEngine.run(PartRenderingEngine.java:916)
at org.eclipse.e4.ui.internal.workbench.E4Workbench.createAndRunUI(E4Workbench.java:86)
at org.eclipse.ui.internal.Workbench$5.run(Workbench.java:585)
at org.eclipse.core.databinding.observable.Realm.runWithDefault(Realm.java:332)
at org.eclipse.ui.internal.Workbench.createAndRunWorkbench(Workbench.java:540)
at org.eclipse.ui.PlatformUI.createAndRunWorkbench(PlatformUI.java:149)
at org.eclipse.ui.internal.ide.application.IDEApplication.start(IDEApplication.java:124)
at org.eclipse.tycho.surefire.osgibooter.UITestApplication.runApplication(UITestApplication.java:31)
at org.eclipse.tycho.surefire.osgibooter.AbstractUITestApplication.run(AbstractUITestApplication.java:114)
at org.eclipse.tycho.surefire.osgibooter.UITestApplication.start(UITestApplication.java:37)
at org.eclipse.equinox.internal.app.EclipseAppHandle.run(EclipseAppHandle.java:196)
at org.eclipse.core.runtime.internal.adaptor.EclipseAppLauncher.runApplication(EclipseAppLauncher.java:110)
at org.eclipse.core.runtime.internal.adaptor.EclipseAppLauncher.start(EclipseAppLauncher.java:79)
at org.eclipse.core.runtime.adaptor.EclipseStarter.run(EclipseStarter.java:353)
at org.eclipse.core.runtime.adaptor.EclipseStarter.run(EclipseStarter.java:180)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
at java.lang.reflect.Method.invoke(Method.java:597)
at org.eclipse.equinox.launcher.Main.invokeFramework(Main.java:629)
at org.eclipse.equinox.launcher.Main.basicRun(Main.java:584)
at org.eclipse.equinox.launcher.Main.run(Main.java:1438)
at org.eclipse.equinox.launcher.Main.main(Main.java:1414)

Caused by: java.lang.ClassNotFoundException: junit.framework.AssertionFailedError
at org.eclipse.osgi.internal.loader.BundleLoader.findClassInternal(BundleLoader.java:501)
at org.eclipse.osgi.internal.loader.BundleLoader.findClass(BundleLoader.java:421)
at org.eclipse.osgi.internal.loader.BundleLoader.findClass(BundleLoader.java:412)
at org.eclipse.osgi.internal.baseadaptor.DefaultClassLoader.loadClass(DefaultClassLoader.java:107)
at java.lang.ClassLoader.loadClass(ClassLoader.java:247)
... 54 more

这对我来说没有意义。 org.junit 和 org.junit4 是运行测试的包以及包含 AbstractCommandTest 的包的依赖项。这些测试在我的工作空间中运行时通过了,那么为什么 maven/tycho 无法加载 junit 类?

如果有帮助,我很乐意提供更多信息,例如指向 github 存储库的链接。


编辑:提供更多细节

github 仓库在这里:https://github.com/grails/grails-sts-tests

您可以看到它是一个简单的单个插件,只运行一些测试。测试套件由来自指定为依赖项的其他存储库中的插件的测试组成。请注意,位于其他存储库中的测试插件在另一个 CI 服务器上运行,并且没有 NoClassDefFoundError 问题。我查看了其他 CI 服务器,并没有发现任何不同(不幸的是,此 CI 服务器不可公开访问,因此我无法共享指向它的链接)。

显示问题的 hudson 构建工作在这里:http://hudson.grails.org/job/grails-sts-tests-2.0.x/17/console

【问题讨论】:

  • 请尝试提供更多关于您如何配置 Tycho/测试项目的详细信息。根据我的经验,Tycho 中的构建错误通常不是由于对其默认插件模型的一些小的误解造成的。
  • 谢谢。提供更多细节。
  • java.lang.NoClassDefFoundError 在找不到或无法加载类的依赖项时抛出。由于您说插件在另一个 CI 服务器上编译,我怀疑它在不同的 JVM 版本上运行。你能粘贴完整的堆栈跟踪吗?
  • 是在测试整个项目还是测试一个类时发生?
  • @melix 我添加了完整的堆栈跟踪。这不是很有趣。 JUnit 类位于类路径 somwwhere 中,但测试包的类加载器无法加载它。这是一个 OSGi 问题,我不确定为什么会这样,因为我的测试包需要 JUnit 包。

标签: eclipse maven junit junit4 tycho


【解决方案1】:

我会做的检查:

  1. 检查 NoClassDefFoundError 的原因。最常见的原因有多种,例如 UnSupportedClassVersionError 和 ExceptionINinitializationError。
  2. 使用 JVM 选项 -verbose:class 获取类加载日志并检查类是否从所需类的预期工件加载。

【讨论】:

  • NoClassDefFoundError 由 OSGi 抛出,因为在测试包的类加载器中找不到该类。我刚刚添加了 -verbose:class 选项,并且正在浏览日志。到目前为止没有什么太有趣的事情......
【解决方案2】:

我在一个依赖于几个 3rd 方 jar 的 Android 项目上运行 junit 测试时遇到了类似的问题,问题最终是其中一个依赖 jar 是用 jdk v1.5 构建的,而其他的都是 1.6。我将一个库更新为使用 1.6 构建的较新版本,然后错误消失了。

不知道是不是同样的问题,或者你是否可以配置 tycho 或更新它,但它可能值得一看.....

【讨论】:

    【解决方案3】:

    我们遇到了非常相似的问题。原因是 junit 框架试图创建和使用自定义类加载器,而这与 eclipse 插件类加载器不兼容。我们现在遵循一些使用 Tycho 运行单元测试的指南。

    1. 您的单元测试位于插件片段中。单元测试片段依赖于 JUnit。
    2. 您的 pom 应该关闭对单元测试的系统类加载器的使用。这就是导致 junit 测试类丢失的原因。
    3. 然后您使用与标准插件相同的包装(确切地说是eclipse-plugin)。

    所以一个简单的 POM(对我们来说)看起来像这样:

    <?xml version="1.0" encoding="UTF-8"?>
    <project
    xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"
    xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
      <modelVersion>4.0.0</modelVersion>
      <parent>
        <artifactId>master</artifactId>
        <groupId>mgws</groupId>
        <version>0.0.1-SNAPSHOT</version>
        <relativePath>../../mgws/build-environment/pom.xml</relativePath>
      </parent>
      <groupId>mgws</groupId>
      <artifactId>mgws.spectral.test</artifactId>
      <version>1.0.0-SNAPSHOT</version>
      <packaging>eclipse-plugin</packaging>
      <build>
        <plugins>
          <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-surefire-plugin</artifactId>
            <version>2.12</version>
            <executions>
              <execution>
                <id>JUnitTest</id>
                <goals>
                  <goal>test</goal>
                </goals>
                <phase>install</phase>
                <configuration>
                  <useSystemClassLoader>false</useSystemClassLoader>
                </configuration>
              </execution>
            </executions>
          </plugin>
        </plugins>
      </build>
    </project>
    

    这使得单元测试框架使用 eclipse 插件类加载器,现在它可以找到所有的类。

    【讨论】:

    • 我对此感到惊讶。为什么不使用 tycho-surefire-plugin 运行测试? tycho-surefire-plugin 的配置部分看起来完全不同。但是,感谢 useSystemClassLoader 提示。我现在正在尝试。
    • 我们需要将单元测试作为非插件测试运行。我不记得为什么,已经好几年了。
    • 我必须将其添加到配置中以使测试运行:target/classes
    【解决方案4】:

    仍然没有人能够回答这个问题,但感谢您提供的信息,即使它没有直接有用。

    我已经取得了一些进展。现在,我的 60 个测试中有 45 个通过了。我只是在 tycho-surefire-pluign 配置区域中添加了一些额外的依赖项:

                    <dependencies>
                        <dependency>
                            <type>p2-installable-unit</type>
                            <artifactId>org.junit</artifactId>
                            <version>0.0.0</version>
                        </dependency>
                        ...
                    </dependencies>
    

    不幸的是,剩余的测试仍然失败,同样的NoClassDefFoundError。可能我需要添加更多依赖项,一切都会正常工作。

    【讨论】:

      猜你喜欢
      • 2012-05-27
      • 2019-05-01
      • 2011-07-23
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2022-11-06
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多