简体   繁体   English

Java 7 NIO WatchService与JPathWatch

[英]Java 7 NIO watchservice vs jpathwatch

The project I'm working has been using Java 6 and jpathwatch (.95) and is now upgrading to Java 7. Currently on Windows 7 and 2008 Server. 我正在工作的项目一直在使用Java 6和jpathwatch(.95),现在正在升级到Java7。目前在Windows 7和2008 Server上。 I'm refactoring areas of code to use the new Java 7 NIO and is relatively straight forward - even using the NIO.2 to replace jpathwatch. 我正在重构代码区域以使用新的Java 7 NIO,并且相对简单-甚至使用NIO.2代替jpathwatch。 However, the file watching area of our code began failing unit tests. 但是,我们代码的文件监视区域开始未通过单元测试。 It seems the Java 7 NIO will not pick up changes in UNC paths to other machines - 看来Java 7 NIO不会接收到其他计算机的UNC路径中的更改-

\\otherMach\path\to\watch.  

To test, I implemented the code from the Java NIO tutorial site http://docs.oracle.com/javase/tutorial/essential/io/fileio.html and then created a duplicate class swapping in the jpathwwatch imports instead of the Java NIO imports. 为了进行测试,我从Java NIO教程站点http://docs.oracle.com/javase/tutorial/essential/io/fileio.html实现了代码,然后在jpathwwatch导入而不是Java NIO中创建了一个重复的类交换。进口。 jpathwatch works for the UNC paths but Java NIO does not. jpathwatch适用于UNC路径,但Java NIO不能。 It seems to register and even returns an initial event key for the location: (sample output) 似乎注册并甚至返回了该位置的初始事件键:(示例输出)

INFO: Watching: \\otherMach\path\to\watch
DEBUG: Added: \\otherMach\path\to\watch
INFO: Got event key: sun.nio.fs.WindowsWatchService$WindowsWatchKey@1f26ecd2
INFO: event key for: \\otherMach\path\to\watch

but then never recognizes any further changes. 但随后再也看不到任何进一步的变化。

jpathwatch registers and reports directory and file events (although it doesn't report the initial event right after registering). jpathwatch注册并报告目录和文件事件(尽管在注册后它不会立即报告初始事件)。

INFO: Watching: \\otherMach\path\to\watch
DEBUG: Added: \\otherMach\path\to\watch
INFO: Got event key: name.pachler.nio.file.impl.WindowsPathWatchService$WatchRecord@79a7bd3b
INFO: event key for: \\otherMach\path\to\watch
INFO: EVENT RECEIVED: ENTRY_CREATE file/dir created - \\otherMach\path\to\watch\New folder
INFO: Got event key: name.pachler.nio.file.impl.WindowsPathWatchService$WatchRecord@79a7bd3b
INFO: event key for: \\otherMach\path\to\watch
INFO: EVENT RECEIVED: ENTRY_CREATE file/dir created - \\otherMach\path\to\watch\New Text Document.txt

This is despite seeing on the jpathwatch discussion that networked watching is NOT supported - note response by Uwe Pachler refering to UNC paths - http://sourceforge.net/p/jpathwatch/discussion/888207/thread/8ea778de/?limit=25#0037 尽管在jpathwatch讨论中看到不支持网络观看,但是-Uwe Pachler的注释响应是指UNC路径-http://sourceforge.net/p/jpathwatch/discussion/888207/thread/8ea778de/?limit =25# 0037

Has anyone had any luck with watching UNC paths and Java 7 NIO.2? 有人在监视UNC路径和Java 7 NIO.2方面有运气吗? Any other or more recent solutions? 还有其他解决方案吗?

Thank you, 谢谢,

-mjash -mjash

It looks like this is a bug in the JDK which was fixed in JDK 1.7.0_u60. 看起来这是一个错误的JDK其固定在JDK 1.7.0_u60。 I just tried u71 (had been using u45) and verified it now works for me across a UNC. 我刚刚尝试过u71(曾经使用过u45),并验证了它现在可以在UNC上对我有效。

If you are using the tutorial and examples from the Oracle documentation on WatchEvent, you might have missed calling key.reset() after handing the event. 如果您在WatchEvent上使用Oracle文档中的教程和示例,则可能在处理事件后错过了调用key.reset()的操作。 I just ran into the same issue: 我只是遇到了同样的问题:

    void processEvent(){
    for(;;){
        WatchKey key;           
        try {
            key = this.watcher.take();
        } catch (InterruptedException ex){
            return;
        }

        for(WatchEvent<?> event: key.pollEvents()){
            WatchEvent<Path> newevent = (WatchEvent<Path>)event;
            Path filepath = newevent.context();

        ... clipped ....
        }

        boolean valid = key.reset();
        if(!valid){
            break;
        }
    }

Though there's no really clear description about UNC Paths and remote file-systems in general, here is what I found out: 尽管总体上没有关于UNC路径和远程文件系统的真正清晰的描述,但我发现的是:

At first it seems to be possible to register a WatchKey, but immediately the WatchKey invalidates ( WatchKey.isValid() ). 起初似乎可以注册一个WatchKey,但是WatchKey立即失效( WatchKey.isValid() )。

Due to the straight connection to the FileSystem it's not possible to register a WatchKey to a remote location. 由于与FileSystem的直接连接,因此无法将WatchKey注册到远程位置。

Possible workarounds: 可能的解决方法:

1. Remote FileWatcher 1.远程FileWatcher

Share a list of paths to watch to a remote jvm and let it forward the changes to your machine. 共享路径列表以监视远程jvm,并将其转发给您的计算机。

2. Polling 2.轮询

The other workaround would be a poller (only recomendable if not time-critical). 另一个解决方法是使用轮询程序(仅在非时间紧迫的情况下才可推荐)。
If you'd poll constantly, this would cause a lot of network-traffic. 如果您不停地轮询,这将导致大量的网络流量。

Would be nice to either get an Exception when registering to a remote Path or at leaset read that in the When to Use and Not Use This API section. 最好是在注册到远程路径时获得异常,或者至少在“ When to Use and Not Use This API部分中读取该异常。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM