java / / 2023. 11. 1. 20:06

WatchService와 Apache Commons IO Monitor (파일시스템 변경 감지)

파일시스템 변경을 감지해야 할 경우가 있다. 특정 디렉토리에 파일 변경(추가/삭제/수정)이 발생한 경우를 주기적으로 모니터링 해야 하는 경우이다.

기본적으로 아래의 두 가지 방법이 있다.

  • WatchService 사용
  • Apache Commons IO Monitor 라이브러리 사용

1. WatchService

동작 방식

WatchService를 사용하는 첫 번째 단계는 java.nio.file.FileSystem 인스턴스를 생성하는 것이다.

WatchService watchService = FileSystems.getDefault().newWatchService();

그 다음 모니터링 할 디렉토리 경로를 만들자.

Path path = Paths.get("pathToDir");

이 단계 이후에 StandardWatchEventKindsWatchKey를 경로에 등록해야 한다.

WatchKey watchKey = path.register(
  watchService, StandardWatchEventKinds...);

StandardWatchEventKinds

  • StandardWatchEventKinds.ENTRY_CREATE – 새 파일 생성이나 기존 파일의 이름 변경 등의 변경이 발생할 때
  • StandardWatchEventKinds.ENTRY_MODIFY – 파일 수정이나 파일 속성이 변경될 때
  • StandardWatchEventKinds.ENTRY_DELETE – 파일이 삭제되거나 이동, 이름이 변경될 때
  • StandardWatchEventKinds.OVERFLOW – 이벤트가 없어질 때

예제

public class WatcherServiceSample {

    public static void main(String[] args) throws IOException, InterruptedException {
        WatchService watchService = FileSystems.getDefault().newWatchService();
        Path path = Paths.get("/tmp");

        path.register(
                watchService,
                StandardWatchEventKinds.ENTRY_CREATE,
                StandardWatchEventKinds.ENTRY_DELETE,
                StandardWatchEventKinds.ENTRY_MODIFY);

        WatchKey key;
        while ((key = watchService.take()) != null) {
            for (WatchEvent<?> event : key.pollEvents()) {
                System.out.println("Event kind:" + event.kind() + ". File affected: " + event.context() + ".");
            }
            key.reset();
        }
    }
}

/tmp 디렉토리에 파일 변경을 감지한다. 변경이 있을 경우 로그를 찍게 된다.

실행결과
Event kind:ENTRY_MODIFY. File affected: test2.txt.
Event kind:ENTRY_DELETE. File affected: test.txt.
Event kind:ENTRY_CREATE. File affected: test3.txt.

2. Apache Commons IO Monitor

maven dependencies

<dependency>
    <groupId>commons-io</groupId>
    <artifactId>commons-io</artifactId>
    <version>2.13.0</version>
</dependency>

Apache Commons IO library는 FileAlterationListener 인터페이스에서 파일의 변경이 감지되면 콜백 메소드가 호출된다.

예제

public class CommonsIOMonitorSample {

    private static final int POLL_INTERVAL = 1000;

    public static void main(String[] args) throws Exception {
        FileAlterationObserver observer = new FileAlterationObserver("/tmp");
        FileAlterationMonitor monitor = new FileAlterationMonitor(POLL_INTERVAL);
        FileAlterationListener listener = new FileAlterationListenerAdaptor() {
            @Override
            public void onFileCreate(File file) {
                System.out.println("File created: " + file.getName());
            }

            @Override
            public void onFileDelete(File file) {
                System.out.println("File deleted: " + file.getName());
            }

            @Override
            public void onFileChange(File file) {
                System.out.println("File changed: " + file.getName());
            }
        };
        observer.addListener(listener);
        monitor.addObserver(observer);
        monitor.start();
    }
}

/tmp 디렉토리에 파일 변경을 감지한다. 변경을 감지할 시간은 1초로 설정했다.

변경이 있을 경우 아래의 로그를 찍게 된다.

실행결과
File created: test.txt
File changed: test.txt

3. 비교 (WatchService vs Apache Commons IO Monitor)

WatchService는 운영체제에서 발생하는 파일 시스템 이벤트 변경을 감지한다. 파일 시스템을 반복적으로 폴링하지 않게 한다. 시스템 리소스는 적게 먹지만 변경이 감지되는 시간은 지연이 많다.

반면에 Apache Commons IO Monitor는 파일 시스템 위치를 특정 시간간격으로 listFiles() 메소드를 호출한다. 이러한 방법은 변경사항이 없다면 CPU를 잡아먹는 작업이다. 특정 테스트 용도로 사용하고자 한다면 Interval 시간을 줄이면 변경내역을 바로 확인할 수 있는 장점이 있지만 시스템 리소스를 많이 먹으니 조심해서 사용해야 한다.

참고자료

https://www.baeldung.com/java-nio2-watchservice

https://www.baeldung.com/java-watchservice-vs-apache-commons-io-monitor-library

반응형
  • 네이버 블로그 공유
  • 네이버 밴드 공유
  • 페이스북 공유
  • 카카오스토리 공유