最近遇到了一个读取jar资源文件的问题,对于maven项目打包后,项目结构将会改变。打包后,若想读取jar包内文件需要返回流操作,示例如下:
public static InputStream getResourceByName(String name) {
return MyClass.class.getResourceAsStream("/" + name);
}
现实中,经常有用户配置文件是不应该打入jar包中,需要调用jar时,动态从用户的项目中找文件,这时候就要使用如下文件查找算法了,下例代码提取自ansj的分词系统,觉得很好用就提出来了,该代码实现了按深度和优先级关系实现了文件的搜索,正好能满足jar包读取用户配置的问题。
/**
* 从系统各个环境中找文件.或者文件夹
*
*/
public class FileFinder {
private FileFinder(){
}
private static final Logger bltLogger = BltLog.getLogger();
/**
* 系统路径分隔符
*/
private static final String SEPARATOR = System.getProperty("path.separator");
private static final String[] PATHS_PROPERTIES = new String[] { "java.class.path", "java.library.path" };
protected static List<File> fileDir = new ArrayList<>();
static {
fileDir.add(new File("").getAbsoluteFile());
}
/**
* 输入一个文件名或者文件的最后路径寻找文件 default deep Integer.max
*
* @param
* @return
*/
public static File find(String lastPath) {
return find(lastPath, Integer.MAX_VALUE);
}
/**
* 输入一个文件名或者文件的最后路径寻找文件
*
* @param
* @return
*/
public static File find(String lastPath, int deep) {
// 先深度查找
for (File file : fileDir) {
if (file.exists() && file.canRead()) {
file = findByFile(file, lastPath, deep);
if (file != null) {
return file;
}
}
}
// 再从基本几个目录中查找
for (String pathProperties : PATHS_PROPERTIES) {
String[] propertyPath = System.getProperty(pathProperties).split(SEPARATOR);
for (String path : propertyPath) {
File file = new File(path);
try {
if (file.canRead() && file.exists()) {
file = findByFile(file, lastPath, deep);
if (file != null) {
return file;
}
}
} catch (AccessControlException e) {
bltLogger.info(path + " not access to visit");//log日志,可自行修改
}
}
}
return null;
}
/**
* 根据一个文件深度查找
*
* @param file
* @param lastPath
* @param deep integer.max
* @return
*/
public static File findByFile(File file, String lastPath) {
return findByFile(file, lastPath, Integer.MAX_VALUE);
}
/**
* 根据一个文件深度查找
*
* @param file
* @param lastPath
* @param deep
* @return
*/
public static File findByFile(File file, String lastPath, int deep) {
if (deep == 0 || !file.exists() || !file.canRead()) {
return null;
}
if (file.getAbsolutePath().endsWith(lastPath)) {
return file;
}
if (file.isDirectory()) {
File[] listFiles = file.listFiles();
if (listFiles != null && listFiles.length > 0) {
for (File file2 : listFiles) {
File temp = findByFile(file2, lastPath, deep - 1);
if (temp != null) {
return temp;
}
}
}
}
return null;
}
}