Skip to content

Commit

Permalink
Merge pull request #5261 from webpack/bugfix/import-context-strict-this
Browse files Browse the repository at this point in the history
Fixes for import call context
  • Loading branch information
sokra committed Jul 11, 2017
2 parents bcde519 + 6842d50 commit a6c8362
Show file tree
Hide file tree
Showing 12 changed files with 160 additions and 16 deletions.
34 changes: 18 additions & 16 deletions lib/dependencies/HarmonyImportDependencyParserPlugin.js
Expand Up @@ -66,25 +66,27 @@ module.exports = class HarmonyImportDependencyParserPlugin {
dep.namespaceObjectAsContext = true;
dep.loc = expr.callee.loc;
parser.state.current.addDependency(dep);
return true;
});
parser.plugin("call imported var", (expr) => {
const args = expr.arguments;
const fullExpr = expr;
expr = expr.callee;
const name = expr.name;
const settings = parser.state.harmonySpecifier[`$${name}`];
const dep = new HarmonyImportSpecifierDependency(settings[0], settings[1], settings[2], name, expr.range, this.strictExportPresence);
dep.directImport = true;
dep.callArgs = args;
dep.call = fullExpr;
dep.loc = expr.loc;
parser.state.current.addDependency(dep);
if(args)
parser.walkExpressions(args);
if(expr.arguments)
parser.walkExpressions(expr.arguments);
return true;
});
}
parser.plugin("call imported var", (expr) => {
const args = expr.arguments;
const fullExpr = expr;
expr = expr.callee;
const name = expr.name;
const settings = parser.state.harmonySpecifier[`$${name}`];
const dep = new HarmonyImportSpecifierDependency(settings[0], settings[1], settings[2], name, expr.range, this.strictExportPresence);
dep.directImport = true;
dep.callArgs = args;
dep.call = fullExpr;
dep.loc = expr.loc;
parser.state.current.addDependency(dep);
if(args)
parser.walkExpressions(args);
return true;
});
parser.plugin("hot accept callback", (expr, requests) => {
const dependencies = requests
.filter(request => HarmonyModulesHelpers.checkModuleVar(parser.state, request))
Expand Down
2 changes: 2 additions & 0 deletions lib/optimize/ConcatenatedModule.js
Expand Up @@ -478,6 +478,8 @@ class HarmonyImportSpecifierDependencyConcatenatedTemplate {
let content;
if(dep.id === null) {
content = `__WEBPACK_MODULE_REFERENCE__${info.index}_ns__`;
} else if(dep.namespaceObjectAsContext) {
content = `__WEBPACK_MODULE_REFERENCE__${info.index}_ns__[${JSON.stringify(dep.id)}]`;
} else {
const exportIdx = (module.providedExports).indexOf(dep.id);
content = exportIdx === -1 ? "undefined" : `__WEBPACK_MODULE_REFERENCE__${info.index}_${exportIdx}__`;
Expand Down
14 changes: 14 additions & 0 deletions test/cases/parsing/harmony-this/abc.js
@@ -0,0 +1,14 @@
function returnThis() {
if(typeof this === "undefined") return "undefined";
return this;
}

var a = returnThis;
var b = returnThis;

export {
a,
b
}

export default returnThis;
28 changes: 28 additions & 0 deletions test/cases/parsing/harmony-this/index.js
@@ -0,0 +1,28 @@
"use strict";

import d, {a, b as B} from "./abc";

import * as abc from "./abc";

function x() { throw new Error("should not be executed"); }
it("should have this = undefined on imported non-strict functions", function() {
x
d().should.be.eql("undefined");
x
a().should.be.eql("undefined");
x
B().should.be.eql("undefined");
});

import C2, { C } from "./new";

import * as New from "./new";

it("should be possible to use new correctly", function() {
x
new C().should.match({ok: true});
x
new C2().should.match({ok: true});
x
new New.C().should.match({ok: true});
});
10 changes: 10 additions & 0 deletions test/cases/parsing/harmony-this/new.js
@@ -0,0 +1,10 @@
function C() {
this.ok = this.pok;
}

C.prototype.pok = true;

export default C;
export {
C
};
14 changes: 14 additions & 0 deletions test/configCases/parsing/harmony-this-concat/abc.js
@@ -0,0 +1,14 @@
function returnThis() {
if(typeof this === "undefined") return "undefined";
return this;
}

var a = returnThis;
var b = returnThis;

export {
a,
b
}

export default returnThis;
33 changes: 33 additions & 0 deletions test/configCases/parsing/harmony-this-concat/index.js
@@ -0,0 +1,33 @@
"use strict";

import d, {a, b as B} from "./abc";

import * as abc from "./abc";

function x() { throw new Error("should not be executed"); }
it("should have this = undefined on imported non-strict functions", function() {
x
d().should.be.eql("undefined");
x
a().should.be.eql("undefined");
x
B().should.be.eql("undefined");
x
abc.a().should.be.type("object");
x
var thing = abc.a();
Object.keys(thing).should.be.eql(["a", "b", "default"]);
});

import C2, { C } from "./new";

import * as New from "./new";

it("should be possible to use new correctly", function() {
x
new C().should.match({ok: true});
x
new C2().should.match({ok: true});
x
new New.C().should.match({ok: true});
});
10 changes: 10 additions & 0 deletions test/configCases/parsing/harmony-this-concat/new.js
@@ -0,0 +1,10 @@
function C() {
this.ok = this.pok;
}

C.prototype.pok = true;

export default C;
export {
C
};
@@ -0,0 +1,9 @@
var webpack = require("../../../../");
module.exports = {
module: {
strictThisContextOnImports: true
},
plugins: [
new webpack.optimize.ModuleConcatenationPlugin()
]
};
@@ -0,0 +1,11 @@
import value, { identity } from "./module";
import * as m from "./module";

it("should parse and translate identifiers correctly", function() {
identity(value).should.be.eql(1234);
m.identity(value).should.be.eql(1234);
m.identity(identity).should.be.eql(identity);
m.identity(m.identity).should.be.eql(m.identity);
identity(m.identity).should.be.eql(m.identity);
identity(m.default).should.be.eql(1234);
});
@@ -0,0 +1,2 @@
export function identity(a) { return a; }
export default 1234;
@@ -0,0 +1,9 @@
var webpack = require("../../../../");
module.exports = {
module: {
strictThisContextOnImports: true
},
plugins: [
new webpack.optimize.ModuleConcatenationPlugin()
]
};

0 comments on commit a6c8362

Please sign in to comment.