1 |
|
2 | 'use strict';
|
3 |
|
4 | var path = require('path');
|
5 | var fs = require('fs');
|
6 | var hashForDep = require('hash-for-dep');
|
7 | var HTMLBarsInlinePrecompilePlugin = require('babel-plugin-htmlbars-inline-precompile');
|
8 | var SilentError = require('silent-error');
|
9 | var resolve = require('resolve');
|
10 | var semver = require('semver');
|
11 |
|
12 | module.exports = {
|
13 | name: 'ember-cli-htmlbars-inline-precompile',
|
14 |
|
15 | init() {
|
16 | this._super.init && this._super.init.apply(this, arguments);
|
17 |
|
18 | let babelPath = resolve.sync('ember-cli-babel/package.json', { basedir: this.parent.root });
|
19 | let babelVersion = require(babelPath).version;
|
20 |
|
21 | var hasCorrectBabelVersion = semver.lt(babelVersion, '6.0.0-alpha.1');
|
22 |
|
23 | if (!hasCorrectBabelVersion) {
|
24 | throw new SilentError('ember-cli-htmlbars-inline-precompile@0.3 requires the host to use ember-cli-babel@5. To use ember-cli-babel@6 please upgrade ember-cli-htmlbars-inline-precompile to 0.4.');
|
25 | }
|
26 | },
|
27 |
|
28 | setupPreprocessorRegistry: function(type, registry) {
|
29 | if (type === 'parent') {
|
30 | this.parentRegistry = registry;
|
31 | }
|
32 | },
|
33 |
|
34 | included: function(app) {
|
35 | this._super.included(app);
|
36 |
|
37 | var emberCLIHtmlBars = this.project.findAddonByName('ember-cli-htmlbars');
|
38 |
|
39 | if(emberCLIHtmlBars && emberCLIHtmlBars.inlinePrecompilerRegistered) {
|
40 | return;
|
41 | }
|
42 |
|
43 | app.options = app.options || {};
|
44 | app.options.babel = app.options.babel || {};
|
45 | app.options.babel.plugins = app.options.babel.plugins || [];
|
46 |
|
47 |
|
48 | var projectConfig = this.projectConfig() || {};
|
49 | var EmberENV = projectConfig.EmberENV || {};
|
50 | var templateCompilerPath = this.templateCompilerPath();
|
51 |
|
52 |
|
53 |
|
54 |
|
55 |
|
56 |
|
57 |
|
58 |
|
59 | delete require.cache[templateCompilerPath];
|
60 |
|
61 | var clonedEmberENV = JSON.parse(JSON.stringify(EmberENV));
|
62 | global.EmberENV = clonedEmberENV;
|
63 |
|
64 | var pluginInfo = this.astPlugins();
|
65 | var Compiler = require(templateCompilerPath);
|
66 | var templateCompilerFullPath = require.resolve(templateCompilerPath);
|
67 | var templateCompilerCacheKey = fs.readFileSync(templateCompilerFullPath, { encoding: 'utf-8' });
|
68 |
|
69 | pluginInfo.plugins.forEach(function(plugin) {
|
70 | Compiler.registerPlugin('ast', plugin);
|
71 | });
|
72 |
|
73 | var PrecompileInlineHTMLBarsPlugin = HTMLBarsInlinePrecompilePlugin(Compiler.precompile, {
|
74 | cacheKey: [templateCompilerCacheKey].concat(pluginInfo.cacheKeys).join('|')
|
75 | });
|
76 |
|
77 | delete require.cache[templateCompilerPath];
|
78 | delete global.Ember;
|
79 | delete global.EmberENV;
|
80 |
|
81 |
|
82 |
|
83 | if (!this._registeredWithBabel) {
|
84 | app.options.babel.plugins.push(PrecompileInlineHTMLBarsPlugin);
|
85 | this._registeredWithBabel = true;
|
86 | }
|
87 | },
|
88 |
|
89 |
|
90 | astPlugins: function() {
|
91 | var pluginWrappers = this.parentRegistry.load('htmlbars-ast-plugin');
|
92 | var plugins = [];
|
93 | var cacheKeys = [];
|
94 |
|
95 | for (var i = 0; i < pluginWrappers.length; i++) {
|
96 | var wrapper = pluginWrappers[i];
|
97 |
|
98 | plugins.push(wrapper.plugin);
|
99 |
|
100 | if (typeof wrapper.baseDir === 'function') {
|
101 | var pluginHashForDep = hashForDep(wrapper.baseDir());
|
102 | cacheKeys.push(pluginHashForDep);
|
103 | } else {
|
104 |
|
105 | var log = this.ui.writeDeprecateLine || this.ui.writeLine;
|
106 |
|
107 | log.call(this.ui, 'ember-cli-htmlbars-inline-precompile is opting out of caching due to an AST plugin that does not provide a caching strategy: `' + wrapper.name + '`.');
|
108 | cacheKeys.push((new Date()).getTime() + '|' + Math.random());
|
109 | }
|
110 | }
|
111 |
|
112 | return {
|
113 | plugins: plugins,
|
114 | cacheKeys: cacheKeys
|
115 | };
|
116 | },
|
117 |
|
118 |
|
119 | projectConfig: function () {
|
120 | return this.project.config(process.env.EMBER_ENV);
|
121 | },
|
122 |
|
123 |
|
124 | templateCompilerPath: function() {
|
125 | var config = this.projectConfig();
|
126 | var templateCompilerPath = config['ember-cli-htmlbars'] && config['ember-cli-htmlbars'].templateCompilerPath;
|
127 |
|
128 | var ember = this.project.findAddonByName('ember-source');
|
129 | if (ember) {
|
130 | return ember.absolutePaths.templateCompiler;
|
131 | } else if (!templateCompilerPath) {
|
132 | templateCompilerPath = this.project.bowerDirectory + '/ember/ember-template-compiler';
|
133 | }
|
134 |
|
135 | return path.resolve(this.project.root, templateCompilerPath);
|
136 | }
|
137 | };
|