in src/main/java/org/apache/commons/io/input/Tailer.java [944:1031]
public void run() {
RandomAccessResourceBridge reader = null;
try {
FileTime last = FileTimes.EPOCH; // The last time the file was checked for changes
long position = 0; // position within the file
// Open the file
while (getRun() && reader == null) {
try {
reader = tailable.getRandomAccess(RAF_READ_ONLY_MODE);
} catch (final FileNotFoundException e) {
listener.fileNotFound();
}
if (reader == null) {
ThreadUtils.sleep(delayDuration);
} else {
// The current position in the file
position = tailAtEnd ? tailable.size() : 0;
last = tailable.lastModifiedFileTime();
reader.seek(position);
}
}
while (getRun()) {
final boolean newer = tailable.isNewer(last); // IO-279, must be done first
// Check the file length to see if it was rotated
final long length = tailable.size();
if (length < position) {
// File was rotated
listener.fileRotated();
// Reopen the reader after rotation ensuring that the old file is closed iff we re-open it
// successfully
try (RandomAccessResourceBridge save = reader) {
reader = tailable.getRandomAccess(RAF_READ_ONLY_MODE);
// At this point, we're sure that the old file is rotated
// Finish scanning the old file and then we'll start with the new one
try {
readLines(save);
} catch (final IOException ioe) {
listener.handle(ioe);
}
position = 0;
} catch (final FileNotFoundException e) {
// in this case we continue to use the previous reader and position values
listener.fileNotFound();
ThreadUtils.sleep(delayDuration);
}
continue;
}
// File was not rotated
// See if the file needs to be read again
if (length > position) {
// The file has more content than it did last time
position = readLines(reader);
last = tailable.lastModifiedFileTime();
} else if (newer) {
/*
* This can happen if the file is truncated or overwritten with the exact same length of information. In cases like
* this, the file position needs to be reset
*/
position = 0;
reader.seek(position); // cannot be null here
// Now we can read new lines
position = readLines(reader);
last = tailable.lastModifiedFileTime();
}
if (reOpen && reader != null) {
reader.close();
}
ThreadUtils.sleep(delayDuration);
if (getRun() && reOpen) {
reader = tailable.getRandomAccess(RAF_READ_ONLY_MODE);
reader.seek(position);
}
}
} catch (final InterruptedException e) {
Thread.currentThread().interrupt();
listener.handle(e);
} catch (final Exception e) {
listener.handle(e);
} finally {
try {
IOUtils.close(reader);
} catch (final IOException e) {
listener.handle(e);
}
close();
}
}