<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>Three of Coins &#187; ucw</title>
	<atom:link href="http://www.3ofcoins.net/tag/ucw/feed/" rel="self" type="application/rss+xml" />
	<link>http://www.3ofcoins.net</link>
	<description>Just another WordPress weblog</description>
	<lastBuildDate>Thu, 21 Jan 2010 14:01:34 +0000</lastBuildDate>
	<generator>http://wordpress.org/?v=2.9.1</generator>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
			<item>
		<title>Yaclml in pictures, part I: HTML generation</title>
		<link>http://www.3ofcoins.net/2009/02/07/yaclml-in-pictures-part-i-html-generation/</link>
		<comments>http://www.3ofcoins.net/2009/02/07/yaclml-in-pictures-part-i-html-generation/#comments</comments>
		<pubDate>Sat, 07 Feb 2009 20:41:04 +0000</pubDate>
		<dc:creator>Maciej</dc:creator>
				<category><![CDATA[Uncategorized]]></category>
		<category><![CDATA[bese]]></category>
		<category><![CDATA[cl-who]]></category>
		<category><![CDATA[ediware]]></category>
		<category><![CDATA[html]]></category>
		<category><![CDATA[html-template]]></category>
		<category><![CDATA[lisp]]></category>
		<category><![CDATA[ucw]]></category>
		<category><![CDATA[yaclml]]></category>

		<guid isPermaLink="false">http://www.3ofcoins.net/?p=49</guid>
		<description><![CDATA[Everyone and their dog loves Edi Weitz&#8217;s Lisp software (unless they don&#8217;t use Lisp, that is).  Not without reason—Edi&#8217;s libraries are solid, well-designed and robust pieces of software.  CL-PPCRE is unbeatable (it parses Perl&#8217;s regular expressions faster than Perl, when properly compiled, and is more compatible with Perl 5.8 than Perl 5.8 is with Perl [...]]]></description>
			<content:encoded><![CDATA[<p>Everyone and their dog loves <a href="http://www.weitz.de/">Edi Weitz&#8217;s Lisp software</a> (unless they don&#8217;t use Lisp, that is).  Not without reason—Edi&#8217;s libraries are solid, well-designed and robust pieces of software.  <a href="http://www.weitz.de/cl-ppcre/">CL-PPCRE</a> is unbeatable (it parses Perl&#8217;s regular expressions faster than Perl, when properly compiled, and is more compatible with Perl 5.8 than Perl 5.8 is with Perl 5.6), and <a href="http://www.weitz.de/hunchentoot/">Hunchentoot</a> seems to be the best and most hassle-free HTTP server library available for Lisp.  Hunchentoot is also most popular server, and many people using it, automatically use Edi&#8217;s <a href="http://www.weitz.de/cl-who/">CL-WHO</a> for HTML output, and <a href="http://www.weitz.de/html-template/">HTML-Template</a> for templating, which—I think—are not the best libraries available for this, and I will explain now, why.</p>
<p>I worked for about a year on an <a href="http://common-lisp.net/project/ucw/">UnCommon Web</a>-based application.  This was an interesting experience; <abbr title="UnCommon Web">UCW</abbr> provides a great way to express complex behaviour in a Web application, as it is <a href="http://en.wikipedia.org/wiki/Continuation">continuation</a>-based, which enabled me to code app&#8217;s logic as regular control flow, complete with looping, conditions, etc., from time to time presenting user a form and receiving user-supplied values (form presentation was as simple as calling out to a function, which returned values supplied by user).  Cool, huh?  Currently, <abbr title="UnCommon Web">UCW</abbr> seems to be mostly a dead project, and there is an alternative, which may be more interesting—namely, <a href="http://common-lisp.net/project/cl-weblocks/">Weblocks</a>—but I didn&#8217;t check that out yet.  What&#8217;s more, <abbr title="UnCommon Web">UCW</abbr>, with all its complexity, had very little documentation, and what was avalilable, was mostly outdated, as the framework was constantly evolving at that time.  Not so cool, but it forced me to learn to <acronym title="Read The Fine Source">RTFS</acronym> when needed (with <a href="http://common-lisp.net/project/slime/">Slime</a>&#8217;s <code>M-.</code> it was not as hard as it seems).  But I digress; <abbr title="UnCommon Web">UCW</abbr> made use of some other projects of Bese (<abbr title="UnCommon Web">UCW</abbr> developers seemed to have quite a bad case of <abbr title="Not Invented Here">NIH</abbr>), including HTML output and templating library <a href="http://common-lisp.net/project/bese/yaclml.html">Yaclml</a>—Yet Another Common Lisp Markup Language—which I really loved, and which, in my opinion, surpasses CL-WHO + HTML-Template in many ways.  Unfortunately it is almost undocumented, which is what I&#8217;ll try to fix in this article, along with comparing Yaclml to its Ediware counterparts.<span id="more-49"></span></p>
<h2>Formatting HTML output</h2>
<p>Edi, when designing CL-WHO, decided to use keyword symbols to represent HTML tags; Bese guys decided to create separate package for tags—<code>it.bese.yaclml.tags</code>, conveniently nicknamed <code>&lt;</code>.  Let&#8217;s compare a simple example code:</p>
<pre style="color: #000000; background-color: #EAF0F0;"><span style="color: #008b8b;">;; </span><span style="color: #008b8b;">CL-WHO
</span>(<span style="color: #551a8b;">with-html-output-to-string</span> (s)
  (<span style="color: #b03060;">:ul</span> (<span style="color: #b03060;">:li</span> <span style="color: #4d4d4d;">"foo"</span>)
       (<span style="color: #b03060;">:li</span> <span style="color: #4d4d4d;">"bar"</span>)))

<span style="color: #008b8b;">;; </span><span style="color: #008b8b;">Yaclml
</span>(<span style="color: #551a8b;">with-yaclml-output-to-string</span>
  (&lt;:ul (&lt;:li <span style="color: #4d4d4d;">"foo"</span>)
        (&lt;:li <span style="color: #4d4d4d;">"bar"</span>)))</pre>
<p>Looks like a trivial difference, only on visual level (but this level is also important: we see the <code>&lt;</code> sign, which is distinct visually and actually looks like an HTML tag, not a keyword that looks just like any other keyword scattered throughout the code), but it actually has many subtle consequences.  First, keywords can&#8217;t have a function or macro definition, at least not in a practical way without conflicting with anything.  Thus, with CL-WHO syntax, one has to explicitly pass the sexprs through sexp-to-html translation function or macro; escaping to Lisp code from HTML-describing sexprs, and back to HTML is not trivial and requires a separate macro layer to switch back and forth.  Using separate package to describe HTML tags makes it possible to implement tags as macros, which was what Bese guys did.  As an important side effect, this enables basic HTML validation support, and guards users from their own typos, which CL-WHO is simply unable to do.  Yaclml also avoided the stream variable binding (they just use a dynamically bound special variable to hold output stream), so we don&#8217;t see this binding contributing to visual noise.  Now, let&#8217;s see what happens with the code when we wish to use loop to generate list items:</p>
<pre style="color: #000000; background-color: #EAF0F0;"><span style="color: #008b8b;">;; </span><span style="color: #008b8b;">CL-WHO
</span>(<span style="color: #551a8b;">with-html-output-to-string</span> (s)
  (<span style="color: #b03060;">:ul</span> (<span style="color: #551a8b;">dolist</span> (i '(<span style="color: #4d4d4d;">"foo"</span> <span style="color: #4d4d4d;">"bar"</span> <span style="color: #4d4d4d;">"baz"</span> 23))
         (htm (<span style="color: #b03060;">:li</span> (esc (princ-to-string i)))))))

<span style="color: #008b8b;">;; </span><span style="color: #008b8b;">Yaclml
</span>(<span style="color: #551a8b;">with-yaclml-output-to-string</span>
  (&lt;:ul (<span style="color: #551a8b;">dolist</span> (i '(<span style="color: #4d4d4d;">"foo"</span> <span style="color: #4d4d4d;">"bar"</span> <span style="color: #4d4d4d;">"baz"</span> 23))
          (&lt;:li (&lt;:as-html i)))))</pre>
<p>We see now that Yaclml actually includes a whole lot less visual noise.  There is an <code>&lt;:AS-HTML</code> macro, which is necessary because tags are implemented as macros, not as functions, which allows for some optimizations, but requires some more thought from user.  Yaclml authors decided to ignore value returned by forms included in tag macros, and require them to write directly to <code>YACLML:*YACLML-STREAM*</code>.  There are helper macros <!--more-->&lt;:AS-HTML (with shorthand <code>&lt;:AH</code>), which quotes its arguments&#8217; evaluation results to Yaclml output stream, and <code>&lt;:AS-IS</code> (<code>&lt;:AI</code>), which outputs evaluation results directly to the stream, allowing called function to generate its own HTML, but also requiring it to escape anything that needs to be escaped.</p>
<p>Using special variable <code>YACLML:*YACLML-STREAM*</code> instead of a lexical binding (which is what CL-WHO does) has one more benefit, when we want to delegate some parts of HTML generation to separate functions.  Let&#8217;s compare once again:</p>
<pre style="color: #000000; background-color: #EAF0F0;"><span style="color: #008b8b;">;; </span><span style="color: #008b8b;">CL-WHO
</span>(<span style="color: #551a8b;">defun</span> <span style="color: #00008b;">item-html/who</span> (val)
  (<span style="color: #551a8b;">with-html-output-to-string</span> (s)
    (<span style="color: #b03060;">:li</span> <span style="color: #b03060;">:class</span> <span style="color: #4d4d4d;">"item"</span>
         (esc (princ-to-string val)))))
(<span style="color: #551a8b;">with-html-output-to-string</span> (s)
  (<span style="color: #b03060;">:ul</span> (<span style="color: #551a8b;">dolist</span> (i '(<span style="color: #4d4d4d;">"foo"</span> <span style="color: #4d4d4d;">"bar"</span> <span style="color: #4d4d4d;">"baz"</span> 23))
          (str (item-html/who i)))))

<span style="color: #008b8b;">;; </span><span style="color: #008b8b;">Yaclml
</span>(<span style="color: #551a8b;">defun</span> <span style="color: #00008b;">&lt;item</span> (val)
  (&lt;:li <span style="color: #b03060;">:class</span> <span style="color: #4d4d4d;">"item"</span>
    (&lt;:ah val)))
(<span style="color: #551a8b;">with-yaclml-output-to-string</span>
  (&lt;:ul (<span style="color: #551a8b;">dolist</span> (i '(<span style="color: #4d4d4d;">"foo"</span> <span style="color: #4d4d4d;">"bar"</span> <span style="color: #4d4d4d;">"baz"</span> 23))
          (&lt;item i)))</pre>
<p>The CL-WHO functions include very much noise, which Yaclml manages to avoid.  The visual distinction of tags with the <code>&lt;</code> package alias helps with code readability.  We also use a convention to put formatting-only functions and macros in a separate package, with name starting with <code>&lt;</code>, or to start their names with <code>&lt;</code>.  This convention clearly indicates formatting/visual layer; for simplicity, I used function name starting with <code>&lt;</code>, but in a larger project, I&#8217;d use separate package for formatting, nicknamed <code>&lt;project</code>, so I would use <code>&lt;project:item</code> here.</p>
<p>Could Yaclml HTML generation be better?  Sure thing.  It could step away from macros (at a performance penalty, though), and use functions, which would return and consume HTML fragments (or consume strings, or actually any Lisp values—including closures for lazy evaluation).  This would introduce first-class HTML fragment object, giving us sort of DOM and possibility of passing around and manipulating already generated HTML fragments, and wouldn&#8217;t requre the <code>&lt;:AH</code> and <code>&lt;:AI</code> helper macros (or actually would require only one of those).  That seems to be what <a href="http://labs.core.gen.tr/">core-server</a> guys are doing with their <a href="http://labs.core.gen.tr/#domprogramming">DOM programming support</a>.  I don&#8217;t use it yet, partly because I don&#8217;t need this kind of functionality and I&#8217;m more acquainted with Yaclml; partly because I don&#8217;t want to buy into core-server as a whole—core-server is a monolith and ripping DOM support out of it would require substantial amount of work—and partly because I use the second part of Yaclml, which I will describe in the following article: <a href="http://www.3ofcoins.net/2010/01/21/yaclml-in-pictures-part-ii-templating/">HTML and XML templating</a>.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.3ofcoins.net/2009/02/07/yaclml-in-pictures-part-i-html-generation/feed/</wfw:commentRss>
		<slash:comments>6</slash:comments>
		</item>
	</channel>
</rss>
