summaryrefslogtreecommitdiffstats
path: root/lib
diff options
context:
space:
mode:
authorkpdecker <kpdecker@gmail.com>2015-08-04 09:26:19 -0500
committerkpdecker <kpdecker@gmail.com>2015-08-04 09:26:19 -0500
commita62cbad95acdf544dc9daae9834588453ee1f835 (patch)
treef83f5e1f353d63b3c4fb887e6755319d73184099 /lib
parentba31ef8ae4964f2cc9cb6bedd44d7dbf829693ab (diff)
downloadhandlebars.js-a62cbad95acdf544dc9daae9834588453ee1f835.zip
handlebars.js-a62cbad95acdf544dc9daae9834588453ee1f835.tar.gz
handlebars.js-a62cbad95acdf544dc9daae9834588453ee1f835.tar.bz2
Refactor precompiler API into two phase
Load templates and then parse them in a distinct operation. This will allow us to use other input sources such as stdin and strings.
Diffstat (limited to 'lib')
-rw-r--r--lib/precompiler.js154
1 files changed, 83 insertions, 71 deletions
diff --git a/lib/precompiler.js b/lib/precompiler.js
index 48cfebd..2809b1b 100644
--- a/lib/precompiler.js
+++ b/lib/precompiler.js
@@ -5,28 +5,73 @@ import {basename} from 'path';
import {SourceMapConsumer, SourceNode} from 'source-map';
import uglify from 'uglify-js';
+module.exports.loadTemplates = function(opts) {
+ // Build file extension pattern
+ let extension = (opts.extension || 'handlebars').replace(/[\\^$*+?.():=!|{}\-\[\]]/g, function(arg) { return '\\' + arg; });
+ extension = new RegExp('\\.' + extension + '$');
+
+ let ret = [];
+ function processTemplate(template, root) {
+ let path = template,
+ stat;
+ try {
+ stat = fs.statSync(template);
+ } catch (err) {
+ throw new Handlebars.Exception(`Unable to open template file "${template}"`);
+ }
+
+ if (stat.isDirectory()) {
+ opts.hasDirectory = true;
+
+ fs.readdirSync(template).map(function(file) {
+ let childPath = template + '/' + file;
+
+ if (extension.test(childPath) || fs.statSync(childPath).isDirectory()) {
+ processTemplate(childPath, root || template);
+ }
+ });
+ } else {
+ let data = fs.readFileSync(path, 'utf8');
+
+ if (opts.bom && data.indexOf('\uFEFF') === 0) {
+ data = data.substring(1);
+ }
+
+ // Clean the template name
+ if (!root) {
+ template = basename(template);
+ } else if (template.indexOf(root) === 0) {
+ template = template.substring(root.length + 1);
+ }
+ template = template.replace(extension, '');
+
+ ret.push({
+ path: path,
+ name: template,
+ source: data
+ });
+ }
+ }
+ opts.templates.forEach(function(template) {
+ processTemplate(template, opts.root);
+ });
+ opts.templates = ret;
+};
+
module.exports.cli = function(opts) {
if (opts.version) {
console.log(Handlebars.VERSION);
return;
}
- if (!opts.templates.length) {
+ if (!opts.templates.length && !opts.hasDirectory) {
throw new Handlebars.Exception('Must define at least one template or directory.');
}
- opts.templates.forEach(function(template) {
- try {
- fs.statSync(template);
- } catch (err) {
- throw new Handlebars.Exception(`Unable to open template file "${template}"`);
- }
- });
-
if (opts.simple && opts.min) {
throw new Handlebars.Exception('Unable to minimize simple output');
}
- if (opts.simple && (opts.templates.length !== 1 || fs.statSync(opts.templates[0]).isDirectory())) {
+ if (opts.simple && (opts.templates.length !== 1 || opts.hasDirectory)) {
throw new Handlebars.Exception('Unable to output multiple templates in simple mode');
}
@@ -41,10 +86,6 @@ module.exports.cli = function(opts) {
}
}
- // Build file extension pattern
- let extension = opts.extension.replace(/[\\^$*+?.():=!|{}\-\[\]]/g, function(arg) { return '\\' + arg; });
- extension = new RegExp('\\.' + extension + '$');
-
let output = new SourceNode();
if (!opts.simple) {
if (opts.amd) {
@@ -63,76 +104,47 @@ module.exports.cli = function(opts) {
}
output.add('{};\n');
}
- function processTemplate(template, root) {
- let path = template,
- stat = fs.statSync(path);
- if (stat.isDirectory()) {
- fs.readdirSync(template).map(function(file) {
- let childPath = template + '/' + file;
- if (extension.test(childPath) || fs.statSync(childPath).isDirectory()) {
- processTemplate(childPath, root || template);
- }
- });
- } else {
- let data = fs.readFileSync(path, 'utf8');
-
- if (opts.bom && data.indexOf('\uFEFF') === 0) {
- data = data.substring(1);
- }
-
- let options = {
- knownHelpers: known,
- knownHelpersOnly: opts.o
- };
+ opts.templates.forEach(function(template) {
+ let options = {
+ knownHelpers: known,
+ knownHelpersOnly: opts.o
+ };
- if (opts.map) {
- options.srcName = path;
- }
- if (opts.data) {
- options.data = true;
- }
+ if (opts.map) {
+ options.srcName = template.path;
+ }
+ if (opts.data) {
+ options.data = true;
+ }
- // Clean the template name
- if (!root) {
- template = basename(template);
- } else if (template.indexOf(root) === 0) {
- template = template.substring(root.length + 1);
- }
- template = template.replace(extension, '');
+ let precompiled = Handlebars.precompile(template.source, options);
- let precompiled = Handlebars.precompile(data, options);
+ // If we are generating a source map, we have to reconstruct the SourceNode object
+ if (opts.map) {
+ let consumer = new SourceMapConsumer(precompiled.map);
+ precompiled = SourceNode.fromStringWithSourceMap(precompiled.code, consumer);
+ }
- // If we are generating a source map, we have to reconstruct the SourceNode object
- if (opts.map) {
- let consumer = new SourceMapConsumer(precompiled.map);
- precompiled = SourceNode.fromStringWithSourceMap(precompiled.code, consumer);
+ if (opts.simple) {
+ output.add([precompiled, '\n']);
+ } else if (opts.partial) {
+ if (opts.amd && (opts.templates.length == 1 && !opts.hasDirectory)) {
+ output.add('return ');
}
-
- if (opts.simple) {
- output.add([precompiled, '\n']);
- } else if (opts.partial) {
- if (opts.amd && (opts.templates.length == 1 && !fs.statSync(opts.templates[0]).isDirectory())) {
- output.add('return ');
- }
- output.add(['Handlebars.partials[\'', template, '\'] = template(', precompiled, ');\n']);
- } else {
- if (opts.amd && (opts.templates.length == 1 && !fs.statSync(opts.templates[0]).isDirectory())) {
- output.add('return ');
- }
- output.add(['templates[\'', template, '\'] = template(', precompiled, ');\n']);
+ output.add(['Handlebars.partials[\'', template.name, '\'] = template(', precompiled, ');\n']);
+ } else {
+ if (opts.amd && (opts.templates.length == 1 && !opts.hasDirectory)) {
+ output.add('return ');
}
+ output.add(['templates[\'', template.name, '\'] = template(', precompiled, ');\n']);
}
- }
-
- opts.templates.forEach(function(template) {
- processTemplate(template, opts.root);
});
// Output the content
if (!opts.simple) {
if (opts.amd) {
- if (opts.templates.length > 1 || (opts.templates.length == 1 && fs.statSync(opts.templates[0]).isDirectory())) {
+ if (opts.templates.length > 1 || (opts.templates.length == 1 && opts.hasDirectory)) {
if (opts.partial) {
output.add('return Handlebars.partials;\n');
} else {