无法从tomcat中的jar读取文件

时间:2013-01-28 09:38:38

标签: java file-io classloader tomcat7

我有一个在tomcat 7下运行的Web应用程序,在其中一个类中,我试图在WEB-INF / lib文件夹下的一个jar中读取一个文件。

URL resourceURL = MyClass.class.getClassLoader().getResource("xml/xslt/master.xsl");
File xslfile = new File(resourceURL.getPath());
AssertUtil.assertTrue(xslfile.exists(),"xsl file not found");

MyClass和master.xsl都位于同一个jar中,包装没有问题。但是上面的片段在断言语句中失败,因为xslfile.exists返回false。 URL正确解析为jar中文件的位置,如下所示

file:/<MY_WEBAPP_LOCATION>/MyApp/WEB-INF/lib/MyComponent.jar!/xml/xslt/master.xsl

其中MY_WEBAPP_LOCATION对应于我的tomcat服务器webapp目录的绝对路径。

但是,如果我重写下面的代码来读取输入流,它可以正常工作。

InputStream xslFile = MyClass.class.getClassLoader().getResourceAsStream("xml/xslt/master.xsl");

任何人都可以解释阻止从jar资源创建File的原因,而输入流创建工作正常。是否需要从tomcat端获取任何其他权限设置,以读取jar中的文件?

编辑:还有一个观察结果,如果文件放在WEB-INF / classes下,使用上面的代码创建File可以正常工作。只有当它放在WEB-INF / lib

下的jar中时才会出现问题

3 个答案:

答案 0 :(得分:0)

请注意,ClassLoader.getResource似乎不处理相对路径。 请参阅this

GetResourceAsStream恰好采用相对于ClassLoader的路径(而不是类!!)。我觉得你很幸运,这里也有同样的情况。

答案 1 :(得分:0)

如果是桌面应用程序,getResource()将起作用 但由于这是一个Web应用程序,因此需要从Context中提取资源,因此getResoruceAsStream()

答案 2 :(得分:0)

这不是权限问题,而是使用java.io.File API - 特别是构造函数http://docs.oracle.com/javase/7/docs/api/java/io/File.html#File%28java.lang.String%29

使用

构建File对象时
File xslfile = new File(resourceURL.getPath());

您正在使用需要“抽象路径名”的java.io.File #File(String)方法。什么是可接受/有效的路径名由File类的javadoc描述:http://docs.oracle.com/javase/7/docs/api/java/io/File.html

您从getPath()方法获得的字符串值:

file:/<MY_WEBAPP_LOCATION>/MyApp/WEB-INF/lib/MyComponent.jar!/xml/xslt/master.xsl

根本不构成有效的“抽象路径名” - 它是一个转换为java.lang.String的URL(并且应该使用“jar”而不是“file”的URL方案返回IMHO)。因此呼吁

isExist() 

返回false,因为磁盘上没有带有此类名称的文件。 另一方面,如果资源在jar之外(例如在WEB-INF / classes目录下),resourceURL.getPath()将返回一个呈现有效抽象路径名的值,因为有问题的资源确实是一个简单的文件。

当你使用java.lang.ClassLoader#getResourceAsStream(java.lang.String)时,该方法将资源直接流出到java.lang.InputStream中,甚至可能在其实现中不使用File类。