Skip to content
This repository has been archived by the owner on Oct 9, 2020. It is now read-only.

Commit

Permalink
builder invalidation API
Browse files Browse the repository at this point in the history
  • Loading branch information
guybedford committed Oct 5, 2015
1 parent 765f8a5 commit c041074
Show file tree
Hide file tree
Showing 2 changed files with 70 additions and 14 deletions.
70 changes: 56 additions & 14 deletions lib/builder.js
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,62 @@ function Builder(baseURL, cfg) {
this.loadConfigSync(cfg, true, !!baseURL);
}

// invalidate the cache for a given module name
// accepts wildcards (*) which are taken to be deep-matching
Builder.prototype.invalidate = function(invalidationModuleName) {
var loader = this.loader;

var invalidated = [];

// invalidation happens in normalized-space
invalidationModuleName = loader.normalizeSync(invalidationModuleName);

// wildcard detection and handling
var invalidationWildcardIndex = invalidationModuleName.indexOf('*');
if (invalidationModuleName.lastIndexOf('*') != invalidationWildcardIndex)
throw new TypeError('Only a single wildcard supported for invalidation.');

if (invalidationWildcardIndex != -1) {
var wildcardLHS = invalidationModuleName.substr(0, invalidationWildcardIndex);
var wildcardRHS = invalidationModuleName.substr(invalidationWildcardIndex + 1);
}

function matchesInvalidation(moduleName) {
if (moduleName == invalidationModuleName)
return true;

if (invalidationWildcardIndex == -1)
return false;

return moduleName.substr(0, invalidationWildcardIndex) == wildcardLHS
&& moduleName.substr(moduleName.length - wildcardRHS.length) == wildcardRHS;
}

// clear the given path from the trace cache
var traceCache = this.cache.trace;
Object.keys(traceCache).forEach(function(canonical) {
var moduleName = loader.normalizeSync(canonical);
if (matchesInvalidation(moduleName)) {
invalidated.push(moduleName);
traceCache[canonical] = undefined;
}
});

// clear the given path from the pluginLoader registry
var pluginLoader = loader.pluginLoader;
Object.keys(pluginLoader._loader.modules).forEach(function(moduleName) {
if (matchesInvalidation(moduleName)) {
invalidated.push(moduleName);
pluginLoader.delete(moduleName);
}
});

// we leave the compile cache in-tact as it is hashed

// return array of invalidated canonicals
return invalidated;
};

Builder.prototype.reset = function(baseLoader) {
baseLoader = baseLoader || this.loader || System;

Expand Down Expand Up @@ -117,20 +173,6 @@ Builder.prototype.reset = function(baseLoader) {
return normalized;
};

// add a local fetch cache to the loader
// useful for plugin duplications of hooks
var fetchCache = {};
var loaderFetch = loader.fetch;
loader.fetch = pluginLoader.fetch = function(load) {
if (fetchCache[load.address])
return fetchCache[load.address];

return Promise.resolve(loaderFetch.call(this, load)).then(function(source) {
fetchCache[load.address] = source;
return source;
});
};

if (this.resetConfig)
executeConfigFile.call(this, false, true, this.resetConfig);

Expand Down
14 changes: 14 additions & 0 deletions test/test-build-cache.js
Original file line number Diff line number Diff line change
Expand Up @@ -76,6 +76,20 @@ suite('Test compiler cache', function() {
return builder.bundle('simple.js').then(function(output) {
expect(output.source).to.contain('fake cache');
});
});

test('Cache invalidation', function() {
var cacheObj = {
trace: {
'simple.js': {},
'another/path.js': {}
}
};

builder.reset();
builder.setCache(cacheObj);

var invalidated = builder.invalidate('*');
assert.deepEqual(invalidated, [System.normalizeSync('simple.js'), System.normalizeSync('another/path.js')]);
});
});

0 comments on commit c041074

Please sign in to comment.