Search code examples
javawatchservice

Java monitoring multiple folders


I need to monitor multiple folder and I want to khow which folder has received an event to execute a particular treatment. I've tried this code.

WatchService watchService = FileSystems.getDefault().newWatchService();
opexFolder.register(watchService, StandardWatchEventKinds.ENTRY_CREATE);
docupostFolder.register(watchService, StandardWatchEventKinds.ENTRY_CREATE);

    boolean valid = true;
    do {
        WatchKey watchKey = watchService.take();
        for (WatchEvent<?> event : watchKey.pollEvents()) {
            WatchEvent.Kind kind = event.kind();                
            if (StandardWatchEventKinds.ENTRY_CREATE.equals(event.kind())) {                    
                String fileName = event.context().toString();                   

                //here I want to khow the path of the folder that has 
                // received the ENTRY event 
               String pathToExplore = ??;
              if (pathToExplore has some value) {
                treatments;
              } else {
                other treatments;
                }

            }
        }
        valid = watchKey.reset();

    } while (valid);
}

Is it possible to do that, or I must to create watchService per folder.

Thanks.


Solution

  • WatchService.take() will return a different watch key for every watched dir. And you can get the watched dir from the WatchKey::watchable() method.

    So by inspecting the returned value of WatchKey::watchable() you'll know for which directory is this event.


    Is the WatchKey usualy constant?

    No. The WatchKey is not a constant. You acquire it by calling WatchKey watchKey = watchService.take(); You've already done it in the code you've posted.

    How can I say this is opexFolder's key or docupostFolder's key

    Just call Path directory = WatchKey::watchable()

    Here is a simple example application:

    import java.io.IOException;
    import java.nio.file.*;
    import java.nio.file.attribute.BasicFileAttributes;
    
    public final class WatchServiceExample {
    
        public static void main(String[] args) throws Exception {
            //We'll use this watch service to monitor all directories we are interested in
            final WatchService watchService = FileSystems.getDefault().newWatchService();
    
            //We'll use this directory for the test in order not to create junk in the system
            final Path tempDirectory = Files.createTempDirectory("watch-service-example");
            System.out.println("Created temporary directory: " + tempDirectory.toAbsolutePath());
    
            for (int i = 0; i < 10; i++) {
                final Path watchedDir = Files.createDirectory(tempDirectory.resolve("watched_" + i));
                System.out.println("Created watched directory: " + watchedDir.toAbsolutePath());
                watchedDir.register(watchService, StandardWatchEventKinds.ENTRY_CREATE);
            }
    
            System.out.println("Initialization complete. When you create an entry in the watch dirs you'll be notified.");
            while (true) {
                final WatchKey watchKey = watchService.take();
                final Watchable watchable = watchKey.watchable();
    
                //Since we are registering only paths in teh watch service, the watchables must be paths
                if (!(watchable instanceof Path)) {
                    throw new AssertionError("The watchable should have been a Path");
                }
    
                final Path directory = (Path) watchable;
                System.out.println("Processing events for watched directory: " + directory);
    
                for (WatchEvent<?> event : watchKey.pollEvents()) {
                    System.out.println("Received event '"
                      + event.kind()
                      + "' for entry '"
                      + event.context()
                      + "' in watched directory '"
                      + directory + "'"
                    );
                }
    
                if (!watchKey.reset()) {
                    System.out.println("Failed to reset watch key: will not process more events");
                    break;
                }
            }
    
            //Lets clean up after ourselves
            Files.walkFileTree(tempDirectory, new SimpleFileVisitor<Path>() {
                @Override
                public FileVisitResult visitFile(Path file, BasicFileAttributes attrs) throws IOException {
                    Files.delete(file);
                    return FileVisitResult.CONTINUE;
                }
    
                @Override
                public FileVisitResult postVisitDirectory(Path dir, IOException exc) throws IOException {
                    Files.delete(dir);
                    return FileVisitResult.CONTINUE;
                }
            });
        }
    }
    

    Output from the sample application:

    Created temporary directory: /tmp/watch-service-example4292865635932187600
    Created watched directory: /tmp/watch-service-example4292865635932187600/watched_0
    Created watched directory: /tmp/watch-service-example4292865635932187600/watched_1
    Created watched directory: /tmp/watch-service-example4292865635932187600/watched_2
    Created watched directory: /tmp/watch-service-example4292865635932187600/watched_3
    Created watched directory: /tmp/watch-service-example4292865635932187600/watched_4
    Created watched directory: /tmp/watch-service-example4292865635932187600/watched_5
    Created watched directory: /tmp/watch-service-example4292865635932187600/watched_6
    Created watched directory: /tmp/watch-service-example4292865635932187600/watched_7
    Created watched directory: /tmp/watch-service-example4292865635932187600/watched_8
    Created watched directory: /tmp/watch-service-example4292865635932187600/watched_9
    Initialization complete. When you create an entry in the watch dirs you'll be notified.
    Processing events for watched directory: /tmp/watch-service-example4292865635932187600/watched_5
    Received event 'ENTRY_CREATE' for entry 'test' in watched directory '/tmp/watch-service-example4292865635932187600/watched_5'
    Processing events for watched directory: /tmp/watch-service-example4292865635932187600/watched_8
    Received event 'ENTRY_CREATE' for entry 'test' in watched directory '/tmp/watch-service-example4292865635932187600/watched_8'