相对于类

时间:2017-10-05 06:51:41

标签: java java-ee classpath classloader ear

我很困惑java从类加载器的角度来看文件系统。

假设我在EAR的APP-INF / lib文件夹中有一个jar文件。此jar文件包含一个实例化new File("foo.txt")的类。此外,foo.txt位于jar。旁边的APP-INF / lib文件夹中。

然后,我在WAR模块中使用此库。现在,代码是否仍然可以找到该文件,或者除了它在EAR的根目录或WAR的根目录中找到它之外?

2 个答案:

答案 0 :(得分:1)

我很确定该文件需要在WAR的根目录下,因为WAR会从您的jar文件中加载来自EAR的APP-INF / lib,因此它将相对于WAR的文件路径< / p>

这是一个如何在类路径中处理它的例子

package main;

import java.io.IOException;
import java.io.InputStream;
import java.net.URL;

public class Test {

    private Test() {
        Class<?> c = this.getClass();
        ClassLoader cl = c.getClassLoader();
        InputStream[] iss = new InputStream[8];
        URL[] urls = new URL[8];
        iss[0] = c.getResourceAsStream("/resources/txtFile.txt");
        iss[1] = c.getResourceAsStream("resources/txtFile.txt");
        iss[2] = c.getResourceAsStream("/txtFile.txt");
        iss[3] = c.getResourceAsStream("txtFile.txt");
        iss[4] = cl.getResourceAsStream("/resources/txtFile.txt");
        iss[5] = cl.getResourceAsStream("resources/txtFile.txt");
        iss[6] = cl.getResourceAsStream("/txtFile.txt");
        iss[7] = cl.getResourceAsStream("txtFile.txt");
        urls[0] = c.getResource("/resources/txtFile.txt");
        urls[1] = c.getResource("resources/txtFile.txt");
        urls[2] = c.getResource("/txtFile.txt");
        urls[3] = c.getResource("txtFile.txt");
        urls[4] = cl.getResource("/resources/txtFile.txt");
        urls[5] = cl.getResource("resources/txtFile.txt");
        urls[6] = cl.getResource("/txtFile.txt");
        urls[7] = cl.getResource("txtFile.txt");
        for (int i = 0; i < 8; i++)
            System.out.println("iss[" + i + "] is "
                    + String.valueOf(iss[i] == null));
        for (int i = 0; i < 8; i++)
            System.out.println("url[" + i + "] is "
                    + String.valueOf(urls[i] == null));

    }

    public static final void main(String[] args) {
        new Test();
    }
}

打印

iss[0] is false
iss[1] is true
iss[2] is true
iss[3] is true
iss[4] is true
iss[5] is false
iss[6] is true
iss[7] is true
url[0] is false
url[1] is true
url[2] is true
url[3] is true
url[4] is true
url[5] is false
url[6] is true
url[7] is true

答案 1 :(得分:1)

您不能依赖于能够以java.io.File对象的身份访问EAR文件部署中的任何内容。

Java EE服务器不需要在文件系统中“爆炸”部署,许多不会。一些供应商可能会提供这样做的选项,但一般而言,依赖此功能并不明智。

此外,使用类加载器完全无法访问内置到EAR文件中的普通文件。

在EAR文件中,如果对象位于EAR / lib jar文件,EJB模块,RAR模块或WEB模块(WAR)中,则只能从类加载器访问对象。即便如此,有关于哪些模块可以在其他模块中看到的规则,如My ear is not able to find ejb module classes

的答案中所述

那就是说,你的问题是指一个非标准的APP-INF/lib目录。您需要参考供应商文档以了解它的功能。我模糊地回忆起它是WebLogic或WebSphere中EAR / lib机制标准化的前提(在2009年的Java EE 5中)。