Java文件读取 jar包内文件读取
2016-11-16 17:33
801 查看
最近遇到一些Jar包内外配置文件读取的问题。索性自己测试总结一下,与大家分享。
主要是关于ClassLoader.getResource和Class.getResource方法路径区别的问题。
特别说明:</span>用URI/URL的方式构造路径是个人比较推荐的,可以解决一些路径读取的问题。例如:Spring会对URI/URL格式的路径进行专有处理可以准确定位的位置,而直接使用绝对路径,在用Classpath和FileSystem两种不同的初始化方式下,可能会出现错误。
对于不在ClassPath下的Jar包的读取,当作一个本地文件用JarFile读取即可。路径可使用绝对路径。或者用上面的url.getConnection也可以处理。这里不再实现。 希望对你有所帮助。
主要是关于ClassLoader.getResource和Class.getResource方法路径区别的问题。
1. 绝对路径文件读取,最简单,最直接的方式
/** * 从绝对路径读取文件,最基本的文件读取方式 * * @author lihzh * @data 2012-4-11 下午9:33:44 */ @Test public void testGetFileFromAbsolutePath() { String dirPathNotUnderClasspath = "D:\\workspace-home\\JavaDemo\\conf"; File dirFile = new File(dirPathNotUnderClasspath); AssertDirFile(dirFile); } /** * 对文件夹类型文件的断言 * * @param dirFile * @author lihzh * @data 2012-4-11 下午9:49:14 */ private void AssertDirFile(File dirFile) { // 文件存在 Assert.assertTrue(dirFile.exists()); // 是绝对路径 Assert.assertTrue(dirFile.isAbsolute()); // 是个文件夹 Assert.assertTrue(dirFile.isDirectory()); // 获取文件夹下所有文件 File[] files = dirFile.listFiles(); // 下面有文件 Assert.assertNotNull(files); // 且只有一个 Assert.assertEquals(1, files.length); // 文件名匹配 Assert.assertEquals("test.properties", files[0].getName()); }
2. 相对于执行编译命令路径的方式读取
/** * 从相对路径读取文件,相对于编译路径,在Eclipse中即为工程所在根目录。 本质还是绝对路径读取。 * * @author lihzh * @data 2012-4-11 下午9:51:10 */ @Test public void testGetFileFromRelativePath() { String dirPath = System.getProperty("user.dir") + "\\conf"; File dirFile = new File(dirPath); AssertDirFile(dirFile); }
3. 用URI构造本地文件读取
/** * 构造URI/URL格式的文件路径,读取本地文件 * * @author lihzh * @throws URISyntaxException * @throws MalformedURLException * @data 2012-4-11 下午10:25:00 */ @Test public void testGetFileFromURIPath() throws URISyntaxException, MalformedURLException { // 直接用URI构造, 由于URI和URL可以互转,所以如果为URL直接用URL.toURI转换成URI即可 URI uri = new URI("file:/D:/workspace-home/JavaDemo/conf/"); File dirFile = new File(uri); AssertDirFile(dirFile); }
特别说明:</span>用URI/URL的方式构造路径是个人比较推荐的,可以解决一些路径读取的问题。例如:Spring会对URI/URL格式的路径进行专有处理可以准确定位的位置,而直接使用绝对路径,在用Classpath和FileSystem两种不同的初始化方式下,可能会出现错误。
4. 利用ClassLoader读取Jar包内部文件
/** * 从依赖的Jar包中读取文件, Jar包内的文件是无法用File读取的,只能用Stream的方式读取。 * * @author lihzh * @throws URISyntaxException * @throws IOException * @data 2012-4-11 下午11:07:58 */ @Test public void testGetFileFromJarInClassPath() throws URISyntaxException, IOException { Enumeration<URL> urls = this.getClass().getClassLoader().getResources("conf/test.properties"); URL url = this.getClass().getClassLoader().getResource("conf/test.properties"); Assert.assertTrue(urls.hasMoreElements()); Assert.assertNotNull(url); // 注意两种不同调用方式的路径的区别,此处如果不以'/' 开头,会被当作相对于当前类所在的包类处理,自然无法找到。 // 因为在Class的getResource方法的开头,有一个resolveName方法,处理了传入的路径格式问题。而ClassLoader类里的 // getResource和getResources均无此处理。使用时候需要用心。 URL clzURL = this.getClass().getResource("/conf/test.properties"); URL nullURL = this.getClass().getResource("conf/test.properties"); Assert.assertNotNull(clzURL); Assert.assertNull(nullURL); URL thisClzURL = this.getClass().getResource(""); Assert.assertNotNull(thisClzURL); // 开始读取文件内容 InputStream is = this.getClass().getResourceAsStream("/conf/test.properties"); Properties props = new Properties(); props.load(is); Assert.assertTrue(props.containsKey("test.key")); Assert.assertEquals("thisIsValue", props.getProperty("test.key")); }
5. 读取Jar内某路径下的所有文件
/** * 从ClassPath中的Jar包读取某文件夹下的所有文件 * * @author lihzh * @throws IOException * @data 2012-4-13 下午10:22:24 */ @Test public void testGetFilesFromJarInClassPathWithDirPath() throws IOException { String dirPath = "conf/"; URL url = this.getClass().getClassLoader().getResource(dirPath); Assert.assertNotNull(url); String urlStr = url.toString(); // 找到!/ 截断之前的字符串 String jarPath = urlStr.substring(0, urlStr.indexOf("!/") + 2); URL jarURL = new URL(jarPath); JarURLConnection jarCon = (JarURLConnection) jarURL.openConnection(); JarFile jarFile = jarCon.getJarFile(); Enumeration<JarEntry> jarEntrys = jarFile.entries(); Assert.assertTrue(jarEntrys.hasMoreElements()); Properties props = new Properties(); while (jarEntrys.hasMoreElements()) { JarEntry entry = jarEntrys.nextElement(); // 简单的判断路径,如果想做到像Spring,Ant-Style格式的路径匹配需要用到正则。 String name = entry.getName(); if (name.startsWith(dirPath) && !entry.isDirectory()) { // 开始读取文件内容 InputStream is = this.getClass().getClassLoader().getResourceAsStream(name); Assert.assertNotNull(is); props.load(is); } } Assert.assertTrue(props.containsKey("test.key")); Assert.assertEquals("thisIsValue", props.getProperty("test.key")); Assert.assertTrue(props.containsKey("test.key.two")); Assert.assertEquals("thisIsAnotherValue", props.getProperty("test.key.two")); }
对于不在ClassPath下的Jar包的读取,当作一个本地文件用JarFile读取即可。路径可使用绝对路径。或者用上面的url.getConnection也可以处理。这里不再实现。 希望对你有所帮助。
相关文章推荐
- java读取jar中指定的文件
- core java ziptest 第12章如何从zip文件或者jar文件中读取数据
- java 从jar中读取文件 三种方法<Enumeration>
- java 从jar包中读取资源文件
- Java用jdom.jar解析读取XML文件信息
- 从 Java 档案 (JAR) 中读取文件
- 从Java的jar文件中读取数据
- web工程中jar读取 配置的文件,java工程中jar 读取配置的文件方式
- java 解析jar 文件,读取并进行调用
- java 从jar包中读取资源文件
- java.util.jar 读取文件
- java 从jar包中读取资源文件
- 从 Java 档案 (JAR) 中读取文件
- java读取jar包内的文件
- 随心所欲学Java,文件读取问题研究,Jar包内文件读取 推荐
- 从 Java 档案 (JAR) 中读取文件
- 从 Java 档案(JAR) 中读取文件
- java 从jar包中读取资源文件
- java读取和写入jar包外的properties文件
- Java读取Jar中资源文件