123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145 |
- const pluginCompat = require('./util/plugin-compat');
- const relateContext = require('./util/relate-context');
- const { parityCacheFromCache, pushParityWriteOps } = require('./util/parity');
- const relateNormalPath = relateContext.relateNormalPath;
- function relateNormalRequest(compiler, key) {
- return key
- .split('!')
- .map(subkey => relateNormalPath(compiler, subkey))
- .join('!');
- }
- function relateNormalModuleId(compiler, id) {
- return id.substring(0, 24) + relateNormalRequest(compiler, id.substring(24));
- }
- class ModuleCache {
- apply(compiler) {
- const compilerHooks = pluginCompat.hooks(compiler);
- let moduleCache = {};
- let parityCache = {};
- const moduleArchetypeCache = {
- _ops: [],
- get(id) {
- if (moduleCache[id] && !moduleCache[id].invalid) {
- if (typeof moduleCache[id] === 'string') {
- moduleCache[id] = JSON.parse(moduleCache[id]);
- }
- return moduleCache[id];
- }
- },
- set(id, item) {
- moduleCache[id] = item;
- if (item) {
- this._ops.push(id);
- } else if (moduleCache[id]) {
- if (typeof moduleCache[id] === 'string') {
- moduleCache[id] = JSON.parse(moduleCache[id]);
- }
- moduleCache[id].invalid = true;
- moduleCache[id].invalidReason = 'overwritten';
- this._ops.push(id);
- }
- },
- operations() {
- const _this = this;
- const ops = this._ops.map(id => ({
- key: relateNormalModuleId(compiler, id),
- value: _this.get(id) || null,
- }));
- this._ops.length = 0;
- return ops;
- },
- };
- compilerHooks._hardSourceArchetypeRegister.call(
- 'Module',
- moduleArchetypeCache,
- );
- let moduleCacheSerializer;
- compilerHooks._hardSourceCreateSerializer.tap(
- 'HardSource - ModuleCache',
- (cacheSerializerFactory, cacheDirPath) => {
- moduleCacheSerializer = cacheSerializerFactory.create({
- name: 'module',
- type: 'data',
- cacheDirPath,
- autoParse: true,
- });
- },
- );
- compilerHooks._hardSourceResetCache.tap('HardSource - ModuleCache', () => {
- moduleCache = {};
- });
- compilerHooks._hardSourceReadCache.tapPromise(
- 'HardSource - ModuleCache',
- ({ contextKeys, contextNormalModuleId, copyWithDeser }) =>
- moduleCacheSerializer
- .read()
- .then(_moduleCache => {
- Object.keys(_moduleCache).forEach(key => {
- if (key.startsWith('__hardSource_parityToken')) {
- parityCache[key] = _moduleCache[key];
- delete _moduleCache[key];
- }
- });
- return _moduleCache;
- })
- .then(contextKeys(compiler, contextNormalModuleId))
- .then(copyWithDeser.bind(null, moduleCache)),
- );
- compilerHooks._hardSourceParityCache.tap(
- 'HardSource - ModuleCache',
- parityRoot => {
- parityCacheFromCache('Module', parityRoot, parityCache);
- },
- );
- compilerHooks.compilation.tap('HardSource - ModuleCache', compilation => {
- compilation.__hardSourceModuleCache = moduleCache;
- });
- compilerHooks._hardSourceWriteCache.tapPromise(
- 'HardSource - ModuleCache',
- compilation => {
- const moduleOps = moduleArchetypeCache.operations();
- if (!compilation.compiler.parentCompilation) {
- // Add ops to remove no longer valid modules. If they were replaced with a
- // up to date module, they will already have replaced this item so we
- // won't accidentally delete up to date modules.
- Object.keys(moduleCache).forEach(key => {
- const cacheItem = moduleCache[key];
- if (cacheItem && cacheItem.invalid) {
- // console.log('invalid', cacheItem.invalidReason);
- moduleCache[key] = null;
- moduleOps.push({
- key,
- value: null,
- });
- }
- });
- }
- pushParityWriteOps(compilation, moduleOps);
- return moduleCacheSerializer.write(moduleOps);
- },
- );
- }
- }
- module.exports = ModuleCache;
|