今天看到mybatis配置(xml)动态更新,就想到他们如何实现的对文件修改感知,搜了一下。
有两个思路:
1.创建线程,定时扫描,对比上次和本次的扫描结果。类似实现是:Apache common-io的 monitor
2.使用操作系统提供,jdk对其封装的类 WatchService
好了不多说,上代码:
1.common-io 示例 :
jar包maven地址:
<dependency> <groupId>commons-io</groupId> <artifactId>commons-io</artifactId> <version>2.4</version> <type>jar</type> </dependency>
FileAlterationObserver注册要监控的文件根目录,然后向其注册监听器 FileAlterationListener负责事件处理,最后创建FileAlterationMonitor 将Observer注册进来 ,启动monitor线程
import java.io.File; import org.apache.commons.io.monitor.FileAlterationListener; import org.apache.commons.io.monitor.FileAlterationMonitor; import org.apache.commons.io.monitor.FileAlterationObserver; public class FileMonitorTest { public static void main(String[] args) { FileAlterationObserver observer = new FileAlterationObserver("E:/test"); observer.addListener(new FileAlterationListener() { @Override public void onStart(FileAlterationObserver observer) { System.out.println("start..."); } @Override public void onFileCreate(File file) { System.out.println(file.getName() + "文件 create..."); } @Override public void onFileChange(File file) { System.out.println(file.getName() + "文件 change..."); } @Override public void onFileDelete(File file) { System.out.println(file.getName() + "文件 delete..."); } @Override public void onStop(FileAlterationObserver observer) { System.out.println("stop..."); } @Override public void onDirectoryCreate(File dic) { System.out.println(dic.getName() + "文件夹 create..."); } @Override public void onDirectoryChange(File dic) { System.out.println(dic.getName() + "文件夹 create..."); } @Override public void onDirectoryDelete(File dic) { System.out.println(dic.getName() + "文件夹 create..."); } }); FileAlterationMonitor monitor = new FileAlterationMonitor(10000, observer); try { monitor.start(); } catch (Exception e) { e.printStackTrace(); } } }
2.jdk NIO的WatchService
示例
import java.nio.file.FileSystems; import java.nio.file.Path; import java.nio.file.StandardWatchEventKinds; import java.nio.file.WatchEvent; import java.nio.file.WatchKey; import java.nio.file.WatchService; public class WatchFilePathTask implements Runnable{ private String filePath = "E:/test"; private WatchService watchService; @Override public void run() { try{ //获取监控服务 watchService = FileSystems.getDefault().newWatchService(); Path path = FileSystems.getDefault().getPath(filePath); WatchKey key = path.register(watchService, StandardWatchEventKinds.ENTRY_CREATE , StandardWatchEventKinds.ENTRY_MODIFY,StandardWatchEventKinds.OVERFLOW, StandardWatchEventKinds.ENTRY_DELETE); while (true) { key = watchService.take(); for (WatchEvent<?> event : key.pollEvents()) { System.out.print(event.kind()+" : ");//事件类型 System.out.println(event.context());//发生改变的文件 } key.reset(); } } catch (Exception e) { e.printStackTrace(); } } public static void main(String[] args) { new Thread(new WatchFilePathTask()).start(); } }