Получить местоположение файла, созданного с помощью WatchService

Я использую WatchService для просмотра папки и ее подпапок на наличие новых созданных файлов. Однако при создании файла WatchService выдает имя созданного файла, а не его местоположение. Есть ли способ получить абсолютный/относительный путь к созданному файлу.

Грубым способом решения этой проблемы является поиск имени файла во всех подпапках и поиск файла с последней датой создания. Есть лучший способ сделать это?


person user2335580    schedule 03.01.2018    source источник


Ответы (1)


Если вы зарегистрируете каталог WatchService в каталоге dir, получить полный путь будет просто:

// If the filename is "test" and the directory is "foo",
// the resolved name is "test/foo".
Path path = dir.resolve(filename);

Это работает, потому что WatchService отслеживает только один каталог. Если вы хотите отслеживать подпапки, вам необходимо зарегистрировать новый WatchServices.

Ответьте на ваш неформатированный комментарий (это решит вашу проблему)

public static void registerRecursive(Path root,WatchService watchService) throws IOException { 
   WatchServiceWrapper wsWrapper = new WatchServiceWrapper();

   // register all subfolders 
   Files.walkFileTree(root, new SimpleFileVisitor<Path>() { 
      public FileVisitResult preVisitDirectory(Path dir, BasicFileAttributes attrs) throws IOException {
         wsWrapper.register(watchService, dir);
         return FileVisitResult.CONTINUE; 
      } 
   });  

   wsWrapper.processEvents();
}

public class WatchServiceWrapper {
   private final Map<WatchKey,Path> keys;

   public WatchServiceWrapper () {
      keys = new HashMap<>();
   }

   public void register(WatchService watcher, Path dir) throws IOException {
      WatchKey key = dir.register(watcher, StandardWatchEventKinds.ENTRY_CREATE);
      keys.put(key, dir);
   }

   public void processEvents() {
      for (;;) {
        // wait for key to be signalled
        WatchKey key;
        try {
            key = watcher.take();
        } catch (InterruptedException x) {
            return;
        }

        Path dir = keys.get(key);
        if (dir == null) {
            System.err.println("WatchKey not recognized!!");
            continue;
        }

        //get fileName from WatchEvent ev (code emitted)
        Path fileName = ev.context();

        Path fullFilePath = dir.resolve(fileName);

        //do some other stuff
      }
   }
}
person polis    schedule 03.01.2018
comment
Не могли бы вы предоставить пример кода, как отслеживать несколько служб одновременно. Я рекурсивно регистрирую службу наблюдения, используя: attrs) выдает IOException {dir.register(watchService,StandardWatchEventKinds.ENTRY_CREATE); return FileVisitResult.CONTINUE; } }); } - person user2335580; 03.01.2018