在Java中,你可以使用相同的API但使用不同的URL协议加载各种资源:

file:///tmp.txt
http://127.0.0.1:8080/a.properties
jar:http://www.foo.com/bar/baz.jar!/COM/foo/Quux.class

这很好地将资源的实际加载与需要资源的应用程序分离开来,而且由于URL只是一个字符串,资源加载也非常容易配置。

是否存在使用当前类加载器加载资源的协议? 这与Jar协议类似,只是我不需要知道资源来自哪个Jar文件或类文件夹。

当然,我可以使用Class.getResourceAsStream(“a.xml”)做到这一点,但这需要我使用不同的API,因此需要对现有代码进行更改。我希望能够在所有可以为资源指定URL的地方使用它,只需更新属性文件即可。


当前回答

再延伸一下Dilums的回答:

在不更改代码的情况下,您可能需要按照Dilum的建议,使用URL相关接口的自定义实现。为了简化事情,我建议查看Spring Framework的资源的源代码。虽然代码不是流处理程序的形式,但它的设计完全是为了做您想做的事情,并且是在ASL 2.0许可下进行的,这使得它足够友好,可以在您的代码中重用。

其他回答

如果你在类路径中有tomcat,它就像这样简单:

TomcatURLStreamHandlerFactory.register();

这将为“war”和“classpath”协议注册处理程序。

再延伸一下Dilums的回答:

在不更改代码的情况下,您可能需要按照Dilum的建议,使用URL相关接口的自定义实现。为了简化事情,我建议查看Spring Framework的资源的源代码。虽然代码不是流处理程序的形式,但它的设计完全是为了做您想做的事情,并且是在ASL 2.0许可下进行的,这使得它足够友好,可以在您的代码中重用。

我不知道是否已经有了,但你可以很容易地自己做。

在我看来,不同协议的例子就像外观模式。当每种情况都有不同的实现时,您就有了一个公共接口。

您可以使用相同的原理,创建一个ResourceLoader类,它从属性文件中获取字符串,并检查我们的自定义协议

myprotocol:a.xml
myprotocol:file:///tmp.txt
myprotocol:http://127.0.0.1:8080/a.properties
myprotocol:jar:http://www.foo.com/bar/baz.jar!/COM/foo/Quux.class

从字符串开始剥离myprotocol,然后决定用哪种方式加载资源,只给你资源。

URL url = getClass().getClassLoader().getResource("someresource.xxx");

这样就行了。

灵感来自@Stephen https://stackoverflow.com/a/1769454/980442 和http://docstore.mik.ua/orelly/java/exp/ch09_06.htm

使用

new URL("classpath:org/my/package/resource.extension").openConnection()

只需将这个类创建到sun.net.www.protocol.classpath包中,并将其运行到Oracle JVM实现中即可。

package sun.net.www.protocol.classpath;

import java.io.IOException;
import java.net.URL;
import java.net.URLConnection;
import java.net.URLStreamHandler;

public class Handler extends URLStreamHandler {

    @Override
    protected URLConnection openConnection(URL u) throws IOException {
        return Thread.currentThread().getContextClassLoader().getResource(u.getPath()).openConnection();
    }
}

如果您正在使用另一个JVM实现,请设置java.protocol.handler.pkgs=sun.net.www.protocol系统属性。

仅供参考: URL http://docs.oracle.com/javase/7/docs/api/java/net/URL.html(以% 20以% 20 int, % 20以)