Skip to content

Commit

Permalink
Disable the modules API polyfill on latest Ember
Browse files Browse the repository at this point in the history
Disables the modules API polyfill on the latest versions of Ember.
  • Loading branch information
Chris Garrett authored and rwjblue committed Mar 17, 2021
1 parent 9ef9507 commit 26d9fdc
Show file tree
Hide file tree
Showing 10 changed files with 1,109 additions and 290 deletions.
57 changes: 54 additions & 3 deletions lib/colocated-babel-plugin.js
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,11 @@
module.exports = function (babel) {
let t = babel.types;

function makeSetComponentTemplateMemberExpression() {
function makeSetComponentTemplateExpression(state) {
if (!state.opts.requiresModuleApiPolyfill) {
return state._colocationEnsureImport('setComponentTemplate', '@ember/component');
}

return t.memberExpression(t.identifier('Ember'), t.identifier('_setComponentTemplate'));
}

Expand All @@ -15,6 +19,53 @@ module.exports = function (babel) {
name: 'ember-cli-htmlbars-colocation-template',

visitor: {
Program(path, state) {
let allAddedImports = {};

state._colocationEnsureImport = (exportName, moduleName) => {
let addedImports = (allAddedImports[moduleName] = allAddedImports[moduleName] || {});

if (addedImports[exportName]) return addedImports[exportName];

let importDeclarations = path.get('body').filter((n) => n.type === 'ImportDeclaration');

let preexistingImportDeclaration = importDeclarations.find(
(n) => n.get('source').get('value').node === moduleName
);

if (preexistingImportDeclaration) {
let importSpecifier = preexistingImportDeclaration
.get('specifiers')
.find(({ node }) => {
return exportName === 'default'
? t.isImportDefaultSpecifier(node)
: node.imported.name === exportName;
});

if (importSpecifier) {
addedImports[exportName] = importSpecifier.node.local;
}
}

if (!addedImports[exportName]) {
let uid = path.scope.generateUidIdentifier(
exportName === 'default' ? moduleName : exportName
);
addedImports[exportName] = uid;

let newImportSpecifier =
exportName === 'default'
? t.importDefaultSpecifier(uid)
: t.importSpecifier(uid, t.identifier(exportName));

let newImport = t.importDeclaration([newImportSpecifier], t.stringLiteral(moduleName));
path.unshiftContainer('body', newImport);
}

return addedImports[exportName];
};
},

VariableDeclarator(path, state) {
if (path.node.id.name === '__COLOCATED_TEMPLATE__') {
state.colocatedTemplateFound = true;
Expand All @@ -38,7 +89,7 @@ module.exports = function (babel) {

state.setComponentTemplateInjected = true;
let defaultExportDeclaration = path.node.declaration;
let setComponentTemplateMemberExpression = makeSetComponentTemplateMemberExpression();
let setComponentTemplateMemberExpression = makeSetComponentTemplateExpression(state);
let colocatedTemplateIdentifier = makeColocatedTemplateIdentifier();

if (defaultExportDeclaration.type === 'ClassDeclaration') {
Expand Down Expand Up @@ -85,7 +136,7 @@ module.exports = function (babel) {
state.setComponentTemplateInjected = true;
path.parent.body.push(
t.expressionStatement(
t.callExpression(makeSetComponentTemplateMemberExpression(), [
t.callExpression(makeSetComponentTemplateExpression(state), [
makeColocatedTemplateIdentifier(),
defaultSpecifier.local,
])
Expand Down
15 changes: 12 additions & 3 deletions lib/ember-addon-main.js
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@
const path = require('path');
const SilentError = require('silent-error');
const utils = require('./utils');
const VersionChecker = require('ember-cli-version-checker');

let registryInvocationCounter = 0;

Expand Down Expand Up @@ -62,7 +63,7 @@ module.exports = {
transpileTree(inputTree, htmlbarsOptions) {
const TemplateCompiler = require('./template-compiler-plugin');

return new TemplateCompiler(inputTree, htmlbarsOptions);
return new TemplateCompiler(inputTree, htmlbarsOptions, this._requiresModuleApiPolyfill);
},

setupPreprocessorRegistry(type, registry) {
Expand Down Expand Up @@ -169,6 +170,9 @@ module.exports = {

let isProduction = process.env.EMBER_ENV === 'production';

let checker = new VersionChecker(this.parent).for('ember-source', 'npm');
this._requiresModuleApiPolyfill = checker.exists() && checker.lt('3.27.0-alpha.1');

// This is an option intended to be used only be `ember-template-imports`.
// DO NOT USE THIS
let customModules =
Expand All @@ -190,7 +194,8 @@ module.exports = {
this.projectConfig(),
templateCompilerPath,
isProduction,
customModules
customModules,
this._requiresModuleApiPolyfill
);

babelPlugins.push(htmlbarsInlinePrecompilePlugin);
Expand All @@ -205,14 +210,18 @@ module.exports = {
projectConfig: this.projectConfig(),
templateCompilerPath,
modules: customModules,
requiresModuleApiPolyfill: this._requiresModuleApiPolyfill,
});

babelPlugins.push(htmlBarsPlugin);
}
}

if (this._shouldColocateTemplates() && !utils.isColocatedBabelPluginRegistered(babelPlugins)) {
babelPlugins.push(require.resolve('./colocated-babel-plugin'));
babelPlugins.push([
require.resolve('./colocated-babel-plugin'),
{ requiresModuleApiPolyfill: this._requiresModuleApiPolyfill },
]);
}
},

Expand Down
49 changes: 28 additions & 21 deletions lib/template-compiler-plugin.js
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@ function rethrowBuildError(error) {
}

class TemplateCompiler extends Filter {
constructor(inputTree, _options) {
constructor(inputTree, _options, requiresModuleApiPolyfill) {
let options = _options || {};

if (!('persist' in options)) {
Expand All @@ -35,6 +35,7 @@ class TemplateCompiler extends Filter {

this.options = options;
this.inputTree = inputTree;
this.requiresModuleApiPolyfill = requiresModuleApiPolyfill;

// TODO: do we need this?
this.precompile = this.options.templateCompiler.precompile;
Expand All @@ -51,6 +52,7 @@ class TemplateCompiler extends Filter {
processString(string, relativePath) {
let srcDir = this.inputPaths[0];
let srcName = path.join(srcDir, relativePath);

try {
// we have to reverse these for reasons that are a bit bonkers. the initial
// version of this system used `registeredPlugin` from
Expand All @@ -63,25 +65,23 @@ class TemplateCompiler extends Filter {
// sooooooo...... we are forced to maintain that **absolutely bonkers** ordering
let astPlugins = this.options.plugins ? [...this.options.plugins.ast].reverse() : [];

let result =
'export default ' +
utils.template(this.options.templateCompiler, stripBom(string), {
contents: string,
isProduction: this.options.isProduction,
moduleName: relativePath,
parseOptions: {
srcName: srcName,
},

// intentionally not using `plugins: this.options.plugins` here
// because if we do, Ember will mutate the shared plugins object (adding
// all of the built in AST transforms into plugins.ast, which breaks
// persistent caching)
plugins: {
ast: astPlugins,
},
}) +
';';
let precompiled = this.options.templateCompiler.precompile(stripBom(string), {
contents: string,
isProduction: this.options.isProduction,
moduleName: relativePath,
parseOptions: {
srcName: srcName,
},

// intentionally not using `plugins: this.options.plugins` here
// because if we do, Ember will mutate the shared plugins object (adding
// all of the built in AST transforms into plugins.ast, which breaks
// persistent caching)
plugins: {
ast: astPlugins,
},
});

if (this.options.dependencyInvalidation) {
let plugins = pluginsWithDependencies(this.options.plugins.ast);
let dependencies = [];
Expand All @@ -91,7 +91,12 @@ class TemplateCompiler extends Filter {
}
this.dependencies.setDependencies(relativePath, dependencies);
}
return result;

if (this.requiresModuleApiPolyfill) {
return `export default Ember.HTMLBars.template(${precompiled});`;
} else {
return `import { createTemplateFactory } from '@ember/template-factory';\n\nexport default createTemplateFactory(${precompiled});`;
}
} catch (error) {
rethrowBuildError(error);
}
Expand All @@ -106,6 +111,8 @@ class TemplateCompiler extends Filter {
}
}

strippedOptions._requiresModuleApiPolyfill = this.requiresModuleApiPolyfill;

return strippedOptions;
}

Expand Down
21 changes: 9 additions & 12 deletions lib/utils.js
Original file line number Diff line number Diff line change
Expand Up @@ -50,17 +50,20 @@ function isInlinePrecompileBabelPluginRegistered(plugins) {
}

function isColocatedBabelPluginRegistered(plugins) {
return plugins.some(
(plugin) => typeof plugin === 'string' && plugin === require.resolve('./colocated-babel-plugin')
);
return plugins.some((plugin) => {
let path = Array.isArray(plugin) ? plugin[0] : plugin;

return typeof path === 'string' && path === require.resolve('./colocated-babel-plugin');
});
}

function buildParalleizedBabelPlugin(
pluginInfo,
projectConfig,
templateCompilerPath,
isProduction,
customModules
customModules,
requiresModuleApiPolyfill
) {
let parallelBabelInfo = {
requireFile: require.resolve('./require-from-worker'),
Expand All @@ -71,6 +74,7 @@ function buildParalleizedBabelPlugin(
projectConfig,
parallelConfigs: pluginInfo.parallelConfigs,
modules: Object.assign({}, customModules, INLINE_PRECOMPILE_MODULES),
requiresModuleApiPolyfill,
},
};

Expand Down Expand Up @@ -199,12 +203,6 @@ function initializeEmberENV(templateCompiler, EmberENV) {
}
}

function template(templateCompiler, string, options) {
let precompiled = templateCompiler.precompile(string, options);

return 'Ember.HTMLBars.template(' + precompiled + ')';
}

function setup(pluginInfo, options) {
let projectConfig = options.projectConfig || {};
let templateCompilerPath = options.templateCompilerPath;
Expand Down Expand Up @@ -261,7 +259,7 @@ function setup(pluginInfo, options) {
{
precompile,
isProduction: options.isProduction,
ensureModuleApiPolyfill: true,
ensureModuleApiPolyfill: options.requiresModuleApiPolyfill,
modules: Object.assign({}, options.modules, INLINE_PRECOMPILE_MODULES),
},
'ember-cli-htmlbars:inline-precompile',
Expand Down Expand Up @@ -355,7 +353,6 @@ function setupPlugins(wrappers) {
module.exports = {
buildOptions,
initializeEmberENV,
template,
setup,
makeCacheKey,
setupPlugins,
Expand Down
1 change: 1 addition & 0 deletions node-tests/addon-test.js
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,7 @@ describe('ember-cli-htmlbars addon', function () {
project,
parent: project,
ui: this.ui,
_requiresModuleApiPolyfill: true,
});

project.addons.push(this.addon);
Expand Down
Loading

0 comments on commit 26d9fdc

Please sign in to comment.