diff --git a/docs/hooks.md b/docs/hooks.md index 6ca7a6d1..19411c7c 100644 --- a/docs/hooks.md +++ b/docs/hooks.md @@ -57,7 +57,7 @@ This function downloads and executes the code for a module. The promise must res The default system.js implementation is to append a script tag that downloads and executes the module's code, subsequently resolving the promise with the most recent register: `resolve(System.getRegister())`. [Example](https://github.com/systemjs/systemjs/blob/master/src/features/script-load.js). -#### getRegister() -> [deps: String[], declare: Function] +#### getRegister(url) -> [deps: String[], declare: Function] > This hook is intended for custom module format integrations only. diff --git a/src/extras/named-register.js b/src/extras/named-register.js index 9706a1d1..1d3e4631 100644 --- a/src/extras/named-register.js +++ b/src/extras/named-register.js @@ -17,10 +17,11 @@ SystemJS.prototype = systemJSPrototype; System.constructor = SystemJS; - var firstNamedDefine; + var firstNamedDefine, firstName; function setRegisterRegistry(systemInstance) { systemInstance.registerRegistry = Object.create(null); + systemInstance.namedRegisterAliases = Object.create(null); } var register = systemJSPrototype.register; @@ -31,10 +32,12 @@ this.registerRegistry[name] = define; if (!firstNamedDefine) { firstNamedDefine = define; - Promise.resolve().then(function () { - firstNamedDefine = null; - }); + firstName = name; } + setTimeout(function () { + firstNamedDefine = null; + firstName = null; + }); return register.apply(this, [deps, declare]); }; @@ -45,7 +48,7 @@ return resolve.call(this, id, parentURL); } catch (err) { if (id in this.registerRegistry) { - return id; + return this.namedRegisterAliases[id] || id; } throw err; } @@ -63,12 +66,16 @@ }; var getRegister = systemJSPrototype.getRegister; - systemJSPrototype.getRegister = function () { + systemJSPrototype.getRegister = function (url) { // Calling getRegister() because other extras need to know it was called so they can perform side effects - var register = getRegister.call(this); + var register = getRegister.call(this, url); + if (firstName && url) { + this.namedRegisterAliases[firstName] = url; + } var result = firstNamedDefine || register; firstNamedDefine = null; + firstName = null; return result; } })(typeof self !== 'undefined' ? self : global); diff --git a/src/extras/transform.js b/src/extras/transform.js index 9caf6d51..da34fb5f 100644 --- a/src/extras/transform.js +++ b/src/extras/transform.js @@ -25,7 +25,7 @@ import { errMsg } from '../err-msg.js'; }) .then(function (source) { (0, eval)(source + '\n//# sourceURL=' + url); - return loader.getRegister(); + return loader.getRegister(url); }); }; diff --git a/src/features/fetch-load.js b/src/features/fetch-load.js index 5dce9d38..d00c5c6e 100644 --- a/src/features/fetch-load.js +++ b/src/features/fetch-load.js @@ -31,7 +31,7 @@ systemJSPrototype.instantiate = function (url, parent) { if (source.indexOf('//# sourceURL=') < 0) source += '\n//# sourceURL=' + url; (0, eval)(source); - return loader.getRegister(); + return loader.getRegister(url); }); }); }; diff --git a/src/features/script-load.js b/src/features/script-load.js index ee7db6be..bace6f8b 100644 --- a/src/features/script-load.js +++ b/src/features/script-load.js @@ -76,7 +76,7 @@ systemJSPrototype.instantiate = function (url, firstParentUrl) { reject(lastWindowError); } else { - var register = loader.getRegister(); + var register = loader.getRegister(url); // Clear any auto import registration for dynamic import scripts during load if (register && register[0] === lastAutoImportDeps) clearTimeout(lastAutoImportTimeout); diff --git a/src/features/worker-load.js b/src/features/worker-load.js index 9e8d7403..c0171b33 100644 --- a/src/features/worker-load.js +++ b/src/features/worker-load.js @@ -9,6 +9,6 @@ if (hasSelf && typeof importScripts === 'function') var loader = this; return Promise.resolve().then(function () { importScripts(url); - return loader.getRegister(); + return loader.getRegister(url); }); }; diff --git a/test/browser/named-register.js b/test/browser/named-register.js index a508c95b..490f5b90 100644 --- a/test/browser/named-register.js +++ b/test/browser/named-register.js @@ -171,4 +171,30 @@ suite('Named System.register', function() { assert.equal(m.b, 'b'); }); }); + + // https://github.com/systemjs/systemjs/issues/2349 + test('Bundles with named register do not instantiate last module more than once', function () { + // First import the module via URL + return System.import('./fixtures/browser/named-instantiate-count.js').then(function (urlModule) { + // Then import the same module via named register name + return System.import('named-instantiate-count').then(function (namedModule) { + assert.equal(urlModule.getInstantiateCount(), 1); + assert.equal(namedModule.getInstantiateCount(), 1); + assert.equal(urlModule, namedModule); + }); + }); + }); + + // https://github.com/systemjs/systemjs/issues/2349 + test('Named bundles that self import', function () { + // First import the module via URL + return System.import('./fixtures/browser/named-self-import.js').then(function (urlModule) { + // Then import the same module via named register name + return System.import('named-self-import').then(function (namedModule) { + assert.equal(urlModule.getInstantiateCount(), 1); + assert.equal(namedModule.getInstantiateCount(), 1); + assert.equal(urlModule, namedModule); + }); + }); + }); }); \ No newline at end of file diff --git a/test/fixtures/browser/named-instantiate-count.js b/test/fixtures/browser/named-instantiate-count.js new file mode 100644 index 00000000..e0839e2a --- /dev/null +++ b/test/fixtures/browser/named-instantiate-count.js @@ -0,0 +1,12 @@ +let instantiateCount = 0; + +System.register("named-instantiate-count", [], function (_export) { + instantiateCount++; + return { + execute: function () { + _export('getInstantiateCount', function () { + return instantiateCount; + }); + } + }; +}); \ No newline at end of file diff --git a/test/fixtures/browser/named-self-import.js b/test/fixtures/browser/named-self-import.js new file mode 100644 index 00000000..468335d7 --- /dev/null +++ b/test/fixtures/browser/named-self-import.js @@ -0,0 +1,31 @@ +let instantiateCount = 0; + +System.register("named-self-import", ["named-self-import/dep"], function (_export) { + instantiateCount++; + var dep; + + return { + setters: [ + function (d) { + dep = d; + } + ], + execute: function () { + dep.method(); + + _export('getInstantiateCount', function () { + return instantiateCount; + }); + } + }; +}); + +System.register("named-self-import/dep", [], function (_export) { + return { + execute: function () { + _export("method", function () { + return 1; + }); + } + }; +});