summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorSamy Pessé <samypesse@gmail.com>2015-01-27 15:22:42 +0100
committerSamy Pessé <samypesse@gmail.com>2015-01-27 15:22:42 +0100
commit131c19dee6db956d758ed4a63ee24dbf087a8c7f (patch)
tree9b31f135fb12a105f395f298b7468962559778df
parent870ca4da0c9fa750acba609aff8d129d5a753466 (diff)
downloadgitbook-131c19dee6db956d758ed4a63ee24dbf087a8c7f.zip
gitbook-131c19dee6db956d758ed4a63ee24dbf087a8c7f.tar.gz
gitbook-131c19dee6db956d758ed4a63ee24dbf087a8c7f.tar.bz2
Move plugin helper methods to a specific class
-rw-r--r--lib/book.js36
-rw-r--r--lib/plugin.js109
-rw-r--r--lib/pluginslist.js117
-rw-r--r--lib/template.js17
4 files changed, 140 insertions, 139 deletions
diff --git a/lib/book.js b/lib/book.js
index 9795bc8..d1c7ece 100644
--- a/lib/book.js
+++ b/lib/book.js
@@ -16,10 +16,13 @@ var logger = require("./utils/logger");
var Configuration = require("./configuration");
var TemplateEngine = require("./template");
var Plugin = require("./plugin");
+var PluginsList = require("./pluginslist");
var generators = require("./generators");
var Book = function(root, context, parent) {
+ var that = this;
+
this.context = _.defaults(context || {}, {
// Extend book configuration
config: {},
@@ -70,7 +73,7 @@ var Book = function(root, context, parent) {
this.files = [];
// List of plugins
- this.plugins = {};
+ this.plugins = new PluginsList(this);
// Structure files
this.summaryFile = null;
@@ -85,6 +88,9 @@ var Book = function(root, context, parent) {
this.field('title', { boost: 10 });
this.field('body');
});
+
+ // Bind methods
+ _.bindAll(this);
};
Book.LOG_LEVELS = {
@@ -327,30 +333,12 @@ Book.prototype.parsePlugins = function() {
var failed = [];
// Load plugins
- var pluginsList = _.map(that.options.plugins, function(plugin) {
- var plugin = new Plugin(that, plugin.name);
- that.log.info("load plugin", plugin.name, "....");
-
- if (!plugin.isValid()) {
- that.log.info.fail();
- failed.push(plugin.name);
- } else {
- that.log.info.ok();
- }
- return plugin;
- });
-
- if (_.size(failed) > 0) return Q.reject(new Error("Error loading plugins: "+failed.join(",")+". Run 'gitbook install' to install plugins from NPM."));
-
- that.log.info.ok(that.plugins.length+" plugins loaded");
- that.log.debug.ln("normalize plugins list");
-
- return Plugin.normalize(pluginsList)
- .then(function(_plugins) {
- that.plugins = _plugins;
+ return that.plugins.load(that.options.plugins)
+ .then(function() {
+ if (_.size(that.plugins.failed) > 0) return Q.reject(new Error("Error loading plugins: "+that.plugins.failed.join(",")+". Run 'gitbook install' to install plugins from NPM."));
- // Add filters
- that.template.addFilters(that.plugins.filters);
+ that.log.info.ok(that.plugins.length+" plugins loaded");
+ that.log.debug.ln("normalize plugins list");
});
};
diff --git a/lib/plugin.js b/lib/plugin.js
index ec55513..fa38e20 100644
--- a/lib/plugin.js
+++ b/lib/plugin.js
@@ -196,113 +196,4 @@ Plugin.prototype.copyAssets = function(out, options) {
}, _.constant(false));
};
-
-// Extract data from a list of plugin
-Plugin.normalize = function(plugins, options) {
- options = _.defaults(options || {}, {
- assetsBase: "book"
- });
-
- // The raw resources extracted from each plugin
- var pluginResources;
-
- // Map of resources
- var resources = {};
-
- // Map of all filters
- var filters = {};
-
- // Get resources of plugins
- return Q.all(_.map(plugins, function(plugin) {
- return plugin.getResources(options.assetsBase);
- }))
-
- // Extract resources out
- // css, js, etc ...
- .then(function(_resources) {
- pluginResources = _resources;
- })
- .then(function() {
- // Group by resource types
- resources = _.chain(Plugin.RESOURCES)
- .map(function(resourceType) {
- // Get resources from all the plugins for this current type
- return [
- // Key
- resourceType,
-
- // Value
- _.chain(pluginResources)
- .pluck(resourceType)
- .compact()
- .flatten()
- .value()
- ];
- })
- .object()
- .value();
- })
-
- // Extract html snippets
- .then(function() {
- // Map of html resources by name added by each plugin
- resources.html = pluginResources.reduce(function(accu, resource) {
- var html = (resource && resource.html) || {};
- _.each(html, function(code, key) {
- // Turn into function if not one already
- if (!_.isFunction(code)) code = _.constant(code);
- // Append
- accu[key] = (accu[key] || []).concat([code]);
- });
-
- return accu;
- }, {});
- })
-
- // Extract filters
- .then(function() {
- _.each(plugins, function(plugin) {
- _.each(plugin.getFilters(), function(filterFunc, filterName) {
- if (filters[filterName]) {
- plugin.book.log.warn.ln("Conflict in filters, '"+filterName+"' is already set");
- } else {
- filters[filterName] = filterFunc;
- }
- });
- });
- })
-
- // Return big multi-plugins object
- .then(function() {
- return {
- 'list': plugins,
- 'resources': resources,
- 'filters': filters,
- 'hook': function(name, data) {
- return _.reduce(plugins, function(prev, plugin) {
- return prev.then(function(ret) {
- return plugin.callHook(name, ret);
- });
- }, Q(data));
- },
- 'template': function(name) {
- var withTpl = _.find(plugins, function(plugin) {
- return (
- plugin.infos.templates &&
- plugin.infos.templates[name]
- );
- });
-
- if (!withTpl) return null;
- return withTpl.resolveFile(withTpl.infos.templates[name]);
- },
- 'html': function(tag, context, options) {
- return _.map(resources.html[tag] || [], function(code) {
- return code.call(context, options);
- }).join("\n");
- }
- };
- });
-};
-
module.exports = Plugin;
diff --git a/lib/pluginslist.js b/lib/pluginslist.js
new file mode 100644
index 0000000..d1d276d
--- /dev/null
+++ b/lib/pluginslist.js
@@ -0,0 +1,117 @@
+var _ = require("lodash");
+var Q = require("q");
+
+var Plugin = require("./plugin");
+
+var PluginsList = function(book, plugins) {
+ this.book = book;
+ this.log = this.book.log;
+
+ // List of Plugin objects
+ this.plugins = [];
+
+ // List of names of failed plugins
+ this.failed = [];
+
+ // List of plugins resources
+ this.resources = {};
+ _.each(Plugin.RESOURCES, function(resourceType) {
+ this.resources[resourceType] = [];
+ }, this);
+
+ // Map of html snippets
+ this.htmlSnippets = {};
+
+ // Bind methods
+ _.bindAll(this);
+
+ if (plugins) this.load(plugins);
+};
+
+// Add and load a plugin
+PluginsList.prototype.load = function(plugin, options) {
+ var that = this;
+ options = _.defaults(options || {}, {
+ assetsBase: "book"
+ });
+
+ if (_.isArray(plugin)) {
+ return _.reduce(plugin, function(prev, p) {
+ prev.then(function() {
+ return that.load(p);
+ });
+ }, Q());
+ }
+ if (_.isString(plugin)) {
+ plugin = new Plugin(this.book, plugin);
+ }
+
+ that.log.info("load plugin", plugin.name, "....");
+ if (!plugin.isValid()) {
+ that.log.info.fail();
+ that.failed.push(plugin.name);
+ return;
+ } else {
+ that.log.info.ok();
+
+ // Push in the list
+ that.plugins.push(plugin);
+ }
+
+ // Extract filters
+ _.each(plugin.getFilters(), function(filterFunc, filterName) {
+ that.book.template.addFilter(filterName, filterFunc);
+ });
+
+ return Q()
+ .then(function() {
+ return plugin.getResources(options.assetsBase);
+ })
+
+ .then(function(plResources) {
+ // Extract js and css
+ _.each(Plugin.RESOURCES, function(resourceType) {
+ that.resources[resourceType].concat(plResources[resourceType] || []);
+ });
+
+ // Map of html resources by name added by each plugin
+ _.each(plResources.html || {}, function(value, tag) {
+ // Turn into function if not one already
+ if (!_.isFunction(value)) value = _.constant(value);
+
+ that.htmlSnippets[tag] = that.htmlSnippets[tag] || [];
+ that.htmlSnippets[tag].push(value);
+ });
+ });
+};
+
+// Call a hook
+PluginsList.prototype.hook = function(name, data) {
+ return _.reduce(this.plugins, function(prev, plugin) {
+ return prev.then(function(ret) {
+ return plugin.callHook(name, ret);
+ });
+ }, Q(data));
+};
+
+// Return a template from a plugin
+PluginsList.prototype.template = function(name) {
+ var withTpl = _.find(this.plugins, function(plugin) {
+ return (
+ plugin.infos.templates &&
+ plugin.infos.templates[name]
+ );
+ });
+
+ if (!withTpl) return null;
+ return withTpl.resolveFile(withTpl.infos.templates[name]);
+};
+
+// Return an html snippet
+PluginsList.prototype.html = function(tag, context, options) {
+ return _.map(this.htmlSnippets[tag] || [], function(code) {
+ return code.call(context, options);
+ }).join("\n");
+};
+
+module.exports = PluginsList;
diff --git a/lib/template.js b/lib/template.js
index 32c46de..69a1bd5 100644
--- a/lib/template.js
+++ b/lib/template.js
@@ -45,6 +45,7 @@ var BookLoader = nunjucks.Loader.extend({
var TemplateEngine = function(book) {
this.book = book;
+ this.log = this.book.log;
// Nunjucks env
this.env = new nunjucks.Environment(
@@ -66,12 +67,16 @@ var TemplateEngine = function(book) {
);
};
-// Add filters
-TemplateEngine.prototype.addFilters = function(filters) {
- _.each(filters, function(func, key) {
- this.book.log.debug.ln("add filter '"+key+"'");
- this.env.addFilter(key, func);
- }, this);
+
+// Add filter
+TemplateEngine.prototype.addFilter = function(key, filter) {
+ if (this.env.getFilter(filterName)) {
+ this.log.warn.ln("conflict in filters, '"+filterName+"' is already set");
+ return false;
+ }
+ this.log.debug.ln("add filter '"+key+"'");
+ this.env.addFilter(key, func, true);
+ return true;
};
// Render a string from the book