dbelyaeff / cogear.js

Modern static websites generator (Node.JS/Webpack)

Home Page:https://cogearjs.org

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

Adding support to additional template engines

webberig opened this issue · comments

Hi,

I'd like to use the Twig.js engine to render templates in a cogear project. Even though Cogear's plugin support is pretty powerful, I feel it's lacking support for rendering pages with a different template engine.

I did manage to get it working though, this is my plugin:

const Twig = require("twig");

module.exports = {
	apply() {
		cogear.on("webpack.config", () => {
			cogear.pageFormats.push("twig");
		});
		cogear.on("parse.after", data => {
			if (data.vars.format !== ".twig") {
				return data;
			}
			return new Promise((resolve, reject) => {
				data.vars.path = data.vars.path.replace(".twig/index", "");
				data.vars.uri = data.vars.uri.replace(".twig/", ".html");
				Twig.renderFile(data.vars.filePath, data.vars, (err, html) => {
					if (err) {
						console.error(err);
						return reject(err);
					}
					data.parsedContent = html;
					resolve()
				});
			})
		});
	}
};

Some parts feel a bit "hacky", specifically:

  1. cogear.pageFormats.push only worked in the webpack.config event, which feels like I'm using the event for the wrong reason. preload didn't cut it because my plugin's handler is fired after the internal preload plugin creates the files array here

  2. parse.after also feels wrong for the same reason mentioned above.

  3. Having the template go through the "default" engine here seems to be unavoidable. I fear this may cause exceptions in some scenarios if the twig syntax collides with EJS.

  4. I had to transform data.vars.path and data.vars.uri to have the page rendered on a proper location instead of page.twig/index.html. I didn't figure out how this works internally, so I don't know this can be done better.

Some possible solutions I had in mind:

  • put cogear.formatOptions in configuration
  • Find a way to let the parser bypass the default template engines so a plugin can handle the rendering. Maybe introduce a render event and check if data.parsedContent has been set ?

I'd like to contribute code to Cogear itself to improve support for what I'm trying to do, but I could use some feedback before making changes that might get rejected.

Hope to hear from you!

Hi, Mathieu!

Greatly appreciate your interest.

I've some thoughts about that.

  1. I think it will be better to merge preload && built processes, but to replace standalone WebPack with Laravel Mix which is a simple Webpack configurator.

To include Laravel Mix into core and make it callable via plugins (to pipeline assets).

  1. That is the place where we can simplify the whole rendering process.

But I need to test whether Webpack can run via Laravel Mix config from Express process or it's needed to be run in parallel. In Rails, for example, there are some supervisors like Foreman or Overmind which allow to run a few processes in parallel via configuration given with Procfile.

Have you heard about something similar for Node?

I think to make any template language available core is needed to be rewritten up to v2.0.