针对 Java EE 6 API 进行测试

Posted

技术标签:

【中文标题】针对 Java EE 6 API 进行测试【英文标题】:Testing against Java EE 6 API 【发布时间】:2011-03-26 08:24:24 【问题描述】:

我为 JAX-RS 编写了一个补充,并将 Java EE 6 API 作为 Maven 依赖项包含在内。

<dependency>
    <groupId>javax</groupId>
    <artifactId>javaee-api</artifactId>
    <version>6.0</version>
    <scope>provided</scope>
</dependency>

然后我有一个小测试用例:

  @Test
  public void testIsWriteable() 
    class SpecialViewable extends Viewable 
      public SpecialViewable() 
        super("test");
      
    
    FreeMarkerViewProcessor processor = new FreeMarkerViewProcessor(null);
    assertTrue(processor.isWriteable(SpecialViewable.class, null, null,
            MediaType.WILDCARD_TYPE));
  

但我得到一个错误:

java.lang.ClassFormatError: Absent Code attribute in method that is not native or abstract in class file javax/ws/rs/core/MediaType
    ...

如果我将 Jersey 作为 JAX-RS 实现而不是 Java EE API,一切都很好。

感谢 BalusC 的提示,我知道我猜到了什么:Java EE 6 只是一个没有方法体的 API: From the java.net blog

你可以用这个编译你的代码 jar,但你当然不能运行 你的应用程序,因为它 仅包含 Java EE 5 API 和 不包含任何方法体。如果 你试着跑,你会得到这个 例外:

线程“main”中的异常 java.lang.ClassFormatError:不存在 方法中的代码属性不是 类文件中的本机或抽象 javax/邮件/会话

为了执行 Java EE 5 应用程序,你仍然需要一个 Java EE 5 容器,例如 GlassFish 应用服务器。

我尝试使用 test 范围添加 Jersy,但没有成功。

<dependency>
    <groupId>javax</groupId>
    <artifactId>javaee-api</artifactId>
    <version>6.0</version>
    <scope>provided</scope>
</dependency>
<dependency>
    <groupId>com.sun.jersey</groupId>
    <artifactId>jersey-server</artifactId>
    <version>$jersey-version</version>
    <scope>test</scope>
</dependency>

如何测试仅依赖于官方 Java EE API 的软件?

解决方案

provider (Jersey) 需要放在 pom.xml 中的 API (javeee-api) 之前

<dependency>
    <groupId>com.sun.jersey</groupId>
    <artifactId>jersey-server</artifactId>
    <version>$jersey-version</version>
    <scope>test</scope>
</dependency>
<dependency>
    <groupId>javax</groupId>
    <artifactId>javaee-api</artifactId>
    <version>6.0</version>
    <scope>provided</scope>
</dependency>

【问题讨论】:

这里有一些相关的问题,有深刻的答案:google.com/… 在遇到这个问题之前,我真的被这个问题咬住了指甲。谢谢! 【参考方案1】:

不确定这是否能解决您的问题,但 GlassFish Embedded 提供了 Java EE 6 实现。将此添加到您的pom.xml

<project>
  ...
  <repositories>
    <repository>
      <id>glassfish-extras-repository</id>
      <url>http://download.java.net/maven/glassfish/org/glassfish/extras</url>
    </repository>
  </repositories>
  ...
  <dependencies>
    <dependency>
      <groupId>org.glassfish.extras</groupId>
      <artifactId>glassfish-embedded-all</artifactId>
      <version>3.0.1</version>
      <scope>test</scope>
    </dependency>
    <dependency>
      <groupId>javax</groupId>
      <artifactId>javaee-api</artifactId>
      <version>6.0</version>
      <scope>provided</scope>
    </dependency>
    ...
  </dependencies>
  ...
</project>

javaee-api之前声明glassfish-embedded-all 工件很重要。

【讨论】:

也许也可以尝试使用 jersey-server 工件(但在 javaee-api 之前声明它)。 我不需要像 GlassFish 这样的完整应用程序服务器,但您提示将提供程序(GlassFish 或在我的情况下为 Jersy)放在 API 成为解决方案之前! 请注意,存储库 URL 实际上应该是 download.java.net/maven/glassfish Java EE 5 是否有嵌入式 glassfish? 这个问题是他们似乎把一堆罐子炸开了,然后把它们一起打包回glassfish-embedded-all。你最好希望你使用的是他们打包在那里的同一个 slf4j 版本,因为他们没有提供一种方法来排除他们给你的东西。必须有更好的方法。【参考方案2】:

对于我来说,JBoss 的实现比整个 Glassfish 小,所以我正在使用:

    <dependency>
        <groupId>org.jboss.spec</groupId>
        <artifactId>jboss-javaee-6.0</artifactId>
        <version>$version.jboss-javaee-6.0</version>
        <type>pom</type>
    </dependency>

&lt;scope&gt;test&lt;/scope&gt; 也应该不会造成伤害。

【讨论】:

JBoss 实现的问题是它有很多依赖收敛失败。【参考方案3】:

与 JSR 提供​​者无关的替代方案是

<dependency>
  <groupId>javax.ws.rs</groupId>
  <artifactId>jsr311-api</artifactId>
  <scope>provided</scope>
</dependency>
<dependency>
    <groupId>javax</groupId>
    <artifactId>javaee-api</artifactId>
    <version>6.0</version>
    <scope>provided</scope>
</dependency>

这允许您将泽西岛与不同的供应商交换。对于 Glassfish 3.1.2,it uses jersey-server 1.11,根据 jersey pom,它使用 jsr311 1.1 版。

【讨论】:

问题是关于单元测试,它不一定在EE容器中运行。

以上是关于针对 Java EE 6 API 进行测试的主要内容,如果未能解决你的问题,请参考以下文章

开发者测试-采用精准测试工具对J2EE Guns开发框架进行测试

从测试数据来看Node.js和Java EE的性能区别

Flask 编写http接口api及接口自动化测试

《Java手写系列》-手写MyBatis框架

TestNG针对特定的API响应结果进行重试

java EE设计模式简介