未注入 JavaEE Wildfly EJB,仅 war 个项目

JavaEE Wildfly EJB not injected, war-only project

我是 JavaEE 的新手,我创建了一个 "hello world" 项目,使用 Hibernate 作为 JPA 提供程序,使用 gradle 构建 并部署到 Wildfly。我想将 @Stateless bean 用于数据库感知 class,它将对数据库执行所有操作,然后将其注入所有包含 REST 端点的 "JAX-RS" classes .

数据库class:

@Stateless
public class DatabaseManager {

    @PersistenceContext
    EntityManager entityManager;

    public DatabaseManager() {
    }

    public String sayHello() {
        // do some db-stuff
        return "EHLO";
    }
}

休息 class:

@Path("/")
@SessionScoped
public class RestMainEndpoint implements Serializable {

    @EJB
    private DatabaseManager databaseManager;

    public RestMainEndpoint() {
    }

    @GET
    @Path("/hello")
    @Produces("text/plain")
    public String helloFromDb() {
        return databaseManager.sayHello();
    }
}

问题是 @EJB private DatabaseManager databaseManager; 总是 null。它永远不会被注入。

我知道 REST 正在运行,因为所有与数据库无关的端点都运行良好。我还假设 DatabaseManager bean 已创建并初始化,因为我可以在 Wildfly 管理面板上看到它。

我不确定我是否正确打包和部署它 - 它全部打包到单个 war 并部署。 我是否需要使用ear或创建单独的项目?我试过了,但我无法成功地将它转换为 ear 项目 gradle.


编辑:在我的源文件的 WEB-INF 目录中我不会有任何 jar,只有 web.xml 和最近添加的 beans.xml (这似乎没有任何效果).有必要吗?

web.xml内容:

<?xml version="1.0" encoding="UTF-8"?>
<web-app id="WebApp_ID" version="2.4" xmlns="http://java.sun.com/xml/ns/j2ee"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/j2ee
    http://java.sun.com/xml/ns/j2ee/web-app_2_4.xsd">
    <display-name>Desktopeo</display-name>
    <servlet>
        <servlet-name>desktopeo</servlet-name>
        <servlet-class>
            org.glassfish.jersey.servlet.ServletContainer
        </servlet-class>
        <init-param>
            <param-name>
                jersey.config.server.provider.packages
            </param-name>
            <param-value>
                edu.desktopeo.server
            </param-value>
        </init-param>
        <load-on-startup>1</load-on-startup>
    </servlet>
    <servlet-mapping>
        <servlet-name>desktopeo</servlet-name>
        <url-pattern>/rest/*</url-pattern>
    </servlet-mapping>
</web-app>

beans.xml内容:

<beans xmlns="http://xmlns.jcp.org/xml/ns/javaee"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xsi:schemaLocation="
      http://xmlns.jcp.org/xml/ns/javaee
      http://xmlns.jcp.org/xml/ns/javaee/beans_1_1.xsd" bean-discovery-mode="all">
</beans>

然而,在output war archive(实际上是一个zip archive)中,我有很多罐子:

我的项目 jars:Commons-1.0.jar(几个 POJO classes)

我的lib jars:(我自己使用gradle添加的libs)

commons-codec-1.10.jar
commons-collections4-4.0.jar
commons-io-2.4.jar
commons-lang3-3.4.jar
guava-19.0-rc2.jar

我的数据库相关的 jar:

hibernate-commons-annotations-5.0.0.Final.jar
hibernate-core-5.0.2.Final.jar
hibernate-entitymanager-5.0.2.Final.jar
hibernate-jpa-2.1-api-1.0.0.Final.jar
sqljdbc4.jar // JDBC driver for MS SQL

其他罐子:(可能主要是其他依赖项)

javaee-api-7.0.jar
activation-1.1.jar
antlr-2.7.7.jar
aopalliance-repackaged-2.4.0-b31.jar
dom4j-1.6.1.jar
genson-1.3.jar
geronimo-jta_1.1_spec-1.1.1.jar
hk2-api-2.4.0-b31.jar
hk2-locator-2.4.0-b31.jar
hk2-utils-2.4.0-b31.jar
jandex-1.2.2.Final.jar
javassist-3.18.1-GA.jar
javax.annotation-api-1.2.jar
javax.inject-1.jar
javax.inject-2.4.0-b31.jar
javax.mail-1.5.0.jar
javax.ws.rs-api-2.0.1.jar
jboss-logging-3.3.0.Final.jar
jersey-client-2.22.1.jar
jersey-common-2.22.1.jar
jersey-container-servlet-2.22.1.jar
jersey-container-servlet-core-2.22.1.jar
jersey-guava-2.22.1.jar
jersey-media-jaxb-2.22.1.jar
jersey-server-2.22.1.jar
jsoup-1.8.3.jar
log4j-1.2.17.jar
slf4j-api-1.7.2.jar
slf4j-log4j12-1.7.2.jar
osgi-resource-locator-1.0.1.jar
validation-api-1.1.0.Final.jar
xml-apis-1.0.b2.jar

问题已解决

正如 Steve C 在回答中所写,问题与输出 war 中不必要的 jars 有关。我将其中几个的范围更改为 provided 并且它有所帮助(并且还使 war 缩小了 4 倍)。

服务器端gradle构建,以供将来参考:

apply plugin: 'java'
apply plugin: 'war'
apply plugin: 'idea'

repositories {
    mavenCentral()
}

buildscript {
    repositories {
        jcenter()
    }
}

configurations {
    provided
}

sourceSets {
    main.compileClasspath += configurations.provided
    test.compileClasspath += configurations.provided
    test.runtimeClasspath += configurations.provided
}

idea {
    module {
        scopes.PROVIDED.plus += [configurations.provided]
    }
}

dependencies {
    provided 'javax:javaee-api:7.0'
    provided 'org.hibernate:hibernate-core:5.0.2.Final'
    provided 'org.hibernate:hibernate-entitymanager:5.0.2.Final'

    // other libs, with regular "compile"
}

您的 EJB 未被注入,因为您已将自己的 JAX-RS 实现副本打包到 Web 应用程序中。此实现不知道如何注入 EJB。

由于这是 WildFly 9,您可以删除所有 jersey jar、它们的依赖项和完整的 web.xml。

在您的 gradle 文件中,您需要确保 javaee-api-7.0 依赖项的范围为 provided。它不应该与您的应用程序打包在一起,因为服务器提供了这些 类。您还需要完全删除 gradle 对:

的引用
  • 激活-1.1.jar
  • geronimo-jta_1.1_spec-1.1.1.jar
  • javax.annotation-api-1.2.jar
  • java.inject-1.jar
  • javax.inject-2.4.0-b31.jar
  • javax.mail-1.5.0.jar
  • javax.ws.rs-api-2.0.1.jar
  • 验证-api-1.1.0.Final.jar
  • xml-apis-1.0.b2.jar

因为这些类都是由javaee-api-7.0依赖提供的

最后,添加一个 java 源文件,其中包含:

import javax.ws.rs.ApplicationPath;
import javax.ws.rs.core.Application;

@ApplicationPath("/rest")
public class JaxRsActivator extends Application {
}

它提供了随 web.xml 一起删除的配置,您应该可以开始了。