Skip to content
This repository has been archived by the owner on Jun 15, 2023. It is now read-only.

Commit

Permalink
Refactor file list with async.
Browse files Browse the repository at this point in the history
  • Loading branch information
paulmillr committed Nov 13, 2019
1 parent 06c16a6 commit 6f7527f
Show file tree
Hide file tree
Showing 4 changed files with 54 additions and 59 deletions.
93 changes: 44 additions & 49 deletions lib/fs_utils/file_list.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,13 +2,12 @@
const debug = require('debug')('brunch:list');
const EventEmitter = require('events');
const readAndCache = require('fcache').updateCache;
const formatError = require('../utils/helpers').formatError;
const FrozenMap = require('../utils/helpers').FrozenMap;
const FrozenSet = require('../utils/helpers').FrozenSet;
const {formatError, FrozenMap, FrozenSet} = require('../utils/helpers');
const Asset = require('./asset');
const SourceFile = require('./source_file');
const BrunchError = require('../utils/error');
const anymatch = require('anymatch');
const deppack = require('deppack');

// A list of `fs_utils.SourceFile` or `fs_utils.Asset` that contains *all* file
// from Brunches app with some additional methods used to simplify file reading / removing.
Expand All @@ -34,10 +33,12 @@ class FileList extends EventEmitter {
this.compiling = new Set();
this.compiled = new Set();

this.timer = null;
this.timer = undefined;
this.initial = true;
this.disposed = false;

this._exploreDeps = deppack.exploreDeps(this);

this.on('change', this._change);
this.on('unlink', this._unlink);

Expand All @@ -57,18 +58,16 @@ class FileList extends EventEmitter {
return !!(this.reading.size || this.compiling.size);
}

copiedAfter(time) {
return Array.from(this.assets.values()).filter(asset => {
return asset.copyTime > time;
});
getAssetsCopiedAfter(time) {
return Array.from(this.assets.values()).filter(asset => asset.copyTime > time);
}

removeDisposedFiles() {
cleanDisposedFiles() {
this.files.forEach((file, path) => file.disposed && this.files.delete(path));
this.assets.forEach((file, path) => file.disposed && this.assets.delete(path));
}

compile(file) {
async _compile(file) {
const path = file.path;
file.removed = false;
if (this.compiling.has(path)) {
Expand All @@ -77,16 +76,17 @@ class FileList extends EventEmitter {
}

this.compiling.add(path);
file.compile().finally(() => {
try {
await file.compile();
} finally {
this.compiling.delete(path);
this._resetTimer();
}).then(() => {
debug(`Compiled ${path}`);
this.compiled.add(path);
});
}
debug(`Compiled ${path}`);
this.compiled.add(path);
}

compileDependencyParents(path) {
_compileDependencyParents(path) {
const isAsset = this.conventions.assets(path);
const files = isAsset ? this.assets : this.files;
const paths = [];
Expand All @@ -102,60 +102,53 @@ class FileList extends EventEmitter {

if (!parents.length) return;
debug(`Compiling ${isAsset ? 'asset' : 'dependency'} ${path} parent(s): ${paths.join(', ')}`);
parents.forEach(file => this.compile(file));
}

_addAsset(path) {
const file = new Asset(path, this.publicPath, this.conventions.assets);
this.assets.set(file.path, file);
return file;
parents.forEach(file => this._compile(file));
}

_addFile(path) {
const file = new SourceFile(path, this.conventions.vendor, this.moduleWrapper, this);
this.files.set(file.path, file);
_get(path, addOnMiss = true) {
const isAsset = this.conventions.assets(path);
const files = isAsset ? this.assets : this.files;
let file = files.get(path);
if (file) return file;
if (!addOnMiss) return;

file = isAsset ?
new Asset(path, this.publicPath, this.conventions.assets) :
new SourceFile(path, this.conventions.vendor, this.moduleWrapper, this._exploreDeps);
files.set(file.path, file);
return file;
}

_change(path) {
if (this.disposed) return;
if (this.reading.has(path)) return;
async _change(path) {
if (this.disposed || this.reading.has(path)) return;

debug(`Reading ${path}`);
const readDate = Date.now();
this.reading.set(path, readDate);

readAndCache(path).then(() => {
try {
await readAndCache(path);
const cachedDate = this.reading.get(path);
if (this.disposed || !cachedDate || cachedDate > readDate) return;
this.reading.delete(path);

const isIgnored = this.conventions.ignored(path);
if (!isIgnored) {
const isAsset = this.conventions.assets(path);
const file = isAsset ?
this.assets.get(path) || this._addAsset(path) :
this.files.get(path) || this._addFile(path);

this.compile(file);
if (!this.conventions.ignored(path)) {
this._compile(this._get(path));
}

if (!this.initial) this.compileDependencyParents(path);
if (!this.initial) this._compileDependencyParents(path);
this._resetTimer();
}, error => {
} catch (error) {
if (!this.disposed) {
throw new BrunchError('READ_FAILED', {path, error});
}
});
};
}

_unlink(path) {
const isIgnored = this.conventions.ignored(path);
if (isIgnored) {
this.compileDependencyParents(path);
if (this.conventions.ignored(path)) {
this._compileDependencyParents(path);
} else {
const isAsset = this.conventions.assets(path);
const file = isAsset ? this.assets.get(path) : this.files.get(path);
const file = this._get(path, false);
if (file && !file.disposed) file.removed = true;
}
this._resetTimer();
Expand All @@ -164,12 +157,14 @@ class FileList extends EventEmitter {
_resetTimer() {
if (this.timer) clearTimeout(this.timer);
this.timer = setTimeout(() => {
this.removeDisposedFiles();
this.cleanDisposedFiles();
if (this.hasPendingFiles) {
// loop
this._resetTimer();
} else {
this.emit('ready');
this.compiled.clear();
// TODO: serialize fileList and write
this.emit('ready');
}
}, this.resetTime);
}
Expand Down
11 changes: 5 additions & 6 deletions lib/fs_utils/source_file.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,12 +2,11 @@
const debug = require('debug')('brunch:file');
const readFromCache = require('fcache').readFile;
const logger = require('loggy');
const deppack = require('deppack');
const {processFile} = require('./pipeline');
const SourceMapConsumer = require('source-map').SourceMapConsumer;
const SourceNode = require('source-map').SourceNode;
const {SourceMapConsumer, SourceNode} = require('source-map');
const BrunchError = require('../utils/error');
const helpers = require('../utils/plugins').helpers;
const {helpers} = require('../utils/plugins');
const deppack = require('deppack');

const identityNode = (code, path) => {
const lines = code.split('\n').map((line, index) => {
Expand Down Expand Up @@ -47,12 +46,12 @@ const getInitialType = path => {
};

class SourceFile {
constructor(path, vendorConvention, moduleWrapper, fileList) {
constructor(path, vendorConvention, moduleWrapper, exploreDeps) {
debug(`Init file ${path}`);

this.isVendor = vendorConvention(path);
this._moduleWrapper = moduleWrapper;
this._exploreDeps = deppack.exploreDeps(fileList);
this._exploreDeps = exploreDeps;

this._realPath = this.path = path;
this.source = '';
Expand Down
5 changes: 3 additions & 2 deletions lib/utils/helpers.js
Original file line number Diff line number Diff line change
@@ -1,8 +1,9 @@
'use strict';
const basename = require('universal-path').basename;
const {promisify} = require('util');
const fslstat = promisify(require('fs').lstat);
const fsaccess = promisify(require('fs').access);
const fs = require('fs');
const fslstat = promisify(fs.lstat);
const fsaccess = promisify(fs.access);

// Single-level flatten.
const flatten = arrays => [].concat(...arrays);
Expand Down
4 changes: 2 additions & 2 deletions lib/watch.js
Original file line number Diff line number Diff line change
Expand Up @@ -287,9 +287,9 @@ class BrunchWatcher {
write(fileList, config, joinConfig, optimizers, startTime).then(data => {
const generatedFiles = data.changed;
const disposed = data.disposed;
fileList.removeDisposedFiles();
fileList.cleanDisposedFiles();
this._endBundle();
const assets = fileList.copiedAfter(startTime);
const assets = fileList.getAssetsCopiedAfter(startTime);
logger.info(helpers.generateCompilationLog(
startTime, assets, generatedFiles, disposed
));
Expand Down

0 comments on commit 6f7527f

Please sign in to comment.