1 | "use strict";
|
2 | Object.defineProperty(exports, "__esModule", { value: true });
|
3 | var fs = require("fs");
|
4 | var Promise = require("bluebird");
|
5 | var sysUtil = require("systemjs-builder/lib/utils.js");
|
6 | var path = require("path");
|
7 | var _ = require("lodash");
|
8 | var utils = require("./utils");
|
9 | var serializer = require("./config-serializer");
|
10 | var minifier = require("html-minifier");
|
11 | var CleanCSS = require("clean-css");
|
12 | var builder_factory_1 = require("./builder-factory");
|
13 | var mkdirp = require("mkdirp");
|
14 | function createBuildExpression(cfg) {
|
15 | var appCfg = serializer.getAppConfig(cfg.configPath);
|
16 | var includes = cfg.includes;
|
17 | var excludes = cfg.excludes;
|
18 | var includeExpression = includes.map(function (m) { return getFullModuleName(m, appCfg.map); }).join(' + ');
|
19 | var excludeExpression = excludes.map(function (m) { return getFullModuleName(m, appCfg.map); }).join(' - ');
|
20 | var buildExpression = includeExpression;
|
21 | if (excludeExpression && excludeExpression.length > 0) {
|
22 | buildExpression = buildExpression + " - " + excludeExpression;
|
23 | }
|
24 | return buildExpression;
|
25 | }
|
26 | function createFetchHook(cfg) {
|
27 | return function (load, fetch) {
|
28 | var address = sysUtil.fromFileURL(load.address);
|
29 | var ext = path.extname(address);
|
30 | if (!(ext === '.html' || ext === '.css')) {
|
31 | return fetch(load);
|
32 | }
|
33 | var plugin = path.basename(sysUtil.fromFileURL(load.name.split('!')[1]));
|
34 | if (!plugin.startsWith('plugin-text')) {
|
35 | return fetch(load);
|
36 | }
|
37 | if (ext === '.html' && cfg.options.minify) {
|
38 | var content = fs.readFileSync(address, 'utf8');
|
39 | var opts = utils.getHTMLMinOpts(cfg.options.htmlminopts);
|
40 | return minifier.minify(content, opts);
|
41 | }
|
42 | if (ext === '.css' && cfg.options.minify) {
|
43 | var content = fs.readFileSync(address, 'utf8');
|
44 | var opts = utils.getCSSMinOpts(cfg.options.cssminopts);
|
45 | var output = new CleanCSS(opts).minify(content);
|
46 | if (output.errors.length) {
|
47 | throw new Error('CSS Plugin:\n' + output.errors.join('\n'));
|
48 | }
|
49 | return output.styles;
|
50 | }
|
51 | return fetch(load);
|
52 | };
|
53 | }
|
54 | function bundle(cfg) {
|
55 | var buildExpression = createBuildExpression(cfg);
|
56 | cfg.options.fetch = createFetchHook(cfg);
|
57 | var tasks = [
|
58 | _bundle(buildExpression, cfg)
|
59 | ];
|
60 | if (cfg.options.depCache) {
|
61 | tasks.push(_depCache(buildExpression, cfg));
|
62 | }
|
63 | return Promise.all(tasks);
|
64 | }
|
65 | exports.bundle = bundle;
|
66 | function depCache(cfg) {
|
67 | var buildExpression = createBuildExpression(cfg);
|
68 | return _depCache(buildExpression, cfg);
|
69 | }
|
70 | exports.depCache = depCache;
|
71 | function _depCache(buildExpression, cfg) {
|
72 | var builder = builder_factory_1.createBuilder(cfg);
|
73 | return builder.trace(buildExpression, cfg.options)
|
74 | .then(function (tree) {
|
75 | var depCache = builder.getDepCache(tree);
|
76 | var configPath = cfg.injectionConfigPath;
|
77 | var appCfg = serializer.getAppConfig(configPath);
|
78 | var dc = appCfg.depCache || {};
|
79 | _.assign(dc, depCache);
|
80 | appCfg.depCache = dc;
|
81 | serializer.saveAppConfig(configPath, appCfg);
|
82 | return Promise.resolve();
|
83 | });
|
84 | }
|
85 | function _bundle(buildExpression, cfg) {
|
86 | var builder = builder_factory_1.createBuilder(cfg);
|
87 | return builder.bundle(buildExpression, cfg.options)
|
88 | .then(function (output) {
|
89 | var outfile = utils.getOutFileName(output.source, cfg.bundleName + '.js', cfg.options.rev);
|
90 | var outPath = createOutputPath(cfg.baseURL, outfile, cfg.outputPath);
|
91 | writeOutput(output, outPath, cfg.force, cfg.options.sourceMaps);
|
92 | if (cfg.options.sourceMaps && cfg.options.sourceMaps !== 'inline') {
|
93 | writeSourcemaps(output, outPath + ".map", cfg.force);
|
94 | }
|
95 | if (cfg.options.inject) {
|
96 | injectBundle(builder, output, outfile, cfg);
|
97 | }
|
98 | return Promise.resolve();
|
99 | });
|
100 | }
|
101 | function createOutputPath(baseURL, outfile, outputPath) {
|
102 | return outputPath ? path.resolve(outputPath, path.basename(outfile)) : path.resolve(baseURL, outfile);
|
103 | }
|
104 | function writeSourcemaps(output, outPath, force) {
|
105 | if (fs.existsSync(outPath)) {
|
106 | if (!force) {
|
107 | throw new Error("A source map named '" + outPath + "' already exists. Use the --force option to overwrite it.");
|
108 | }
|
109 | fs.unlinkSync(outPath);
|
110 | }
|
111 | else {
|
112 | var dirPath = path.dirname(outPath);
|
113 | if (!fs.existsSync(dirPath)) {
|
114 | mkdirp.sync(dirPath);
|
115 | }
|
116 | }
|
117 | fs.writeFileSync(outPath, output.sourceMap);
|
118 | }
|
119 | exports.writeSourcemaps = writeSourcemaps;
|
120 | function writeOutput(output, outPath, force, sourceMap) {
|
121 | if (fs.existsSync(outPath)) {
|
122 | if (!force) {
|
123 | throw new Error("A bundle named '" + outPath + "' already exists. Use the --force option to overwrite it.");
|
124 | }
|
125 | fs.unlinkSync(outPath);
|
126 | }
|
127 | else {
|
128 | var dirPath = path.dirname(outPath);
|
129 | if (!fs.existsSync(dirPath)) {
|
130 | mkdirp.sync(dirPath);
|
131 | }
|
132 | }
|
133 | var source = output.source;
|
134 | if (sourceMap && sourceMap !== 'inline') {
|
135 | var sourceMapFileName = path.basename(outPath) + '.map';
|
136 | source += '\n//# sourceMappingURL=' + sourceMapFileName;
|
137 | }
|
138 | fs.writeFileSync(outPath, source);
|
139 | }
|
140 | exports.writeOutput = writeOutput;
|
141 | function injectBundle(builder, output, outfile, cfg) {
|
142 | var configPath = cfg.injectionConfigPath;
|
143 | var bundleName = builder.getCanonicalName(sysUtil.toFileURL(path.resolve(cfg.baseURL, outfile)));
|
144 | var appCfg = serializer.getAppConfig(configPath);
|
145 | if (!appCfg.bundles) {
|
146 | appCfg.bundles = {};
|
147 | }
|
148 | appCfg.bundles[bundleName] = output.modules.sort();
|
149 | serializer.saveAppConfig(configPath, appCfg);
|
150 | }
|
151 | exports.injectBundle = injectBundle;
|
152 | function getFullModuleName(moduleName, map) {
|
153 | var cleanName = function (n) {
|
154 |
|
155 | var result = n.replace(/^.*:/, '');
|
156 |
|
157 | if (result.charAt(0) === '@') {
|
158 | result = '@' + result.substr(1).replace(/@.*$/, '');
|
159 | }
|
160 | else {
|
161 | result = result.replace(/@.*$/, '');
|
162 | }
|
163 | return result;
|
164 | };
|
165 | var matches = Object.keys(map).filter(function (m) { return m === moduleName; });
|
166 | if (matches.length === 1) {
|
167 | return moduleName;
|
168 | }
|
169 | matches = Object.keys(map).filter(function (m) {
|
170 | return cleanName(m) === cleanName(moduleName);
|
171 | });
|
172 | if (matches.length === 1) {
|
173 | return matches[0];
|
174 | }
|
175 | if (matches.length === 0) {
|
176 | return moduleName;
|
177 | }
|
178 | throw new Error("A version conflict was found among the module names specified in the configuration for '" + moduleName + "'. Try including a full module name with a specific version number or resolve the conflict manually with jspm.");
|
179 | }
|
180 | exports.getFullModuleName = getFullModuleName;
|
181 |
|
\ | No newline at end of file |