public class PollingWatchService extends Object implements PathWatchService
PathWatchService
that polls for changes.
Example:
PathWatchService s = new PollingWatchService(4, 15, TimeUnit.SECONDS); s.register(FileSystems.getDefault().getPath("/home/luke"), StandardWatchEventKinds.ENTRY_CREATE, StandardWatchEventKinds.ENTRY_DELETE, StandardWatchEventKinds.ENTRY_MODIFY); s.start(); for (;;) { WatchKey k = s.take(); ... }
Note: polling is only safe when operating on secure directories (i.e. ones in which there is no risk of a file system attack by a malicious user). If operating on an insecure directory, an attacker may be able to trick this service into reporting file system changes of their choosing (e.g. an ENTRY_CREATE event for a file with a name and path of the attacker's choosing).
According to the CERT Secure Coding website, rule FIO00-J. Do not
operate on files in shared directories (accessed on July 1, 2014):
A directory is secure with respect to a particular user if only the user
and the system administrator are allowed to create, move, or delete files
inside the directory. Furthermore, each parent directory must itself be a
secure directory up to and including the root directory. On most systems,
home or user directories are secure by default and only shared directories
are insecure.
Constructor and Description |
---|
PollingWatchService(int threadPoolSize,
long period,
TimeUnit unit)
Constructs a new service with the specified thread pool size, period, and
time unit, and with a default exception handler that invokes the
exception's
printStackTrace() method and a default information
handler that does nothing. |
PollingWatchService(int threadPoolSize,
long period,
TimeUnit unit,
PollingWatchServiceExceptionHandler handler,
PollingWatchServiceInfoHandler infoHandler)
Constructs a new service with the specified thread pool size, period, time
unit, exception handler, and information handler.
|
Modifier and Type | Method and Description |
---|---|
void |
close()
Closes this watch service.
|
WatchKey |
poll()
Retrieves and removes the next watch key, or
null if none are
present. |
WatchKey |
poll(long timeout,
TimeUnit unit)
Retrieves and removes the next watch key, waiting if necessary up to the
specified wait time if none are yet present.
|
WatchKey |
register(Path dir,
WatchEvent.Kind<?>... kinds)
Registers the specified directory, using the specified
WatchEvent
kinds and no WatchEvent modifiers, with this watch service. |
WatchKey |
register(Path dir,
WatchEvent.Kind<?>[] kinds,
WatchEvent.Modifier... modifiers)
Registers the specified directory, using the specified
WatchEvent
kinds and modifiers, with this watch service. |
void |
start()
Starts this service.
|
WatchKey |
take()
Retrieves and removes next watch key, waiting if none are yet present.
|
boolean |
useFileMetadata()
Answers whether this service is configured to use file metadata.
|
void |
useFileMetadata(boolean useFileMetadata)
Configures this service to use file metadata or not.
|
public PollingWatchService(int threadPoolSize, long period, TimeUnit unit)
printStackTrace()
method and a default information
handler that does nothing.threadPoolSize
- size of thread pool used for polling file system for
changesperiod
- interval of time between each pollunit
- time unit of period
public PollingWatchService(int threadPoolSize, long period, TimeUnit unit, PollingWatchServiceExceptionHandler handler, PollingWatchServiceInfoHandler infoHandler)
threadPoolSize
- size of thread pool used for polling file system for
changesperiod
- interval of time between each pollunit
- time unit of period
handler
- exception handler to handle exceptions thrown in this
service; if null
, a default handler will be used that
invokes the exception's printStackTrace()
methodinfoHandler
- information handler to handle information published by
this service; if null
, a default handler will be used
that does nothingpublic boolean useFileMetadata()
true
.true
if this service is configured to use file metadata;
false
otherwiseuseFileMetadata(boolean)
public void useFileMetadata(boolean useFileMetadata)
When using file metadata, this service will read metadata (i.e.
BasicFileAttributes
) for all files in directories being monitored
when polling for changes, and it will use the metadata to determine which
events need to be signaled. When not using file metadata, the files in
directories being monitored will be listed when polling for changes, but
the metadata for those files will not be read. The ENTRY_CREATE
,
ENTRY_DELETE
, and OVERFLOW
watch event kinds may be
signaled, but the ENTRY_MODIFY
event kind will never be signaled
because the metadata that would enable the detection of a modification is
not read.
On some file systems, reading file metadata may be expensive. Configuring
this service to not use file metadata provides a way to not incur the cost
of reading file metadata when polling for changes, but gives up the
ENTRY_MODIFY
event kind. A consumer of the events produced by this
service when configured to not use file metadata would be able to detect
file creation and deletion, but would not, for example, be able to detect
that a file was modified.
If this method is to be invoked, it must be invoked before any paths are
registered via the register
methods of this service and before
this service is started.
useFileMetadata
- true
to use file metadata when determining
which events to signal; false
to notIllegalStateException
- if a register
method has already
been invoked or this service has already been starteduseFileMetadata()
public void start()
PathWatchService
start
in interface PathWatchService
ClosedWatchServiceException
- if closedIllegalStateException
- if already startedpublic void close()
java.nio.file.WatchService
If a thread is currently blocked in the take
or poll
methods waiting for a key to be queued then
it immediately receives a ClosedWatchServiceException
. Any
valid keys associated with this watch service are invalidated
.
After a watch service is closed, any further attempt to invoke
operations upon it will throw ClosedWatchServiceException
.
If this watch service is already closed then invoking this method
has no effect.
close
in interface Closeable
close
in interface AutoCloseable
close
in interface WatchService
public WatchKey poll()
java.nio.file.WatchService
null
if none are
present.poll
in interface WatchService
null
ClosedWatchServiceException
public WatchKey poll(long timeout, TimeUnit unit) throws InterruptedException
java.nio.file.WatchService
poll
in interface WatchService
timeout
- how to wait before giving up, in units of unitunit
- a TimeUnit
determining how to interpret the timeout
parameternull
ClosedWatchServiceException
InterruptedException
- if interrupted while waitingpublic WatchKey take() throws InterruptedException
java.nio.file.WatchService
take
in interface WatchService
ClosedWatchServiceException
InterruptedException
- if interrupted while waitingpublic WatchKey register(Path dir, WatchEvent.Kind<?>... kinds) throws IOException
PathWatchService
WatchEvent
kinds and no WatchEvent
modifiers, with this watch service.
This method is intended to be similar in behavior to
Path.register(WatchService, WatchEvent.Kind[])
.
register
in interface PathWatchService
dir
- directory to watch; must not be a symbolic linkkinds
- events to register forClosedWatchServiceException
- if this watch service is closedNotDirectoryException
- if dir
is not a directoryIOException
- if an I/O error occurspublic WatchKey register(Path dir, WatchEvent.Kind<?>[] kinds, WatchEvent.Modifier... modifiers) throws IOException
PathWatchService
WatchEvent
kinds and modifiers, with this watch service.
This method is intended to be similar in behavior to
Path.register(WatchService, WatchEvent.Kind[], WatchEvent.Modifier[])
.
register
in interface PathWatchService
dir
- directory to watch; must not be a symbolic linkkinds
- events to register formodifiers
- modifiers modifying how dir
is registeredClosedWatchServiceException
- if this watch service is closedNotDirectoryException
- if dir
is not a directoryIOException
- if an I/O error occurs