Skip to content

Commit

Permalink
provide additional method instead of changing existing one
Browse files Browse the repository at this point in the history
avoid deeply collecting watchers since they are always collected during time collection

add existence file time info for directories

fix safeTime collection
  • Loading branch information
sokra committed Nov 24, 2021
1 parent 4c9c76f commit a3b2b82
Show file tree
Hide file tree
Showing 4 changed files with 44 additions and 27 deletions.
11 changes: 8 additions & 3 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -112,14 +112,19 @@ const { changes, removals } = wp.getAggregated();
// when futher changes happen
// Can also be used when paused.

// Watchpack.prototype.getTimeInfoEntries()
var fileTimes = wp.getTimeInfoEntries();
// returns a Map with all known time info objects for files and directories
// Watchpack.prototype.collectTimeInfoEntries(fileInfoEntries: Map<string, Entry>, directoryInfoEntries: Map<string, Entry>)
wp.collectTimeInfoEntries(fileInfoEntries, directoryInfoEntries);
// collects time info objects for all known files and directories
// this include info from files not directly watched
// key: absolute path, value: object with { safeTime, timestamp }
// safeTime: a point in time at which it is safe to say all changes happened before that
// timestamp: only for files, the mtime timestamp of the file

// Watchpack.prototype.getTimeInfoEntries()
var fileTimes = wp.getTimeInfoEntries();
// returns a Map with all known time info objects for files and directories
// similar to collectTimeInfoEntries but returns a single map with all entries

// (deprecated)
// Watchpack.prototype.getTimes()
var fileTimes = wp.getTimes();
Expand Down
22 changes: 14 additions & 8 deletions lib/DirectoryWatcher.js
Original file line number Diff line number Diff line change
Expand Up @@ -706,29 +706,34 @@ class DirectoryWatcher extends EventEmitter {
return obj;
}

getTimeInfoEntries(fileTimestamps, directoryTimestamps, safeTime) {
safeTime.value = Math.max(safeTime.value, this.lastWatchEvent);
collectTimeInfoEntries(fileTimestamps, directoryTimestamps) {
let safeTime = this.lastWatchEvent;
for (const [file, entry] of this.files) {
fixupEntryAccuracy(entry);
safeTime.value = Math.max(safeTime.value, entry.safeTime);
safeTime = Math.max(safeTime, entry.safeTime);
fileTimestamps.set(file, entry);
}
if (this.nestedWatching) {
for (const w of this.directories.values()) {
w.directoryWatcher.getTimeInfoEntries(
fileTimestamps,
directoryTimestamps,
safeTime
safeTime = Math.max(
safeTime,
w.directoryWatcher.collectTimeInfoEntries(
fileTimestamps,
directoryTimestamps,
safeTime
)
);
}
fileTimestamps.set(this.path, EXISTANCE_ONLY_TIME_ENTRY);
directoryTimestamps.set(this.path, {
safeTime: safeTime.value
safeTime
});
} else {
for (const dir of this.directories.keys()) {
// No additional info about this directory
directoryTimestamps.set(dir, EXISTANCE_ONLY_TIME_ENTRY);
}
fileTimestamps.set(this.path, EXISTANCE_ONLY_TIME_ENTRY);
directoryTimestamps.set(this.path, EXISTANCE_ONLY_TIME_ENTRY);
}
if (!this.initialScan) {
Expand All @@ -741,6 +746,7 @@ class DirectoryWatcher extends EventEmitter {
}
}
}
return safeTime;
}

close() {
Expand Down
21 changes: 9 additions & 12 deletions lib/watchpack.js
Original file line number Diff line number Diff line change
Expand Up @@ -10,16 +10,13 @@ const EventEmitter = require("events").EventEmitter;
const globToRegExp = require("glob-to-regexp");
const watchEventSource = require("./watchEventSource");

let EXISTANCE_ONLY_TIME_ENTRY; // lazy required

const EMPTY_ARRAY = [];
const EMPTY_OPTIONS = {};

function addWatchersToSet(watchers, set) {
for (const w of watchers) {
if (w !== true && !set.has(w.directoryWatcher)) {
if (!set.has(w.directoryWatcher)) {
set.add(w.directoryWatcher);
addWatchersToSet(w.directoryWatcher.directories.values(), set);
}
}
}
Expand Down Expand Up @@ -275,20 +272,20 @@ class Watchpack extends EventEmitter {
return obj;
}

getTimeInfoEntries(fileTimestamps, directoryTimestamps) {
getTimeInfoEntries() {
const map = new Map();
this.collectTimeInfoEntries(map, map);
return map;
}

collectTimeInfoEntries(fileTimestamps, directoryTimestamps) {
const allWatchers = new Set();
addWatchersToSet(this.fileWatchers.values(), allWatchers);
addWatchersToSet(this.directoryWatchers.values(), allWatchers);
const map = new Map();
// if timestamp maps are passed in, populate them, otherwise return a new map with both file and directory timestamps.
if (!fileTimestamps && !directoryTimestamps) {
fileTimestamps = directoryTimestamps = map;
}
const safeTime = { value: 0 };
for (const w of allWatchers) {
w.getTimeInfoEntries(fileTimestamps, directoryTimestamps, safeTime);
w.collectTimeInfoEntries(fileTimestamps, directoryTimestamps, safeTime);
}
return map;
}

getAggregated() {
Expand Down
17 changes: 13 additions & 4 deletions test/Watchpack.js
Original file line number Diff line number Diff line change
Expand Up @@ -538,22 +538,31 @@ describe("Watchpack", function() {
changeEvents.should.be.eql([path.join(fixtures, "dir", "sub", "a")]);
const files = new Map();
const directories = new Map();
const times = w.getTimeInfoEntries();
w.getTimeInfoEntries(files, directories);
// aggregated results should be the same as seperated maps
Array.from(times).sort().should.be.eql([...Array.from(files), ...Array.from(directories)].sort())
w.collectTimeInfoEntries(files, directories);
const dir = directories.get(path.join(fixtures, "dir"));
const dirAsFile = files.get(path.join(fixtures, "dir"));
const sub = directories.get(path.join(fixtures, "dir", "sub"));
const subAsFile = files.get(path.join(fixtures, "dir", "sub"));
const a = files.get(path.join(fixtures, "dir", "sub", "a"));
dir.should.be.type("object");
dir.should.have.property("safeTime");
dirAsFile.should.be.type("object");
dirAsFile.should.not.have.property("safeTime");
sub.should.be.type("object");
sub.should.have.property("safeTime");
subAsFile.should.be.type("object");
subAsFile.should.not.have.property("safeTime");
a.should.be.type("object");
a.should.have.property("safeTime");
a.should.have.property("timestamp");
sub.safeTime.should.be.aboveOrEqual(a.safeTime);
dir.safeTime.should.be.aboveOrEqual(sub.safeTime);
w.close();
done();
});
testHelper.dir("dir");
testHelper.dir(path.join("dir", "sub"));
testHelper.dir(path.join("dir", "sub2"));
testHelper.tick(function() {
w.watch([], [path.join(fixtures, "dir")]);
testHelper.tick(function() {
Expand Down

0 comments on commit a3b2b82

Please sign in to comment.