Skip to content

Commit 00c42bf

Browse files
author
Gil Greenberg
authored
Merge pull request #1 from toddbc/race-fix
Generate requirejs stubs immediately
2 parents 3c6fcd6 + 327e13c commit 00c42bf

File tree

1 file changed

+92
-16
lines changed

1 file changed

+92
-16
lines changed

index.js

Lines changed: 92 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -5,30 +5,106 @@ const ConcatSource = require('webpack-sources').ConcatSource;
55
function RequireJsExportPlugin() {
66
}
77

8+
function gatherRequireJsImports(modules) {
9+
let needsImport = [];
10+
for (var module of modules) {
11+
// If the requirejs-loader was used, then we need to wrap and import this module.
12+
// TODO: Clean up this check.
13+
if (module.request && module.request.indexOf('requirejs-loader') !== -1) {
14+
needsImport.push(module.rawRequest);
15+
}
16+
}
17+
18+
return needsImport;
19+
}
20+
21+
function gatherRequireJsExports(modules) {
22+
let needsExport = [];
23+
for (var module of modules) {
24+
// If the requirejs-loader was used, then we need to wrap and import this module.
25+
// TODO: Clean up this check.
26+
if (module.request && module.request.indexOf('requirejs-loader') === -1) {
27+
// We use the raw request to define the same name, including loader.
28+
var name = module.rawRequest;
29+
// TODO: Maybe just strip everything but 'text!'?
30+
if (name.indexOf('script-loader!') === 0) {
31+
name = name.substr('script-loader!'.length);
32+
}
33+
needsExport.push({ id: module.id, name: name });
34+
}
35+
}
36+
37+
return needsExport;
38+
}
39+
40+
function generateProlog(chunkId, imports, exports) {
41+
const jsonImports = JSON.stringify(imports);
42+
const jsonDefineStub = JSON.stringify('__webpack_export_' + chunkId);
43+
44+
let prolog = `
45+
(function(){
46+
var __webpack_exports__ = {};`;
47+
48+
if (imports.length !== 0) {
49+
prolog += `
50+
window.define(${jsonDefineStub}, ${jsonImports}, function() {`;
51+
}
52+
53+
return prolog;
54+
}
55+
56+
function generateEpilog(chunkId, imports, exports) {
57+
let epilog = '';
58+
if (imports.length !== 0) {
59+
epilog += `
60+
});`;
61+
}
62+
63+
const jsonDefineStubs = JSON.stringify(imports.length === 0 ? [] : ['__webpack_export_' + chunkId]);
64+
for (let module of exports) {
65+
const jsonName = JSON.stringify(module.name);
66+
const jsonId = JSON.stringify(module.id);
67+
epilog += `
68+
window.define(${jsonName}, ${jsonDefineStubs}, function() { return __webpack_exports__[${jsonId}]; });`;
69+
}
70+
71+
epilog += `
72+
}());`;
73+
74+
return epilog;
75+
}
76+
877
RequireJsExportPlugin.prototype.apply = function(compiler) {
978
compiler.plugin('compilation', function (compilation, data) {
10-
compilation.plugin('succeed-module', function(module) {
11-
// This ensures we don't export the import stubs for requirejs.
12-
// TODO: Determine loader better.
13-
if (module.request && String(module.request).indexOf('requirejs-loader') !== -1) {
14-
return;
15-
}
79+
compilation.plugin('after-optimize-module-ids', function(modules) {
80+
for (let module of modules) {
81+
// This ensures we don't export the import stubs for requirejs.
82+
// TODO: Determine loader better.
83+
if (module.request && String(module.request).indexOf('requirejs-loader') !== -1) {
84+
continue;
85+
}
1686

17-
// TODO: Find a way around using _source.
18-
if (module.rawRequest && module._source) {
19-
// We use the raw request to define the same name, including loader.
20-
var name = module.rawRequest;
21-
// TODO: Maybe just strip everything but 'text!'?
22-
if (name.indexOf('script-loader!') === 0) {
23-
name = name.substr('script-loader!'.length);
87+
// TODO: Find a way around using _source.
88+
if (module.rawRequest && module._source) {
89+
var definition = '__webpack_exports__[' + JSON.stringify(module.id) + '] = module.exports;';
90+
module._source = new ConcatSource(module._source, '\n', definition);
2491
}
92+
}
93+
});
2594

26-
var definition = 'window.define(' + JSON.stringify(name) + ', [], function() { return module.exports; });';
27-
module._source = new ConcatSource(module._source, '\n', definition);
95+
compilation.plugin('chunk-asset', (chunk, filename) => {
96+
const needsImport = gatherRequireJsImports(chunk.modules);
97+
const needsExport = gatherRequireJsExports(chunk.modules);
98+
if (needsImport.length != 0 || needsExport.length != 0) {
99+
let prolog = generateProlog(chunk.id, needsImport, needsExport);
100+
let epilog = generateEpilog(chunk.id, needsImport, needsExport);
101+
102+
compilation.assets[filename] = new ConcatSource(prolog, "\n", compilation.assets[filename], "\n", epilog);
28103
}
104+
105+
chunk['--requirejs-export:done'] = true;
29106
});
30107
});
31108
};
32109

33-
34110
module.exports = RequireJsExportPlugin;

0 commit comments

Comments
 (0)