Add base for plugin JS api

This commit is contained in:
Samy Pesse
2016-04-26 17:02:59 +02:00
parent 7a46d3b497
commit 8bac111acf
13 changed files with 228 additions and 32 deletions
+15
View File
@@ -0,0 +1,15 @@
var Config = require('../models/config');
/**
Decode changes from a JS API to a config object
@param {Config} config
@param {Object} result: result from API
@return {Config}
*/
function decodeGlobal(config, result) {
var values = result.values;
return Config.updateValues(config, values);
}
module.exports = decodeGlobal;
+21
View File
@@ -0,0 +1,21 @@
var decodeConfig = require('./decodeConfig');
/**
Decode changes from a JS API to a output object
@param {Output} output
@param {Object} result: result from API
@return {Output}
*/
function decodeGlobal(output, result) {
var book = output.getBook();
var config = book.getConfig();
// Update config
config = decodeConfig(config, result.config);
book = book.set('config', config);
return output.set('book', book);
}
module.exports = decodeGlobal;
+5 -5
View File
@@ -1,15 +1,15 @@
/**
Decode changes from a JS API to a page boject
Decode changes from a JS API to a page object
@param {Output} output
@param {Page} page
@param {Object} result
@param {Page} page: page instance to edit
@param {Object} result: result from API
@return {Page}
*/
function decodePage(output, page, result) {
// todo
return page;
}
module.exports = decodePage;
+67
View File
@@ -0,0 +1,67 @@
var logged = {};
/**
Log a deprecated notice
@param {Book|Output} book
@param {String} key
@param {String} message
*/
function logNotice(book, key, message) {
if (logged[key]) return;
logged[key] = true;
var logger = book.getLogger();
logger.warn.ln(message);
}
/**
Deprecate a function
@param {Book|Output} book
@param {String} key: unique identitifer for the deprecated
@param {Function} fn
@param {String} msg: message to print when called
@return {Function}
*/
function deprecateMethod(book, key, fn, msg) {
return function() {
logNotice(book, key, msg);
return fn.apply(this, arguments);
};
}
/**
Deprecate a property of an object
@param {Book|Output} book
@param {String} key: unique identitifer for the deprecated
@param {Object} instance
@param {String} property
@param {String} msg: message to print when called
@return {Function}
*/
function deprecateField(book, key, instance, property, value, msg) {
var getter = function(){
logNotice(book, key, msg);
return value;
};
var setter = function(v) {
logNotice(book, key, msg);
value = v;
return value;
};
Object.defineProperty(instance, property, {
get: getter,
set: setter,
enumerable: true
});
}
module.exports = {
method: deprecateMethod,
field: deprecateField
};
+30
View File
@@ -0,0 +1,30 @@
var objectPath = require('object-path');
var deprecate = require('./deprecate');
/**
Encode a config object into a JS config api
@param {Output} output
@param {Config} config
@return {Object}
*/
function encodeConfig(output, config) {
var result = {
values: config.getValues().toJS(),
get: function(key, defaultValue) {
return objectPath.get(result.values, key, defaultValue);
},
set: function(key, value) {
return objectPath.set(result.values, key, value);
}
};
deprecate.field(output, 'config.options', result, 'options',
result.values, '"config.options" property is deprecated, use "config.get(key)" instead');
return result;
}
module.exports = encodeConfig;
+46
View File
@@ -0,0 +1,46 @@
var path = require('path');
var fs = require('../utils/fs');
var deprecate = require('./deprecate');
var encodeConfig = require('./encodeConfig');
/**
Encode a global context into a JS object
It's the context for page's hook, etc
@param {Output} output
@return {Object}
*/
function encodeGlobal(output) {
var book = output.getBook();
var logger = output.getLogger();
var outputFolder = output.getOptions().get('root');
var result = {
log: logger,
config: encodeConfig(output, book.getConfig())
};
result.output = {
name: 'website',
toURL: function(s) {
return s;
},
writeFile: function(fileName, content) {
var filePath = path.join(outputFolder, fileName);
return fs.writeFile(filePath, content);
}
};
result.isLanguageBook = function() {
return false;
};
return result;
}
module.exports = encodeGlobal;
+20
View File
@@ -1,3 +1,5 @@
var JSONUtils = require('../json');
var deprecate = require('./deprecate');
/**
Encode a page in a context to a JS API
@@ -7,8 +9,26 @@
@return {Object}
*/
function encodePage(output, page) {
var book = output.getBook();
var summary = book.getSummary();
var fs = book.getContentFS();
var file = page.getFile();
// JS Page is based on the JSON output
var result = JSONUtils.encodePage(page, summary);
result.type = file.getType();
result.path = file.getPath();
result.rawPath = fs.resolve(result.path);
deprecate.field(output, 'page.section', result, 'sections', [
{
content: result.content,
type: 'normal'
}
], '"sections" property is deprecated, use page.content instead');
return result;
}
module.exports = encodePage;
+4 -1
View File
@@ -1,5 +1,8 @@
module.exports = {
encodePage: require('./encodePage'),
decodePage: require('./decodePage')
decodePage: require('./decodePage'),
encodeGlobal: require('./encodeGlobal'),
decodeGlobal: require('./decodeGlobal')
};
+11 -1
View File
@@ -1,4 +1,5 @@
var Promise = require('../utils/promise');
var Api = require('../api');
function defaultGetArgument() {
return undefined;
@@ -26,7 +27,13 @@ function callHook(name, getArgument, handleResult, output) {
logger.debug.ln('calling hook "' + name + '"');
// Create the JS context for plugins
var context = Api.encodeGlobal(output);
// Get the arguments
return Promise(getArgument(output))
// Call the hooks in serie
.then(function(arg) {
return Promise.reduce(plugins, function(prev, plugin) {
var hook = plugin.getHook(name);
@@ -34,10 +41,13 @@ function callHook(name, getArgument, handleResult, output) {
return prev;
}
return hook(prev);
return hook.call(context, prev);
}, arg);
})
// Handle final result
.then(function(result) {
output = Api.decodeGlobal(output, context);
return handleResult(output, result);
});
}
+2 -4
View File
@@ -12,9 +12,7 @@ var Promise = require('../utils/promise');
@return {Promise<Page>}
*/
function callPageHook(name, output, page) {
return Promise(page);
/*return callHook(
return callHook(
name,
function(out) {
@@ -26,7 +24,7 @@ function callPageHook(name, output, page) {
},
output
);*/
);
}
module.exports = callPageHook;
+2 -2
View File
@@ -105,7 +105,7 @@ function generateBook(generator, book, options) {
return generator.onFinish(output);
})
/*.then(callHook.bind(null,
.then(callHook.bind(null,
'finish',
function(output) {
return {};
@@ -114,7 +114,7 @@ function generateBook(generator, book, options) {
return output;
}
)
)*/
)
.then(function(output) {
var logger = output.getLogger();
+4 -18
View File
@@ -1,15 +1,12 @@
var _ = require('lodash');
var is = require('is');
var TypedError = require('error/typed');
var WrappedError = require('error/wrapped');
var deprecated = require('deprecated');
var Logger = require('./logger');
var log = new Logger();
// Enforce as an Error object, and cleanup message
function enforce(err) {
if (_.isString(err)) err = new Error(err);
if (is.string(err)) err = new Error(err);
err.message = err.message.replace(/^Error: /, '');
return err;
@@ -84,14 +81,6 @@ var EbookError = WrappedError({
stdout: ''
});
// Deprecate methods/fields
function deprecateMethod(fn, msg) {
return deprecated.method(msg, log.warn.ln, fn);
}
function deprecateField(obj, prop, value, msg) {
return deprecated.field(msg, log.warn.ln, obj, prop, value);
}
module.exports = {
enforce: enforce,
@@ -106,8 +95,5 @@ module.exports = {
TemplateError: TemplateError,
PluginError: PluginError,
ConfigurationError: ConfigurationError,
EbookError: EbookError,
deprecateMethod: deprecateMethod,
deprecateField: deprecateField
EbookError: EbookError
};
+1 -1
View File
@@ -11,7 +11,6 @@
"cp": "0.2.0",
"cpr": "1.1.1",
"crc": "3.4.0",
"deprecated": "0.0.1",
"destroy": "1.0.4",
"direction": "0.1.5",
"dom-serializer": "0.1.0",
@@ -46,6 +45,7 @@
"npmi": "1.0.1",
"nunjucks": "2.4.1",
"nunjucks-do": "1.0.0",
"object-path": "^0.9.2",
"q": "1.4.1",
"read-installed": "^4.0.3",
"request": "2.70.0",