I would like to run a JS function when a specific section of a file changes. The contents that are being watched should be selected by Regex.
As far as I have seen, libraries like Chokidar can only detect changes to a file directly and do not provide information about the contents of the file before and after the changes.
I ended up creating a slightly adjusted version of Prashant Pokhriyal's answer.
const fs = require('fs');
const chokidar = require('chokidar');
const watchForFileContentChanges = (path, regex, callback) => {
const regexFileContents = new Map();
const registerFileContentMatches = (filePath) => {
const currentFileContent = fs.readFileSync(filePath, 'utf8');
const currentFileMatches = currentFileContent.match(regex);
if (currentFileMatches === null) return;
regexFileContents.set(filePath, currentFileMatches);
}
const handleContentChanges = (filePath) => {
const previousFileMatches = regexFileContents.get(filePath);
const hasFileBeenReadBefore = previousFileMatches !== undefined;
const currentFileContent = fs.readFileSync(filePath, 'utf8');
const currentFileMatches = currentFileContent.match(regex);
if (hasFileBeenReadBefore === false) {
regexFileContents.set(filePath, currentFileMatches);
if (currentFileMatches === null) return;
callback();
return;
}
const haveFileMatchesChanged = JSON.stringify(previousFileMatches) !== JSON.stringify(currentFileMatches);
if (haveFileMatchesChanged === false) return;
regexFileContents.set(filePath, currentFileMatches);
callback();
}
const handleFileRemoval = (filePath) => {
regexFileContents.delete(filePath);
}
chokidar.watch(path)
.on('add', registerFileContentMatches)
.on('change', handleContentChanges)
.on('unlink', handleFileRemoval);
}
watchForFileContentChanges('output/*.txt', /foo/g, () => {
console.log('foo changed');
});