Templating the World - Confession 21

2014.07.31 19:59:40

image I have yet to find a single templating system I like, and I've even written my own. Multiple times. Yet, every time I do and every time I look at an existing one, there's just always so many things that bother me and I have yet to figure out a system that I might even begin to like.

One of the major gripes I have with a lot of them is that they mix their own completely different, strange and extremely dumbed-down language into the mix with HTML. This has several glaring disadvantages, the main two being that since it is very featureless you're very limited in what you can do, but also because there is now a different language in there the browser won't be able to display the document properly anymore, which means you can't actually look at the template in any way without either stripping it of code or putting something in it.

Some systems avoid this extra-language kludge by putting all transformations into code somewhere else (e.g. lQuery, HTML-generators). This is already much better, but in the case of lQuery-like systems it means you now have two places with intricate knowledge about the template, the HTML itself and the code that transforms it. In the case of HTML-generators the issue is that now everything is code, so you can't look at it anymore without generating it and it is completely unsuitable for quick designing.

Another approach is to add special HTML tags and attributes that are recognised by an engine that then performs transformations accordingly. This allows you to mix in template code with HTML without making it unable to be loaded by a browser directly. However, unlike the HTML-generators this shares a problem with the other template systems in that there needs to be a way to reference, indicate or access data in the template. Figuring out a way to keep a good symbiosis between HTML and your template engine too is a major issue here.

Out of all the systems I've encountered I prefer the last best as it seems to offer the possibility of a good compromise. However, the issues that remain are still rather bothersome. Template systems should at the same time be expressive and short-handed enough for you to write what you need with ease, but they also shouldn't be too complex so that they can still be compiled with speed and that the templates don't become just another DSL.

In my latest iteration of this arduous endeavour I've finally gotten to working on Clip. Clip's main idea is that any tag and attribute can potentially serve as a way to trigger a template engine action. This allows the structure to look ‘innocent’ and expressive. Another main feature is the integration with lQuery (through an lquery attribute) which allows complex, but simple transforming of elements and filling in of data. Clip uses a central ‘clipboard’ that serves as a data storage. Tags can rebind this clipboard to other objects or modify it and values can be retrieved from it in most cases as if by a locally-bound symbol. Finally, any tag can control the transformation process, so flow- and environment-changing tag ‘macros’ are possible too.

Let's look at an example. As you can see, this is displayed like a normal web page. View its source to see the template definition. This is a very small thing that basically only does one thing: Populate the list with voting options. Important here are the ITERATE and LQUERY attributes. The iterate attribute tells Clip to call the iterate transformer, which then copies the first inner element and transforms it for each element in the named variable. In this case, the variable storing the options must be a list retrievable through a call to CLIP (a generic accessor) from the clipboard. Values for the lquery calls are similarly retrieved. As you can see, it looks like locally bound variables, which is a nice aesthetic effect. In the case of the lquery attribute you can put in complicated lisp snippets that are then evaluated to retrieve the proper value. This allows for a very flexible environment. Since Clip is extensible you can also add your own special tags and attributes to ease the template parsing.

Once I get more time I'll root out my main irks (how attributes are processed, no splicing) with Clip so it can become a fully-fledged templating system. For now it's used in Staple, my new documentation generation app that I've had a long time coming. Now I can finally replace lQuery-Doc!

Anyway, this blog seems a lot less coherent in thought than I'd like and that's mainly down to the fact that I'm still very much a confused man myself. I don't know how to write a template system that I would truly find appealing and everything I've written for Clip and Staple today is still bugging me. I desperately hope someone out there has a better idea about all of this than I and is going to or already has written something that I would want to use as well.

But I'm not going to bet on it.

Written by shinmera