Java:自定义 DI 配置如何适用于 WAR 和 EAR

标签 java dependency-injection war ear

我编写了一个 Bootstrapper 类,它从类路径读取 XML 文件,并且可以在运行时被其他类用作轻量级依赖注入(inject)器:

<!-- myAppConfig.xml -->
<appConfig>
    <environment runningOn="LOCAL" host="localhost.example.com" system="Windows 7"/>
</appConfig>

public class Bootstrapper
{
    private String runningOn = "Unknown";
    private String host = "Unknown";
    private String system = "Unknown";

    public Bootstrapper(final String appConfigFileName)
    {
        setRunningOn(extractRunningOn(appConfigFileName));
        setHost(extractHost(appConfigFileName));
        setSystem(extractSystem(appConfigFileName));
    }

    public String getHost()
    {
        return host;
    }

    // Rest of class ommitted for brevity...
}

// Then in an executable JAR's main method:
public static void main(String[] args)
{
    Bootstrapper bootstrapper = new Bootstrapper("myAppConfig.xml");

    // Prints: "This app is running on the localhost.example.com server node."
    System.out.println("This app is running on the " +
        bootstrapper.getHost() + " server node.");
}

从这个意义上说,appConfigBootstrapper 充当轻量级“DI”机制。

我想知道的是:如何将此设计转换为 WAR 的 web.xml 和 EAR 的 server.xml?

在可执行 JAR 中,main 方法显式实例化一个 Bootstrapper,然后可以询问其字段/属性,而在 WAR/EAR 中,所有内容都在 XML 文件 (web.xml/server.xml) 中定义,没有单个“入口点”。因此,在 WAR 或 EAR 中,如果我有多个类,每个类都需要知道本地主机名是什么,那么我必须一遍又一遍地实例化相同的 Bootstrapper,每次都向其传递相同的 myAppConfig.xml

我想知道是否有一种方法可以配置 web.xml 和 server.xml 以在启动/部署时实例化 Bootstrapper,并立即自动注入(inject)/填充我的依赖类(或者至少,让每个依赖类访问 XML 文件中定义的全局/单例 Bootstrapper)。

提前致谢!

最佳答案

对于 war (以及耳朵,因为它将包含 war )项目,您可以使用 ServletContextListener 来实例化您的 Bootstrapper。

如何使用 ServletContextListener 的一个很好的例子是 here .

但是,如果您使用 Java EE 6,那么更好的方法是使用 EJB 3.1 Singleton 和一些 CDI。

import javax.ejb.Singleton
import javax.ejb.Startup
import javax.enterprise.context.ApplicationScoped

@Singleton         // EJB 3.1 Singleton
@Startup           // Telling the container to eagerly load on startup
@ApplicationScoped // CDI Scope
public class Bootstrapper {

    private String host = "Unknown";

    @PostConstruct
    public void readConfiguration() {
        // ... load your xml file
    }

    public String getHost() {
        return host;
    }
}

使用上述内容,您现在可以通过简单的 @Inject 或 @EJB 注释在大多数 EE 6 生态系统中注入(inject)此 Bootstrapper bean。

关于Java:自定义 DI 配置如何适用于 WAR 和 EAR,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/10387361/

相关文章:

JavaFX 滚动 Pane 从不滚动

C# 依赖注入(inject) - 注入(inject)采用相同接口(interface)作为参数的接口(interface)

java - 使用Java ObjectMapper获取JSON字符串

java - Tomcat:配置类的应用程序监听器时出错

localization - 本地化来自域对象(实体)的验证消息

java - Tomcat 7 : cached copy of war file deployed

java - 如何配置 grails 在生成 war 时保留 grails.app.context 变量?

java - 将 DukeScript 客户端工件打包到 war 中并从 Web 容器(例如 Tomcat)提供服务

Java程序接受输入两次

javafx - 传递参数JavaFX FXML