Remember that AkashaCMS is a generalized name for the synergistic combination of AkashaRender with the plugins. In this section we'll look into coding a Plugin. Plugins provide useful extensions to AkashaRender, and what makes AkashaCMS is the combination of AkashaRender, Mahabhuta, and the plugins.
It is not required to register a plugin with anyone. As we saw in the documentation on using plugins, a project uses a plugin by declaring it in the package.json
and Configuration. No centralized registry is required.
Anyone who has developed a generally useful Plugin may register it on the list of known plugins. We can even arrange for the plugin documentation to appear on the AkashaCMS website.
Inside AkashaRender the Plugin object is used to encapsulate information about each Plugin. It is a simple object with two methods:
configure
is called when the Plugin is added to the Configuration by calling config.use()
name
returns the name of the Plugin, and is used when searching for the Plugin instanceoptions
returns the options object passed when configuring the PluginA given Plugin is free to implement other functions as well. Those functions can be called by any code as so:
config.plugin("plugin-name").functionName(parameter, list);
The typical implementation of a Plugin is to create a Node.js package that returns the Plugin object. To see what that means let's walk through the akashacms-base
plugin (
https://github.com/akashacms/akashacms-base).
The package contains a package.json
and an index.js
as is typical of a Node.js package.
The package.json
declares information required for npm such as the package name, its repository, any scripts, and most importantly the dependencies. Often a Plugin will other Node.js packages to do the heavy lifting. For example the akashacms-embeddables
Plugin uses other packages providing OEmbed-based query for metadata and embed codes of content on other websites.
The index.js
contains at the minimum the Plugin object, which it exports using the module.exports
object. A minimal index.js
might be:
const path = require('path');
const util = require('util');
const url = require('url');
const akasha = require('akasharender');
const mahabhuta = akasha.mahabhuta;
const pluginName = "akashacms-base";
const _plugin_config = Symbol('config');
const _plugin_options = Symbol('options');
module.exports = class BasePlugin extends akasha.Plugin {
constructor() {
super(pluginName);
}
configure(config, options) {
this[_plugin_config] = config;
this[_plugin_options] = options;
options.config = config;
config.addPartialsDir(path.join(__dirname, 'partials'));
config.addLayoutsDir(path.join(__dirname, 'layout'));
config.addAssetsDir(path.join(__dirname, 'assets'));
config.addMahabhuta(module.exports.mahabhutaArray(options));
}
get config() { return this[_plugin_config]; }
get options() { return this[_plugin_options]; }
}
When config.use(require("plugin-name"), { options })
is called this sequence occurs:
use
function receives this objectnew PluginObj()
)configure
function is calledThe configure
function shown here is fairly typical. It uses functions we've already seen to add Plugin-provided directories of assets or partials and an array of Mahabhuta functions. It could call other functions to add JavaScript, CSS and other things.
As shown here the options
object is available from the Plugin, and is passed while constructing the MahafuncArray so that it is available to Mahafuncs.
For akashacms-base
partials, see
https://github.com/akashacms/akashacms-base/partials
The purpose of this plugin is functionality useful for all websites, and the Partials it provides match that purpose.
Partials should endeavor to use CSS classes so website authors can easily customize the look of the partial
See https://github.com/akashacms/akashacms-base/assets/img
A useful naming convention is to store assets in: /vendor/plugin-name/asset.file
See the Mahabhuta documentation to see how to write Mahafuncs: https://akashacms.com/mahabhuta/toc.html
To see how Mahabhuta is used in AkashaCMS projects, it's useful to study some source code:
In each case, the Plugin configure
method contains a line of code similar to:
config.addMahabhuta(... MahafuncArray ...);
As we showed earlier this MahafuncArray is initialized by calling a function, passing along the options object. That function should look like so:
module.exports.mahabhutaArray = function(options) {
let ret = new mahabhuta.MahafuncArray(pluginName, options);
...
ret.addMahafunc(new MahafuncElementClass());
...
return ret;
};
And from there start adding Mahafunc instance's to the MahafuncArray.
In a website config.js
the steps are similar. For example:
config.addMahabhuta(require('./mahafuncs'));
Then in mahafuncs.js
you create a MahafuncArray
module.exports = new mahabhuta.MahafuncArray("techsparx website", {});
And start filling it with Mahafunc's.
Store any data in the options object.