<?xml version="1.0" encoding="UTF-8"?>
<?xml-stylesheet href="/stylesheets/rss.css" type="text/css"?>
<rss version="2.0" xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:trackback="http://madskills.com/public/xml/rss/module/trackback/">
  <channel>
    <title>Tom Moertel's Weblog: Category rails</title>
    <link>http://blog.moertel.com/articles/category/rails</link>
    <language>en-us</language>
    <ttl>40</ttl>
    <description>Quality rants on programming theory and stuff geeks like</description>
    <item>
      <title>I have written a short novel's worth of content for my blog</title>
      <description>&lt;p&gt;How much content have I written for my blog?  Let&amp;#8217;s find out.&lt;/p&gt;


	&lt;p&gt;My blog runs on &lt;a href="http://typosphere.org/"&gt;Typo&lt;/a&gt;, which is built upon
&lt;a href="http://www.rubyonrails.com/"&gt;Ruby on Rails&lt;/a&gt;.  Let&amp;#8217;s fire up the Rails
console and gather a quick word count:&lt;/p&gt;


&lt;div class="typocode"&gt;&lt;pre&gt;&lt;code class="typocode_ruby "&gt;&lt;span class="global"&gt;$ &lt;/span&gt;&lt;span class="ident"&gt;cd&lt;/span&gt; ~&lt;span class="punct"&gt;/&lt;/span&gt;&lt;span class="ident"&gt;blog&lt;/span&gt;
&lt;span class="global"&gt;$ &lt;/span&gt;&lt;span class="ident"&gt;ruby&lt;/span&gt; &lt;span class="ident"&gt;script&lt;/span&gt;&lt;span class="punct"&gt;/&lt;/span&gt;&lt;span class="ident"&gt;console&lt;/span&gt; 
&lt;span class="constant"&gt;Loading&lt;/span&gt; &lt;span class="ident"&gt;development&lt;/span&gt; &lt;span class="ident"&gt;environment&lt;/span&gt;&lt;span class="punct"&gt;.&lt;/span&gt;
&lt;span class="punct"&gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="ident"&gt;require&lt;/span&gt; &lt;span class="punct"&gt;'&lt;/span&gt;&lt;span class="string"&gt;article&lt;/span&gt;&lt;span class="punct"&gt;'&lt;/span&gt;
&lt;span class="punct"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="constant"&gt;true&lt;/span&gt;
&lt;span class="punct"&gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="constant"&gt;Article&lt;/span&gt;&lt;span class="punct"&gt;.&lt;/span&gt;&lt;span class="ident"&gt;find&lt;/span&gt;&lt;span class="punct"&gt;(&lt;/span&gt;&lt;span class="symbol"&gt;:all&lt;/span&gt;&lt;span class="punct"&gt;).&lt;/span&gt;&lt;span class="ident"&gt;inject&lt;/span&gt;&lt;span class="punct"&gt;(&lt;/span&gt;&lt;span class="number"&gt;0&lt;/span&gt;&lt;span class="punct"&gt;)&lt;/span&gt; &lt;span class="punct"&gt;{&lt;/span&gt; &lt;span class="punct"&gt;|&lt;/span&gt;&lt;span class="ident"&gt;sum&lt;/span&gt;&lt;span class="punct"&gt;,&lt;/span&gt;&lt;span class="ident"&gt;a&lt;/span&gt;&lt;span class="punct"&gt;|&lt;/span&gt; &lt;span class="ident"&gt;sum&lt;/span&gt; &lt;span class="punct"&gt;+=&lt;/span&gt;
       &lt;span class="punct"&gt;(&lt;/span&gt;&lt;span class="ident"&gt;a&lt;/span&gt;&lt;span class="punct"&gt;.&lt;/span&gt;&lt;span class="ident"&gt;body&lt;/span&gt; &lt;span class="punct"&gt;+&lt;/span&gt; &lt;span class="ident"&gt;a&lt;/span&gt;&lt;span class="punct"&gt;.&lt;/span&gt;&lt;span class="ident"&gt;extended&lt;/span&gt;&lt;span class="punct"&gt;.&lt;/span&gt;&lt;span class="ident"&gt;to_s&lt;/span&gt;&lt;span class="punct"&gt;).&lt;/span&gt;&lt;span class="ident"&gt;split&lt;/span&gt;&lt;span class="punct"&gt;(/&lt;/span&gt;&lt;span class="regex"&gt;&lt;span class="escape"&gt;\s&lt;/span&gt;+&lt;/span&gt;&lt;span class="punct"&gt;/).&lt;/span&gt;&lt;span class="ident"&gt;length&lt;/span&gt; &lt;span class="punct"&gt;}&lt;/span&gt;
&lt;span class="punct"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="number"&gt;66665&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

	&lt;p&gt;So I have written about 66 kilo-words, which is entering &lt;a href="http://en.wikipedia.org/wiki/Novel"&gt;novel
territory&lt;/a&gt;.  Paperback-wise,
it&amp;#8217;s about 190 pages.&lt;/p&gt;


	&lt;p&gt;All I need now is a villain and some cool cover art.&lt;/p&gt;


&lt;code&gt;;-)&lt;/code&gt;</description>
      <pubDate>Fri, 30 Mar 2007 00:34:00 -0400</pubDate>
      <guid isPermaLink="false">urn:uuid:7f3fdbe1-3f38-4322-b8d2-0ab67f887114</guid>
      <author>Tom Moertel</author>
      <link>http://blog.moertel.com/articles/2007/03/30/i-have-written-a-short-novels-worth-of-content-for-my-blog</link>
      <category>site news</category>
      <category>rails</category>
      <category>writing</category>
      <category>rails</category>
      <category>writing</category>
      <category>words</category>
      <category>word_count</category>
      <category>blog</category>
      <trackback:ping>http://blog.moertel.com/articles/trackback/426</trackback:ping>
    </item>
    <item>
      <title>Ruby 1.9 gets handy new method Object#tap</title>
      <description>&lt;p&gt;Via
&lt;a href="http://eigenclass.org/hiki.rb?Changes-in-Ruby-1.9-update-6"&gt;eigenclass.org&lt;/a&gt;
I learned that Ruby 1.9 will sport a new &lt;code&gt;Object&lt;/code&gt; method
called
&lt;a href="http://eigenclass.org/hiki.rb?Changes+in+Ruby+1.9#l25"&gt;&lt;code&gt;tap&lt;/code&gt;&lt;/a&gt;,
which is something I&amp;#8217;ve been &lt;a href="http://blade.nagaokaut.ac.jp/cgi-bin/scat.rb/ruby/ruby-talk/189541"&gt;hoping
for&lt;/a&gt;.&lt;/p&gt;


	&lt;p&gt;What&amp;#8217;s &lt;code&gt;tap&lt;/code&gt;?  It&amp;#8217;s a helper for call chaining.  It
passes its object into the given block and, after the block finishes,
returns the object:&lt;/p&gt;


&lt;div class="typocode"&gt;&lt;pre&gt;&lt;code class="typocode_ruby "&gt;&lt;span class="ident"&gt;an_object&lt;/span&gt;&lt;span class="punct"&gt;.&lt;/span&gt;&lt;span class="ident"&gt;tap&lt;/span&gt; &lt;span class="keyword"&gt;do&lt;/span&gt; &lt;span class="punct"&gt;|&lt;/span&gt;&lt;span class="ident"&gt;o&lt;/span&gt;&lt;span class="punct"&gt;|&lt;/span&gt;
  &lt;span class="comment"&gt;# do stuff with an_object, which is in o&lt;/span&gt;
&lt;span class="keyword"&gt;end&lt;/span&gt; &lt;span class="comment"&gt;# ===&amp;gt; an_object&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

	&lt;p&gt;The benefit is that &lt;code&gt;tap&lt;/code&gt; always returns the object it&amp;#8217;s called on, even if the block returns some other result.  Thus you can insert a &lt;code&gt;tap&lt;/code&gt; block into the middle of an existing method pipleline without breaking the flow.  MenTaLguY has some &lt;a href="http://moonbase.rydia.net/mental/blog/programming/eavesdropping-on-expressions"&gt;nifty examples&lt;/a&gt; of other things you can do with &lt;code&gt;tap&lt;/code&gt;.&lt;/p&gt;


	&lt;p&gt;Fans of Ruby on Rails may recognize &lt;code&gt;tap&lt;/code&gt; as similar to RoR&amp;#8217;s own
&lt;a href="http://weblog.jamisbuck.org/2006/10/27/mining-activesupport-object-returning"&gt;&lt;code&gt;returning&lt;/code&gt;&lt;/a&gt; helper.&lt;/p&gt;


	&lt;p&gt;Looks like Ruby 1.9 is going to be extra cool for a number of reasons.&lt;/p&gt;</description>
      <pubDate>Wed, 07 Feb 2007 12:08:00 -0500</pubDate>
      <guid isPermaLink="false">urn:uuid:9a2e5bfe-f2b1-462f-88c5-cd231503292a</guid>
      <author>Tom Moertel</author>
      <link>http://blog.moertel.com/articles/2007/02/07/ruby-1-9-gets-handy-new-method-object-tap</link>
      <category>ruby</category>
      <category>rails</category>
      <category>ruby</category>
      <category>rails</category>
      <category>tap</category>
      <category>helpers</category>
      <trackback:ping>http://blog.moertel.com/articles/trackback/362</trackback:ping>
    </item>
    <item>
      <title>A type-based solution to the &amp;quot;strings problem&amp;quot;: a fitting end to XSS and SQL-injection holes?</title>
      <description>&lt;p&gt;Even skilled programmers have a hard time keeping their web
applications free of &lt;span class="caps"&gt;XSS&lt;/span&gt; and &lt;span class="caps"&gt;SQL&lt;/span&gt;-injection vulnerabilities.  And it
shows:  &lt;a href="http://portal.spidynamics.com/blogs/msutton/archive/2006/09/26/How-Prevalent-Are-SQL-Injection-Vulnerabilities_3F00_.aspx"&gt;a sobering portion of web sites are open to some scary security threats&lt;/a&gt;.&lt;/p&gt;


	&lt;p&gt;Why are so many sites vulnerable to these well-known holes?  Probably
because it&amp;#8217;s insanely hard for programmers to solve the fundamental
&amp;#8220;strings problem&amp;#8221; at the heart of these vulnerabilities. The problem
itself is easy to understand, but we humans aren&amp;#8217;t equipped to carry
out the solution.  Simply put, we just plain suck at keeping a
bazillion different strings straight in our heads, let alone
consistently and reliably rendering their interactions safe whenever they
cross paths in a modern web application.  It&amp;#8217;s easy to say, &amp;#8220;just
escape the little buggers,&amp;#8221; but it&amp;#8217;s hard to get it right, every single time.&lt;/p&gt;


	&lt;p&gt;Computers, on the other hand, are pretty good at keeping track of
details by the bucket-full. Wouldn&amp;#8217;t it be nice, then,
if our programming languages gave us the power to delegate this nasty &amp;#8220;strings
problem&amp;#8221; to our computers, which could then devote their unwavering mechanical precision to grinding the problem out of existence?  &lt;a href="http://weblog.raganwald.com/2006/03/ill-take-static-typing-for-800-alex.html" title="Raganwald: I'll take Static Typing for $800, Alex."&gt;Isn&amp;#8217;t that the kind of thing modern programming languages are supposed to be good at?&lt;/a&gt;&lt;/p&gt;


	&lt;p&gt;I&amp;#8217;d like to think the answer to that question is a big, &lt;em&gt;you betcha&lt;/em&gt;.&lt;/p&gt;


	&lt;p&gt;So let&amp;#8217;s grab a modern programming language and solve the strings problem.&lt;/p&gt;


	&lt;h3&gt; Let&amp;#8217;s solve the strings problem in Haskell&lt;/h3&gt;


	&lt;p&gt;In this article, we will look at one way (among many) to solve the strings
problem: by adding Ruby-style string templates to Haskell.  These
templates support &amp;#8220;interpolation&amp;#8221; via the usual, convenient &lt;code&gt;#{var}&lt;/code&gt;
syntax, but here interpolation is type safe. Haskell&amp;#8217;s type system
will prevent us from inadvertently mixing incompatible string types,
and it will detect mistakes at compile time, before they can become
live &lt;span class="caps"&gt;XSS&lt;/span&gt; or &lt;span class="caps"&gt;SQL&lt;/span&gt;-injection holes.  Further, our solution will offer
us these benefits without making us jump through hoops or pay some
onerous syntax penalty.&lt;/p&gt;


	&lt;p&gt;To be more specific, the system offers the following benefits:&lt;/p&gt;


	&lt;ul&gt;
	&lt;li&gt;It provides a string-management kernel that lets you create &amp;#8220;safe strings&amp;#8221; by &lt;em&gt;certifying&lt;/em&gt; a regular string as representing either text or a fragment of a known language.&lt;/li&gt;
		&lt;li&gt;It allows you to conveniently define new language types for any string-based language that you can provide an escaping rule for (e.g., &lt;span class="caps"&gt;XML&lt;/span&gt;, URLs, &lt;span class="caps"&gt;SQL&lt;/span&gt;, untrusted user input).&lt;/li&gt;
		&lt;li&gt;It provides compile-time syntactic sugar (via Template Haskell) that makes working with safe strings as convenient as working with string interpolation in languages like Ruby and Perl.&lt;/li&gt;
		&lt;li&gt;It catches and reports (at compile time) the following commonly made programming errors:
	&lt;ul&gt;
	&lt;li&gt;failing to escape a plain-old-text string before mixing it into a string that represents a language fragment&lt;/li&gt;
		&lt;li&gt;mixing strings that represent fragments of incompatible languages&lt;/li&gt;
		&lt;li&gt;mixing strings that represent fragments of compatible languages in an ambiguous way (the system will force you to disambiguate)&lt;/li&gt;
	&lt;/ul&gt;&lt;/li&gt;
	&lt;/ul&gt;


	&lt;p&gt;(This is a long one, so grab an espresso, lean back, and read on in
style.  Also, if you have a smoking jacket, you might want to get it now.)&lt;/p&gt;&lt;p&gt;Before I describe this Haskell-based solution, let&amp;#8217;s take a closer
look at the strings problem and review why a type-based approach makes
sense.  (If you already understand the strings problem and are
convinced that it is both important and tricky to solve, feel free
to skim the first third of this article.)&lt;/p&gt;


	&lt;h3&gt; Examining the &amp;#8220;strings problem&amp;#8221;&lt;/h3&gt;


	&lt;p&gt;Most web applications are just business-logic-driven string processors.  They
take strings from user-submitted forms, database queries, web-service
responses, templates, and myriad other sources, and they combine the
strings to generate yet more strings, which they emit as output and
fling across the Internet, into your web browser.&lt;/p&gt;


	&lt;p&gt;For example, consider this snippet of Ruby (on Rails) code that I used &lt;a href="http://blog.moertel.com/articles/2006/08/09/adding-reddit-and-del-icio-us-buttons-to-articles-in-typo"&gt;to
add submit-to-Reddit and submit-to-del.icio.us
buttons&lt;/a&gt;
to articles on my blog:&lt;/p&gt;


&lt;pre&gt;&lt;code&gt;def submit_this_article_links(article)
  site_list(article).map do |submit_title, submit_url, image_tag|
    %(&amp;lt;a href="#{h submit_url}" 
         title="#{h submit_title}: &amp;amp;#x201C;#{h article.title}&amp;amp;#x201D;" 
      &amp;gt;#{image_tag}&amp;lt;/a&amp;gt;)
  end.join("&amp;amp;#160;")
end

def site_list(article)
  u_title = u(article.title)
  u_url = u(url_of(article, false))
  [  # I really belong in a database table
    [ "Submit to Reddit.com",
      "http://reddit.com/submit?url=#{u_url}&amp;#38;title=#{u_title}",
      image_tag("reddit.gif", :size =&amp;gt; "18x18", :border =&amp;gt; 0)
    ],
    [ "Save to del.icio.us",
      "http://del.icio.us/post?v=2&amp;#38;url=#{u_url}&amp;#38;title=#{u_title}",
      image_tag("delicious.gif", :size =&amp;gt; "16x16", :border =&amp;gt; 0)
    ]
  ]
end
&lt;/code&gt;&lt;/pre&gt;

	&lt;p&gt;When writing this code, I had to keep track of at least three
different kinds of strings:&lt;/p&gt;


	&lt;ul&gt;
	&lt;li&gt;&lt;strong&gt;Plain-old text&lt;/strong&gt;, e.g., article titles&lt;/li&gt;
		&lt;li&gt;&lt;strong&gt;URLs&lt;/strong&gt;, e.g., article permalinks&lt;/li&gt;
		&lt;li&gt;&lt;strong&gt;&lt;span class="caps"&gt;XHTML&lt;/span&gt; fragments&lt;/strong&gt;, e.g., the hypertext link to Reddit&amp;#8217;s submission form&lt;/li&gt;
	&lt;/ul&gt;


	&lt;p&gt;In code like this, each type of string must conform to the
requirements of its own little language, and it&amp;#8217;s the programmer&amp;#8217;s job &amp;#8211; your job &amp;#8211; to make sure that differences in these requirements are accounted for
when combining strings.  Getting it right is a
difficult trick to pull off, and getting it right consistently is
&lt;a href="http://blog.moertel.com/articles/2006/10/12/if-unit-testing-cant-keep-rails-safe-from-string-escaping-problems-what-makes-you-think-it-will-keep-your-projects-safe"&gt;something even the best developers have difficulty doing&lt;/a&gt;.&lt;/p&gt;


	&lt;p&gt;In the tiny snippet of code above, for example, I had to remember to
do all of these things:&lt;/p&gt;


	&lt;ol&gt;
	&lt;li&gt;&lt;span class="caps"&gt;URL&lt;/span&gt;-escape (using the &lt;code&gt;u&lt;/code&gt; helper method) the article&amp;#8217;s title before inserting it into the submit-URL template&lt;/li&gt;
		&lt;li&gt;&lt;span class="caps"&gt;URL&lt;/span&gt;-escape the &lt;span class="caps"&gt;URL&lt;/span&gt; for the article&amp;#8217;s permalink before inserting it into the submit-URL template&lt;/li&gt;
		&lt;li&gt;&lt;span class="caps"&gt;HTML&lt;/span&gt;-escape (using the &lt;code&gt;h&lt;/code&gt; helper method) the final, expanded submit-URL template before inserting it into the hypertext-link template&lt;/li&gt;
		&lt;li&gt;&lt;span class="caps"&gt;HTML&lt;/span&gt;-escape the submit-title (e.g., &amp;#8220;Submit to Reddit&amp;#8221;) before inserting it into the hypertext-link template&lt;/li&gt;
		&lt;li&gt;&lt;span class="caps"&gt;HTML&lt;/span&gt;-escape the article&amp;#8217;s title before inserting it into the hypertext-link template&lt;/li&gt;
	&lt;/ol&gt;


	&lt;p&gt;That&amp;#8217;s a lot to keep track of when coding.&lt;/p&gt;


	&lt;p&gt;But that&amp;#8217;s not all.  I also had to know &lt;em&gt;not&lt;/em&gt; to escape the result of
calling &lt;code&gt;image_tag&lt;/code&gt;, because that helper method returns
an &lt;span class="caps"&gt;HTML&lt;/span&gt; fragment, which is already in the language of the
hypertext-link template into which it is inserted.  Escaping it would
have turned the image-element markup into embedded text that happens
to look a lot like &lt;span class="caps"&gt;HTML&lt;/span&gt; markup.&lt;/p&gt;


	&lt;p&gt;And that&amp;#8217;s not the worst of it.  If you screw up any one of these
steps for the typical web application, you open
the door to a host of nasty problems.  If you&amp;#8217;re lucky, the damage
will be contained to broken links or a rendering problem that
most people won&amp;#8217;t notice, maybe a weird database error now and again.
In the worst case, however, you&amp;#8217;re screwed: Your application&amp;#8217;s
customers become vulnerable to &lt;a href="http://en.wikipedia.org/wiki/Cross_site_scripting"&gt;cross-site-scripting (XSS)
attacks&lt;/a&gt; and your
database is opened to &lt;a href="http://en.wikipedia.org/wiki/SQL_injection"&gt;injected
&lt;span class="caps"&gt;SQL&lt;/span&gt;&lt;/a&gt;, through which
enterprising crackers might steal your customers&amp;#8217; account data
or do even nastier things.&lt;/p&gt;


	&lt;p&gt;Clearly, the strings problem is common enough and nasty enough to merit
our attention.  Many of our favorite problem-stomping practices,
however, have not proved effective on the ever-tricky strings problem.&lt;/p&gt;


	&lt;h3&gt;Unit testing is an inefficient solution to the strings problem&lt;/h3&gt;


	&lt;p&gt;Unit testing is one of the most efficient programming practices for
increasing the quality of software.  If you write unit tests pervasively
as you code, you are likely to nip many kinds of programming problems
in the bud, saving time and effort, which you can then re-invest in
your code.  Further, unit-testing suites make for swell
regression-detection nets and thus free you to refactor crufty code
without fear of introducing breakage elsewhere.  As a result, you&amp;#8217;re
more likely to keep your code lean and mean.&lt;/p&gt;


	&lt;p&gt;Despite its general effectiveness, unit testing is an inefficient way
to defend against the perils of the strings problem.  That&amp;#8217;s because
the strings problem is caused by knowledge deficits, which you can&amp;#8217;t
test for.  If you don&amp;#8217;t realize that you must escape one &lt;span class="caps"&gt;URL&lt;/span&gt;
before you stuff it into another &lt;span class="caps"&gt;URL&lt;/span&gt;, you probably won&amp;#8217;t think to
write tests for that requirement.&lt;/p&gt;


	&lt;p&gt;Moreover, if you do think to write the tests, it&amp;#8217;s expensive to get
them right.  In most unit testing scenarios, getting the tests right
is usually easier or at least comparable in difficulty to getting the
code that&amp;#8217;s being tested right.  That&amp;#8217;s why unit testing is usually
so efficient.  For the strings problem, however, getting
the tests right is often much more expensive than writing typical
string-handling code.  In my code sample
above, for example, there are at least six ways the strings problem
can cause trouble.  How do you test for them all without making
a mistake?  It&amp;#8217;s not easy.&lt;/p&gt;


	&lt;p&gt;In sum, unit testing probably isn&amp;#8217;t the answer to the strings problem.&lt;/p&gt;


	&lt;h3&gt;Other solutions to the strings problem&lt;/h3&gt;


	&lt;p&gt;If unit testing isn&amp;#8217;t the answer, what is?&lt;/p&gt;


	&lt;p&gt;Joel Spolsky wrote about
the strings problem and &lt;a href="http://www.joelonsoftware.com/articles/Wrong.html"&gt;suggested that using Hungarian notation was
an effective
solution&lt;/a&gt;.
It might work, but it&amp;#8217;s clunky.&lt;/p&gt;


	&lt;p&gt;In the database-programming world, many programmers have adopted the
convention of never inserting a string into a &lt;span class="caps"&gt;SQL&lt;/span&gt; template by hand.
Instead, they insert placeholders, typically question marks,
into a template to indicate where they would like strings to be
inserted.  The template and the strings are then given
to a special function that safely inserts the strings, escaping them
as necessary.  In Ruby on Rails, which has a fairly typical
implementation, template expansion looks like this:&lt;/p&gt;


&lt;pre&gt;&lt;code&gt;Post.find_by_sql \
  [ "SELECT * FROM posts WHERE author = ? AND created &amp;gt; ?",
    author_id, start_date ]
&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;The question-marks-in-the-template solution is effective, but it&amp;#8217;s
also clunky, especially when you&amp;#8217;re trying to insert a lot of strings.
By comparison, Ruby&amp;#8217;s native string-interpolation feature, in which the syntax
&lt;code&gt;#{...}&lt;/code&gt; lets us inject strings into a string template, is
unsafe but much easier to follow:&lt;/p&gt;

&lt;pre&gt;&lt;code&gt;chunkiness = "extra chunky" 
"I love #{chunkiness} bacon!" 
# ==&amp;gt; "I love extra chunky bacon!" 
&lt;/code&gt;&lt;/pre&gt;

	&lt;p&gt;In sum, the Hungarian-notation solution and the question-marks
solution are reasonable responses to the strings problem, but both are
clunky, especially when compared to the straightforwardness of
good-old string interpolation.&lt;/p&gt;


	&lt;p&gt;Perhaps we can do better.&lt;/p&gt;


	&lt;h3&gt; Eating and having one&amp;#8217;s cake: a type-based solution&lt;/h3&gt;


	&lt;p&gt;An ideal solution would combine the safety of the question-marks
solution with the straightforward convenience of string interpolation,
and it would work for all kinds of strings, not just &lt;span class="caps"&gt;SQL&lt;/span&gt;, and, because
I&amp;#8217;m implementing it in Haskell, it would lovingly nestle into
Haskell&amp;#8217;s type system and gain the full benefits of type-inferencing
goodness.&lt;/p&gt;


	&lt;p&gt;How would it work?  Well, let&amp;#8217;s back up and think about strings for a
moment.  We can divide strings into two classes: (1) those that
represent text, in which every character represents literally itself;
and (2) those that represent fragments of interpreted languages, such
as &lt;span class="caps"&gt;XML&lt;/span&gt; or &lt;span class="caps"&gt;SQL&lt;/span&gt;, where each character&amp;#8217;s interpretation depends on the
rules of the associated language.  In text, for example, an ampersand
(&amp;#8220;&amp;#38;&amp;#8221;) represents an ampersand, but in &lt;span class="caps"&gt;XML&lt;/span&gt; an ampersand represents the
start of a character-entity reference.&lt;/p&gt;


	&lt;p&gt;It doesn&amp;#8217;t make sense, then, to join text strings directly with
language-fragment strings.  If you did join them, text characters
could be misinterpreted as language characters.  For the same reason,
it doesn&amp;#8217;t make sense to join fragments of different languages
together.  (It does make sense, however, to &lt;em&gt;escape&lt;/em&gt; text strings or
language fragments &amp;#8220;into&amp;#8221; a target language and &lt;em&gt;then&lt;/em&gt; join them with
strings in the target language.)&lt;/p&gt;


	&lt;p&gt;A sound solution, therefore, should enforce the following fundamental,
safe-string-handling rule: &lt;em&gt;Do not allow strings that represent
fragments of one language to be directly joined with strings that
represent either plain text or fragments of another language&lt;/em&gt;.&lt;/p&gt;


	&lt;p&gt;The trick is making the computer enforce this rule for us.  As
it turns out, modern type systems absolutely love to do this kind of thing.&lt;/p&gt;


	&lt;h3&gt; A solution to the strings problem in Haskell&lt;/h3&gt;


	&lt;p&gt;Making the computer enforce our safe-string-handling rule in Haskell
is fairly easy.  All it takes is a little code.
(As we go through the following code, remember that
we&amp;#8217;re writing a library.  Normally, as users of the library, this
code would be invisible to us.)&lt;/p&gt;


	&lt;p&gt;To begin, we create a module for our code and export
the essential types and functions that make up our about-to-be-written
safe-string kernel:&lt;/p&gt;


&lt;div class="typocode"&gt;&lt;pre&gt;&lt;code class="typocode_haskell "&gt;&lt;span class='keyword'&gt;module&lt;/span&gt; &lt;span class='conid'&gt;SafeStrings&lt;/span&gt;
&lt;span class='layout'&gt;(&lt;/span&gt;
  &lt;span class='conid'&gt;Language&lt;/span&gt;&lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='keyglyph'&gt;..&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;&lt;span class='layout'&gt;,&lt;/span&gt;
&lt;span class='layout'&gt;,&lt;/span&gt; &lt;span class='conid'&gt;SafeString&lt;/span&gt; &lt;span class='comment'&gt;-- we export the data type but not the constructors&lt;/span&gt;
&lt;span class='layout'&gt;,&lt;/span&gt; &lt;span class='varid'&gt;empty&lt;/span&gt;&lt;span class='layout'&gt;,&lt;/span&gt; &lt;span class='varid'&gt;frag&lt;/span&gt;&lt;span class='layout'&gt;,&lt;/span&gt; &lt;span class='varid'&gt;text&lt;/span&gt;
&lt;span class='layout'&gt;,&lt;/span&gt; &lt;span class='varid'&gt;cat&lt;/span&gt;&lt;span class='layout'&gt;,&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varop'&gt;+++&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;
&lt;span class='layout'&gt;,&lt;/span&gt; &lt;span class='varid'&gt;render&lt;/span&gt;&lt;span class='layout'&gt;,&lt;/span&gt; &lt;span class='varid'&gt;renders&lt;/span&gt;&lt;span class='layout'&gt;,&lt;/span&gt; &lt;span class='varid'&gt;lang&lt;/span&gt;
&lt;span class='layout'&gt;,&lt;/span&gt; &lt;span class='varid'&gt;q&lt;/span&gt;
&lt;span class='layout'&gt;,&lt;/span&gt; &lt;span class='varid'&gt;declareSafeString&lt;/span&gt;
&lt;span class='layout'&gt;)&lt;/span&gt;
&lt;span class='keyword'&gt;where&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

	&lt;p&gt;In order to create safe strings that correspond to particular
languages, we need to tell the computer what we mean by &lt;em&gt;Language&lt;/em&gt;:&lt;/p&gt;


&lt;div class="typocode"&gt;&lt;pre&gt;&lt;code class="typocode_haskell "&gt;&lt;span class='keyword'&gt;class&lt;/span&gt; &lt;span class='conid'&gt;Language&lt;/span&gt; &lt;span class='varid'&gt;l&lt;/span&gt; &lt;span class='keyword'&gt;where&lt;/span&gt;
    &lt;span class='varid'&gt;litfrag&lt;/span&gt;  &lt;span class='keyglyph'&gt;::&lt;/span&gt; &lt;span class='conid'&gt;String&lt;/span&gt; &lt;span class='keyglyph'&gt;-&amp;gt;&lt;/span&gt; &lt;span class='varid'&gt;l&lt;/span&gt;   &lt;span class='comment'&gt;-- String is a literal language fragment&lt;/span&gt;
    &lt;span class='varid'&gt;littext&lt;/span&gt;  &lt;span class='keyglyph'&gt;::&lt;/span&gt; &lt;span class='conid'&gt;String&lt;/span&gt; &lt;span class='keyglyph'&gt;-&amp;gt;&lt;/span&gt; &lt;span class='varid'&gt;l&lt;/span&gt;   &lt;span class='comment'&gt;-- String is literal text&lt;/span&gt;
    &lt;span class='varid'&gt;natrep&lt;/span&gt;   &lt;span class='keyglyph'&gt;::&lt;/span&gt; &lt;span class='varid'&gt;l&lt;/span&gt; &lt;span class='keyglyph'&gt;-&amp;gt;&lt;/span&gt; &lt;span class='conid'&gt;String&lt;/span&gt;   &lt;span class='comment'&gt;-- Gets the native-language representation&lt;/span&gt;
    &lt;span class='varid'&gt;language&lt;/span&gt; &lt;span class='keyglyph'&gt;::&lt;/span&gt; &lt;span class='varid'&gt;l&lt;/span&gt; &lt;span class='keyglyph'&gt;-&amp;gt;&lt;/span&gt; &lt;span class='conid'&gt;String&lt;/span&gt;   &lt;span class='comment'&gt;-- Gets the name of the language&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

	&lt;p&gt;Here we&amp;#8217;re saying that &lt;em&gt;Language&lt;/em&gt; is the class of languages, i.e., all
data types &lt;em&gt;l&lt;/em&gt; for which we can provide four functions:&lt;/p&gt;


	&lt;ol&gt;
	&lt;li&gt;&lt;em&gt;litfrag&lt;/em&gt; &amp;#8211; converts a string that represents a language fragment into a language fragment&lt;/li&gt;
		&lt;li&gt;&lt;em&gt;littext&lt;/em&gt; &amp;#8211; converts a string that represents plain text into a language fragment that represents the text (via escaping)&lt;/li&gt;
		&lt;li&gt;&lt;em&gt;natrep&lt;/em&gt; &amp;#8211;  converts a language fragment, verbatim, into a string that represents the language fragment&lt;/li&gt;
		&lt;li&gt;&lt;em&gt;language&lt;/em&gt; &amp;#8211; returns the name of the language associated with a given fragment&lt;/li&gt;
	&lt;/ol&gt;


	&lt;p&gt;Further, we need to declare a few &amp;#8220;language laws&amp;#8221; that conforming
&lt;em&gt;Language&lt;/em&gt; types must obey.  These laws are for us.  They will keep us
honest when teaching the computer about new languages.  Here are the
two laws we will require language types to satisfy:&lt;/p&gt;


	&lt;ul&gt;
	&lt;li&gt;&lt;em&gt;natrep&lt;/em&gt; (&lt;em&gt;litfrag&lt;/em&gt; &lt;em&gt;s&lt;/em&gt;) &lt;code&gt;==&lt;/code&gt; &lt;em&gt;s&lt;/em&gt;&lt;/li&gt;
		&lt;li&gt;&lt;em&gt;natrep&lt;/em&gt; (&lt;em&gt;littext&lt;/em&gt; &lt;em&gt;s&lt;/em&gt;) &lt;code&gt;==&lt;/code&gt; (&lt;em&gt;escape&lt;sub&gt;L&lt;/sub&gt;&lt;/em&gt; &lt;em&gt;s&lt;/em&gt;)&lt;/li&gt;
	&lt;/ul&gt;


	&lt;p&gt;The first law requires that (&lt;em&gt;natrep&lt;/em&gt;&amp;#160;.&amp;#160;&lt;em&gt;litfrag&lt;/em&gt;) be
equivalent to the identity function for strings.  The second law
requires that (&lt;em&gt;natrep&lt;/em&gt;&amp;#160;.&amp;#160;&lt;em&gt;littext&lt;/em&gt;) be equivalent to
the text-escaping function for a given language &lt;em&gt;L&lt;/em&gt;.  For example,
for the language &lt;span class="caps"&gt;XML&lt;/span&gt;:&lt;/p&gt;


&lt;pre&gt;&lt;code&gt;natrep (litfrag "&amp;lt;em&amp;gt;wow!&amp;lt;/em&amp;gt;") ==&amp;gt; "&amp;lt;em&amp;gt;wow!&amp;lt;/em&amp;gt;" 
natrep (littext "ham &amp;#38; eggs")    ==&amp;gt; "ham &amp;amp;amp; eggs" 
&lt;/code&gt;&lt;/pre&gt;

	&lt;p&gt;Next, let&amp;#8217;s construct a type-safe container for strings having
a known language:&lt;/p&gt;


&lt;div class="typocode"&gt;&lt;pre&gt;&lt;code class="typocode_haskell "&gt;&lt;span class='keyword'&gt;data&lt;/span&gt; &lt;span class='conid'&gt;Language&lt;/span&gt; &lt;span class='varid'&gt;l&lt;/span&gt; &lt;span class='keyglyph'&gt;=&amp;gt;&lt;/span&gt; &lt;span class='conid'&gt;SafeString&lt;/span&gt; &lt;span class='varid'&gt;l&lt;/span&gt;
    &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='conid'&gt;SSEmpty&lt;/span&gt;
    &lt;span class='keyglyph'&gt;|&lt;/span&gt; &lt;span class='conid'&gt;SSFragment&lt;/span&gt; &lt;span class='varid'&gt;l&lt;/span&gt;
    &lt;span class='keyglyph'&gt;|&lt;/span&gt; &lt;span class='conid'&gt;SSCat&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='conid'&gt;SafeString&lt;/span&gt; &lt;span class='varid'&gt;l&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='conid'&gt;SafeString&lt;/span&gt; &lt;span class='varid'&gt;l&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

	&lt;p&gt;This data-type definition says that if &lt;em&gt;l&lt;/em&gt; is a language, we
can construct &lt;em&gt;SafeString&lt;/em&gt; values for that language.  Each value can
represent an empty fragment of the language (via &lt;em&gt;SSEmpty&lt;/em&gt;), a
non-empty fragment of the language (via &lt;em&gt;SSFragment&lt;/em&gt;), or the
concatenation of two other &lt;em&gt;SafeString&lt;/em&gt; values for the language
(via &lt;em&gt;SSCat&lt;/em&gt;).&lt;/p&gt;


	&lt;p&gt;Now comes the interesting part.  We are going to use the type
system to enforce the safe-string-handling rule for us.&lt;/p&gt;


	&lt;p&gt;We will do this using the &lt;em&gt;SafeString&lt;/em&gt; data type we just defined.
We have already placed the data type&amp;#8217;s definition into a module that
does &lt;em&gt;not&lt;/em&gt; export the type&amp;#8217;s data constructors.  That means we will not
be able to create &lt;em&gt;SafeString&lt;/em&gt; values for ourselves.  Instead, we must
ask a small set of kernel functions, which &lt;em&gt;are&lt;/em&gt; exported, to create the
values on our behalf.&lt;/p&gt;


	&lt;p&gt;These kernel functions, which we are about to write,
will create &lt;em&gt;SafeString&lt;/em&gt; values only in accordance with our
safe-string-handling rule.  In particular, they will require us
to &lt;em&gt;certify&lt;/em&gt; that an existing string represents either text or a language
fragment before creating a corresponding &lt;em&gt;SafeString&lt;/em&gt; value
for us.  From then on, the type system will know
which language the string is associated with and prevent us from
joining it to regular strings or to &lt;em&gt;SafeString&lt;/em&gt; values associated
with other languages.&lt;/p&gt;


	&lt;p&gt;Let&amp;#8217;s write these constructor functions now:&lt;/p&gt;


&lt;div class="typocode"&gt;&lt;pre&gt;&lt;code class="typocode_haskell "&gt;&lt;span class='varid'&gt;empty&lt;/span&gt;      &lt;span class='keyglyph'&gt;::&lt;/span&gt; &lt;span class='conid'&gt;Language&lt;/span&gt; &lt;span class='varid'&gt;l&lt;/span&gt; &lt;span class='keyglyph'&gt;=&amp;gt;&lt;/span&gt; &lt;span class='conid'&gt;SafeString&lt;/span&gt; &lt;span class='varid'&gt;l&lt;/span&gt;
&lt;span class='varid'&gt;empty&lt;/span&gt;       &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='conid'&gt;SSEmpty&lt;/span&gt;

&lt;span class='varid'&gt;frag&lt;/span&gt;&lt;span class='layout'&gt;,&lt;/span&gt; &lt;span class='varid'&gt;text&lt;/span&gt; &lt;span class='keyglyph'&gt;::&lt;/span&gt; &lt;span class='conid'&gt;Language&lt;/span&gt; &lt;span class='varid'&gt;l&lt;/span&gt; &lt;span class='keyglyph'&gt;=&amp;gt;&lt;/span&gt; &lt;span class='conid'&gt;String&lt;/span&gt; &lt;span class='keyglyph'&gt;-&amp;gt;&lt;/span&gt; &lt;span class='conid'&gt;SafeString&lt;/span&gt; &lt;span class='varid'&gt;l&lt;/span&gt;
&lt;span class='varid'&gt;frag&lt;/span&gt; &lt;span class='varid'&gt;f&lt;/span&gt;      &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='conid'&gt;SSFragment&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;litfrag&lt;/span&gt; &lt;span class='varid'&gt;f&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;
&lt;span class='varid'&gt;text&lt;/span&gt; &lt;span class='varid'&gt;s&lt;/span&gt;      &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='conid'&gt;SSFragment&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;littext&lt;/span&gt; &lt;span class='varid'&gt;s&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

	&lt;p&gt;Here&amp;#8217;s what the functions do:&lt;/p&gt;


	&lt;ul&gt;
	&lt;li&gt;&lt;em&gt;empty&lt;/em&gt; &amp;#8211; creates an empty &lt;em&gt;SafeString&lt;/em&gt; in the &lt;em&gt;Language l&lt;/em&gt;&lt;/li&gt;
		&lt;li&gt;&lt;em&gt;frag f&lt;/em&gt; &amp;#8211; takes a string that you certify as representing a fragment in the &lt;em&gt;Language l&lt;/em&gt; and returns a corresponding &lt;em&gt;SafeString&lt;/em&gt;&lt;/li&gt;
		&lt;li&gt;&lt;em&gt;text s&lt;/em&gt; &amp;#8211; takes a string that you certify as representing text and returns a corresponding &lt;em&gt;SafeString&lt;/em&gt; in the &lt;em&gt;Language l&lt;/em&gt;&lt;/li&gt;
	&lt;/ul&gt;


	&lt;p&gt;Once the kernel creates &lt;em&gt;SafeString&lt;/em&gt; values for us, we need some way
to combine them safely.  Thus we define the &lt;code&gt;(+++)&lt;/code&gt;
operator and the &lt;em&gt;cat&lt;/em&gt; function:&lt;/p&gt;


&lt;div class="typocode"&gt;&lt;pre&gt;&lt;code class="typocode_haskell "&gt;&lt;span class='comment'&gt;-- join two SafeStrings of the same language&lt;/span&gt;
&lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varop'&gt;+++&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt; &lt;span class='keyglyph'&gt;::&lt;/span&gt; &lt;span class='conid'&gt;Language&lt;/span&gt; &lt;span class='varid'&gt;l&lt;/span&gt; &lt;span class='keyglyph'&gt;=&amp;gt;&lt;/span&gt; &lt;span class='conid'&gt;SafeString&lt;/span&gt; &lt;span class='varid'&gt;l&lt;/span&gt; &lt;span class='keyglyph'&gt;-&amp;gt;&lt;/span&gt; &lt;span class='conid'&gt;SafeString&lt;/span&gt; &lt;span class='varid'&gt;l&lt;/span&gt; &lt;span class='keyglyph'&gt;-&amp;gt;&lt;/span&gt; &lt;span class='conid'&gt;SafeString&lt;/span&gt; &lt;span class='varid'&gt;l&lt;/span&gt;
&lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varop'&gt;+++&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;  &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='conid'&gt;SSCat&lt;/span&gt;

&lt;span class='comment'&gt;-- join a list of same-language SafeStrings&lt;/span&gt;
&lt;span class='varid'&gt;cat&lt;/span&gt;   &lt;span class='keyglyph'&gt;::&lt;/span&gt; &lt;span class='conid'&gt;Language&lt;/span&gt; &lt;span class='varid'&gt;l&lt;/span&gt; &lt;span class='keyglyph'&gt;=&amp;gt;&lt;/span&gt; &lt;span class='keyglyph'&gt;[&lt;/span&gt;&lt;span class='conid'&gt;SafeString&lt;/span&gt; &lt;span class='varid'&gt;l&lt;/span&gt;&lt;span class='keyglyph'&gt;]&lt;/span&gt; &lt;span class='keyglyph'&gt;-&amp;gt;&lt;/span&gt; &lt;span class='conid'&gt;SafeString&lt;/span&gt; &lt;span class='varid'&gt;l&lt;/span&gt;
&lt;span class='varid'&gt;cat&lt;/span&gt;    &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='varid'&gt;foldr&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varop'&gt;+++&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt; &lt;span class='varid'&gt;empty&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

	&lt;p&gt;Finally, we need a way to convert &lt;em&gt;SafeString&lt;/em&gt; values into normal
strings so that we can pass them through the boundaries of our
safe-string-protected code and into the outside world.  For this,
we write the &lt;em&gt;render&lt;/em&gt; function:&lt;/p&gt;


&lt;div class="typocode"&gt;&lt;pre&gt;&lt;code class="typocode_haskell "&gt;&lt;span class='varid'&gt;render&lt;/span&gt; &lt;span class='varid'&gt;ss&lt;/span&gt; &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='varid'&gt;renders&lt;/span&gt; &lt;span class='varid'&gt;ss&lt;/span&gt; &lt;span class='str'&gt;""&lt;/span&gt;

&lt;span class='varid'&gt;renders&lt;/span&gt; &lt;span class='conid'&gt;SSEmpty&lt;/span&gt;        &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='varid'&gt;id&lt;/span&gt;
&lt;span class='varid'&gt;renders&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='conid'&gt;SSFragment&lt;/span&gt; &lt;span class='varid'&gt;a&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt; &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;natrep&lt;/span&gt; &lt;span class='varid'&gt;a&lt;/span&gt; &lt;span class='varop'&gt;++&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;
&lt;span class='varid'&gt;renders&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='conid'&gt;SSCat&lt;/span&gt; &lt;span class='varid'&gt;l&lt;/span&gt; &lt;span class='varid'&gt;r&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;    &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='varid'&gt;renders&lt;/span&gt; &lt;span class='varid'&gt;l&lt;/span&gt; &lt;span class='varop'&gt;.&lt;/span&gt; &lt;span class='varid'&gt;renders&lt;/span&gt; &lt;span class='varid'&gt;r&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

	&lt;p&gt;(Don&amp;#8217;t worry about the &lt;em&gt;renders&lt;/em&gt; stuff.  It implements
a Haskell idiom for fast string concatenation.)&lt;/p&gt;


	&lt;p&gt;As a convenience, let&amp;#8217;s round out our kernel with a &lt;em&gt;Show&lt;/em&gt; instance
that tells Haskell how to format
&lt;em&gt;SafeString&lt;/em&gt; values for display.&lt;/p&gt;


&lt;div class="typocode"&gt;&lt;pre&gt;&lt;code class="typocode_haskell "&gt;&lt;span class='keyword'&gt;instance&lt;/span&gt; &lt;span class='conid'&gt;Language&lt;/span&gt; &lt;span class='varid'&gt;l&lt;/span&gt; &lt;span class='keyglyph'&gt;=&amp;gt;&lt;/span&gt; &lt;span class='conid'&gt;Show&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='conid'&gt;SafeString&lt;/span&gt; &lt;span class='varid'&gt;l&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt; &lt;span class='keyword'&gt;where&lt;/span&gt;
    &lt;span class='varid'&gt;showsPrec&lt;/span&gt; &lt;span class='keyword'&gt;_&lt;/span&gt; &lt;span class='varid'&gt;ss&lt;/span&gt; &lt;span class='keyglyph'&gt;=&lt;/span&gt;
        &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;lang&lt;/span&gt; &lt;span class='varid'&gt;ss&lt;/span&gt; &lt;span class='varop'&gt;++&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt; &lt;span class='varop'&gt;.&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='str'&gt;":\""&lt;/span&gt; &lt;span class='varop'&gt;++&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt; &lt;span class='varop'&gt;.&lt;/span&gt; &lt;span class='varid'&gt;renders&lt;/span&gt; &lt;span class='varid'&gt;ss&lt;/span&gt; &lt;span class='varop'&gt;.&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='chr'&gt;'"'&lt;/span&gt;&lt;span class='conop'&gt;:&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;

&lt;span class='varid'&gt;lang&lt;/span&gt; &lt;span class='varid'&gt;ss&lt;/span&gt; &lt;span class='keyglyph'&gt;=&lt;/span&gt;
    &lt;span class='keyword'&gt;let&lt;/span&gt; &lt;span class='conid'&gt;SSFragment&lt;/span&gt; &lt;span class='varid'&gt;e&lt;/span&gt; &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='varid'&gt;ss&lt;/span&gt; &lt;span class='keyword'&gt;in&lt;/span&gt; &lt;span class='varid'&gt;language&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;undefined&lt;/span&gt; &lt;span class='varop'&gt;`asTypeOf`&lt;/span&gt; &lt;span class='varid'&gt;e&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

	&lt;p&gt;And that&amp;#8217;s our SafeStrings kernel.&lt;/p&gt;


	&lt;h3&gt; Another look at the SafeStrings kernel&lt;/h3&gt;


	&lt;p&gt;The following illustration, complete with poorly chosen colors, provides a
visual summary of our system:&lt;/p&gt;


&lt;p style="text-align: center"&gt;
&lt;img src="http://community.moertel.com/~thor/pix/20060908/safe-strings.png" title="Stunning visual interpretation of the SafeStrings kernel and its relationship to the evil outside world" alt="Stunning visual interpretation of the SafeStrings kernel and its relationship to the evil outside world" /&gt;
&lt;/p&gt;

	&lt;p&gt;(Don&amp;#8217;t worry about the &lt;code&gt;$(q ...)&lt;/code&gt; stuff for the
moment, we&amp;#8217;ll talk about it later.)&lt;/p&gt;


	&lt;p&gt;Activating our mad art-interpretation skillz, we can
now decipher the illustration:&lt;/p&gt;


	&lt;p&gt;&lt;em&gt;Regular strings gain &amp;#8220;admittance&amp;#8221; to the SafeStrings kernel only
via the &lt;/em&gt;text&lt;em&gt; and &lt;/em&gt;frag&lt;em&gt; certification functions, which
we use to create corresponding safe strings for a given language.
Once created, the safe strings live their entire lives in the
fleshy-colored, egg-shaped protective sac that is the kernel, whose
safe-string functions and operators use Haskell&amp;#8217;s type system to
prevent us from accidentally mixing the strings in unsafe
ways. Further, because the kernel does not export its underlying data
structures, we can&amp;#8217;t screw around with the innards of our safe strings to
break the kernel&amp;#8217;s promises.  When our safe strings have finally
reached their ultimate, beautiful state, we can &lt;/em&gt;render&lt;em&gt; them
into regular strings and pass them bravely into the cruel outside
world &amp;#8211; where, most likely, somebody else&amp;#8217;s broken code will screw
them up anyway.  But at least we tried.&lt;/em&gt;&lt;/p&gt;


	&lt;h3&gt;Our first SafeString module: SafeXml&lt;/h3&gt;


	&lt;p&gt;Now that we have written our SafeStrings kernel, let&amp;#8217;s use it to
create a SafeXml module that we can use for working with &lt;span class="caps"&gt;XML&lt;/span&gt;.
Again, we will be writing library code that under normal
circumstances would be hidden from view.&lt;/p&gt;


	&lt;p&gt;First, we will create a new module that uses the SafeStrings kernel:&lt;/p&gt;


&lt;div class="typocode"&gt;&lt;pre&gt;&lt;code class="typocode_haskell "&gt;&lt;span class='keyword'&gt;module&lt;/span&gt; &lt;span class='conid'&gt;SafeXml&lt;/span&gt;
&lt;span class='layout'&gt;(&lt;/span&gt; &lt;span class='conid'&gt;Xml&lt;/span&gt;&lt;span class='layout'&gt;,&lt;/span&gt; &lt;span class='varid'&gt;xml&lt;/span&gt;&lt;span class='layout'&gt;,&lt;/span&gt; &lt;span class='varid'&gt;renderXml&lt;/span&gt;&lt;span class='layout'&gt;,&lt;/span&gt; &lt;span class='keyword'&gt;module&lt;/span&gt; &lt;span class='conid'&gt;SafeStrings&lt;/span&gt; &lt;span class='layout'&gt;)&lt;/span&gt;
&lt;span class='keyword'&gt;where&lt;/span&gt;
&lt;span class='keyword'&gt;import&lt;/span&gt; &lt;span class='conid'&gt;SafeStrings&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

	&lt;p&gt;Next, we will create a wrapper type to testify
that a string represents a fragment of &lt;span class="caps"&gt;XML&lt;/span&gt;:&lt;/p&gt;


&lt;div class="typocode"&gt;&lt;pre&gt;&lt;code class="typocode_haskell "&gt;&lt;span class='keyword'&gt;newtype&lt;/span&gt; &lt;span class='conid'&gt;XmlString&lt;/span&gt;
    &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='conid'&gt;XmlString&lt;/span&gt; &lt;span class='layout'&gt;{&lt;/span&gt; &lt;span class='varid'&gt;unXmlString&lt;/span&gt; &lt;span class='keyglyph'&gt;::&lt;/span&gt; &lt;span class='conid'&gt;String&lt;/span&gt; &lt;span class='layout'&gt;}&lt;/span&gt;
    &lt;span class='keyword'&gt;deriving&lt;/span&gt; &lt;span class='conid'&gt;Show&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

	&lt;p&gt;If you go back and look at the export list for the module, you&amp;#8217;ll see
that the &lt;em&gt;XmlString&lt;/em&gt; data type is not exported.  It is internal to the
module, and thus we, as clients of the module, can&amp;#8217;t create values of
that type.  That means we can&amp;#8217;t &amp;#8220;forge&amp;#8221; &lt;span class="caps"&gt;XML&lt;/span&gt; strings into existence.
We can create them only through the safe-string kernel, and even then
only by certifying a regular string as representing text or a language
fragment.  (The kernel, in turn, will create the needed values through
the &lt;em&gt;Language&lt;/em&gt; interface, which we now discuss.)&lt;/p&gt;


	&lt;p&gt;Like all good language types, &lt;em&gt;XmlString&lt;/em&gt; needs to be a member of the
&lt;em&gt;Language&lt;/em&gt; type class, so we provide the necessary instance functions:&lt;/p&gt;


&lt;div class="typocode"&gt;&lt;pre&gt;&lt;code class="typocode_haskell "&gt;&lt;span class='keyword'&gt;instance&lt;/span&gt; &lt;span class='conid'&gt;Language&lt;/span&gt; &lt;span class='conid'&gt;XmlString&lt;/span&gt; &lt;span class='keyword'&gt;where&lt;/span&gt;
    &lt;span class='varid'&gt;litfrag&lt;/span&gt;  &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='conid'&gt;XmlString&lt;/span&gt;
    &lt;span class='varid'&gt;littext&lt;/span&gt;  &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='conid'&gt;XmlString&lt;/span&gt; &lt;span class='varop'&gt;.&lt;/span&gt; &lt;span class='varid'&gt;escapeXml&lt;/span&gt;
    &lt;span class='varid'&gt;natrep&lt;/span&gt;   &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='varid'&gt;unXmlString&lt;/span&gt;
    &lt;span class='varid'&gt;language&lt;/span&gt; &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='varid'&gt;const&lt;/span&gt; &lt;span class='str'&gt;"xml"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

	&lt;p&gt;Note that the functions satisfy the language laws
we defined earlier.  (The proof follows immediately from the definitions
of &lt;em&gt;XmlString&lt;/em&gt;, &lt;em&gt;unXmlString&lt;/em&gt;, and &lt;em&gt;escapeXml&lt;/em&gt;.)&lt;/p&gt;


	&lt;p&gt;Next, we need to write a function to implement the escaping
rule for &lt;span class="caps"&gt;XML&lt;/span&gt;:&lt;/p&gt;


&lt;div class="typocode"&gt;&lt;pre&gt;&lt;code class="typocode_haskell "&gt;&lt;span class='varid'&gt;escapeXml&lt;/span&gt; &lt;span class='varid'&gt;xs&lt;/span&gt; &lt;span class='keyglyph'&gt;=&lt;/span&gt;
    &lt;span class='varid'&gt;concatMap&lt;/span&gt; &lt;span class='varid'&gt;esc&lt;/span&gt; &lt;span class='varid'&gt;xs&lt;/span&gt;
  &lt;span class='keyword'&gt;where&lt;/span&gt;
    &lt;span class='varid'&gt;esc&lt;/span&gt; &lt;span class='chr'&gt;'&amp;lt;'&lt;/span&gt;  &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='str'&gt;"&amp;amp;lt;"&lt;/span&gt;
    &lt;span class='varid'&gt;esc&lt;/span&gt; &lt;span class='chr'&gt;'&amp;gt;'&lt;/span&gt;  &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='str'&gt;"&amp;amp;gt;"&lt;/span&gt;
    &lt;span class='varid'&gt;esc&lt;/span&gt; &lt;span class='chr'&gt;'&amp;amp;'&lt;/span&gt;  &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='str'&gt;"&amp;amp;amp;"&lt;/span&gt;
    &lt;span class='varid'&gt;esc&lt;/span&gt; &lt;span class='chr'&gt;'"'&lt;/span&gt;  &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='str'&gt;"&amp;amp;#34;"&lt;/span&gt;
    &lt;span class='varid'&gt;esc&lt;/span&gt; &lt;span class='chr'&gt;'\''&lt;/span&gt; &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='str'&gt;"&amp;amp;#39;"&lt;/span&gt;
    &lt;span class='varid'&gt;esc&lt;/span&gt; &lt;span class='varid'&gt;x&lt;/span&gt;    &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='keyglyph'&gt;[&lt;/span&gt;&lt;span class='varid'&gt;x&lt;/span&gt;&lt;span class='keyglyph'&gt;]&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

	&lt;p&gt;Next, because we expect to work with &lt;span class="caps"&gt;XML&lt;/span&gt; frequently, we will create a
convenient type synonym, &lt;em&gt;Xml&lt;/em&gt;, for &lt;em&gt;SafeString&lt;/em&gt; values that represent
&lt;span class="caps"&gt;XML&lt;/span&gt;:&lt;/p&gt;


&lt;div class="typocode"&gt;&lt;pre&gt;&lt;code class="typocode_haskell "&gt;&lt;span class='keyword'&gt;type&lt;/span&gt; &lt;span class='conid'&gt;Xml&lt;/span&gt; &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='conid'&gt;SafeString&lt;/span&gt; &lt;span class='conid'&gt;XmlString&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

	&lt;p&gt;Finally, we will create
a few convenience functions to create and render &lt;span class="caps"&gt;XML&lt;/span&gt; fragments.  These
functions are identical to the SafeString kernel&amp;#8217;s &lt;em&gt;frag&lt;/em&gt; and &lt;em&gt;render&lt;/em&gt;
functions but for the &lt;em&gt;Xml&lt;/em&gt; type exclusively.  When we use these
functions, we won&amp;#8217;t need to provide additional type annotations; the
computer will know we are dealing with &lt;span class="caps"&gt;XML&lt;/span&gt; strings:&lt;/p&gt;


&lt;div class="typocode"&gt;&lt;pre&gt;&lt;code class="typocode_haskell "&gt;&lt;span class='varid'&gt;xml&lt;/span&gt; &lt;span class='keyglyph'&gt;::&lt;/span&gt; &lt;span class='conid'&gt;String&lt;/span&gt; &lt;span class='keyglyph'&gt;-&amp;gt;&lt;/span&gt; &lt;span class='conid'&gt;Xml&lt;/span&gt;
&lt;span class='varid'&gt;xml&lt;/span&gt; &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='varid'&gt;frag&lt;/span&gt;

&lt;span class='varid'&gt;renderXml&lt;/span&gt; &lt;span class='keyglyph'&gt;::&lt;/span&gt; &lt;span class='conid'&gt;Xml&lt;/span&gt; &lt;span class='keyglyph'&gt;-&amp;gt;&lt;/span&gt; &lt;span class='conid'&gt;String&lt;/span&gt;
&lt;span class='varid'&gt;renderXml&lt;/span&gt; &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='varid'&gt;render&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

	&lt;p&gt;And we&amp;#8217;re done.&lt;/p&gt;


	&lt;p&gt;Before going on, let me point out two things:&lt;/p&gt;


	&lt;ol&gt;
	&lt;li&gt;If you think the code we have written so far is long or perhaps confusing, please remember that it is &lt;em&gt;library code&lt;/em&gt;.  Typically, you would never see it.  All you would do is &lt;code&gt;import SafeXml&lt;/code&gt; and start using the library.&lt;/li&gt;
		&lt;li&gt;The SafeXml implementation is formulaic, and we can replace all of it except for the escaping function&amp;#8217;s definition with a single line of code, something we will do later.&lt;/li&gt;
	&lt;/ol&gt;


	&lt;h3&gt; A quick test drive of our SafeXml module&lt;/h3&gt;


	&lt;p&gt;Let&amp;#8217;s give our SafeXml module a spin in the &lt;span class="caps"&gt;GHC&lt;/span&gt; interactive shell.&lt;/p&gt;


	&lt;p&gt;We can create an &lt;span class="caps"&gt;XML&lt;/span&gt; fragment by certifying that a regular string
represents a language fragment (via the &lt;em&gt;frag&lt;/em&gt; function) and telling
Haskell that we expect a result of type &lt;em&gt;Xml&lt;/em&gt;.&lt;/p&gt;


&lt;pre&gt;&lt;code&gt;Ok, modules loaded: SafeXml, SafeStrings.
*SafeXml&amp;gt; frag "&amp;lt;em&amp;gt;wow!&amp;lt;/em&amp;gt;" :: Xml
xml:"&amp;lt;em&amp;gt;wow!&amp;lt;/em&amp;gt;" 
&lt;/code&gt;&lt;/pre&gt;

	&lt;p&gt;Note how the output is prefixed with the label &amp;#8220;xml:&amp;#8221; 
to tell us that our kernel certifies this value to represent an &lt;span class="caps"&gt;XML&lt;/span&gt; fragment.&lt;/p&gt;


	&lt;p&gt;Because entering type annotations can be inconvenient, we can instead
use the &lt;em&gt;xml&lt;/em&gt; function, which certifies a string not just as a
fragment but as an &lt;span class="caps"&gt;XML&lt;/span&gt; fragment:&lt;/p&gt;


&lt;pre&gt;&lt;code&gt;*SafeXml&amp;gt; xml "&amp;lt;em&amp;gt;wow!&amp;lt;/em&amp;gt;" 
xml:"&amp;lt;em&amp;gt;wow!&amp;lt;/em&amp;gt;" 
&lt;/code&gt;&lt;/pre&gt;

	&lt;p&gt;If we want to represent text in &lt;span class="caps"&gt;XML&lt;/span&gt;, the kernel will automatically
escape it for us:&lt;/p&gt;


&lt;pre&gt;&lt;code&gt;*SafeXml&amp;gt; text "ham &amp;#38; eggs" :: Xml
xml:"ham &amp;amp;amp; eggs" 
&lt;/code&gt;&lt;/pre&gt;

	&lt;p&gt;Now let&amp;#8217;s try to do something naughty.  Will the type system
let us?&lt;/p&gt;


&lt;pre&gt;&lt;code&gt;*SafeXml&amp;gt; let someXml = xml "&amp;lt;em&amp;gt;Hi!&amp;lt;/em&amp;gt;" 
*SafeXml&amp;gt; let plainOldText = "ham &amp;#38; eggs" 
*SafeXml&amp;gt; someXml ++ plainOldText

&amp;lt;interactive&amp;gt;:1:0:
    Couldn't match `[a]' against `Xml'
      Expected type: [a]
      Inferred type: Xml
    In the first argument of `(++)', namely `someXml'
    In the definition of `it': it = someXml ++ plainOldText
&lt;/code&gt;&lt;/pre&gt;

	&lt;p&gt;In Haskell, the &lt;code&gt;(++)&lt;/code&gt; operator is used (among
other things) to join strings.  In the code above, we tried
to use this operator to join an &lt;span class="caps"&gt;XML&lt;/span&gt; fragment to a plain-old
string, which would have violated our safe-string-handling rule.
Fortunately, we were unable to fool the type system into
allowing this ill-conceived union to occur.&lt;/p&gt;


	&lt;p&gt;In fact, the union was never even attempted: our mistake was caught at
compile time, before the code was ever converted into executable form.
This is a big deal. Mistakes like this are &lt;em&gt;programming errors&lt;/em&gt; that
open security holes.  Being able to catch these errors at compile time
means you have the opportunity to track the errors to their source and
fix them there.  If you caught ill-conceived string unions only at run
time, the logical errors that led to the attempted unions could have
been in upstream code that has already executed &amp;#8211; launching the
missiles, perhaps.  By then, it may be too late to undo the
consequences.&lt;/p&gt;


	&lt;p&gt;Returning to our example, if we certify that the plain-old string
represents text, we can make a safe union, so the type system
lets us go ahead:&lt;/p&gt;


&lt;pre&gt;&lt;code&gt;*SafeXml&amp;gt; someXml +++ text plainOldText
xml:"&amp;lt;em&amp;gt;Hi!&amp;lt;/em&amp;gt;ham &amp;amp;amp; eggs" 
&lt;/code&gt;&lt;/pre&gt;

	&lt;p&gt;And that&amp;#8217;s basically all there is to it.&lt;/p&gt;


	&lt;h3&gt;Syntactic sugar for safe strings&lt;/h3&gt;


	&lt;p&gt;Not having to worry about the strings problem is fabulous and
all, but having to type in &lt;em&gt;frag&lt;/em&gt;, &lt;em&gt;text&lt;/em&gt;, and &lt;code&gt;+++&lt;/code&gt; is
kind of clunky.  Let&amp;#8217;s get rid of the clunkiness by introducing some
syntactic sugar.&lt;/p&gt;


&lt;p&gt;The common case when dealing with strings in web applications is
templates.  For example, here&amp;#8217;s a simplified version of the
&lt;code&gt;link_to&lt;/code&gt; method from the deservedly popular &lt;a href="http://www.rubyonrails.com/"&gt;Ruby on
Rails&lt;/a&gt;.  The method wraps a hypertext link
around some content by &amp;#8220;interpolating&amp;#8221; the content and a &lt;span class="caps"&gt;URL&lt;/span&gt;
into a link template:&lt;/p&gt;

&lt;pre&gt;&lt;code&gt;# NOTE: this example is in Ruby

def link_to(content_xhtml, url)
  "&amp;lt;a href=\"#{h url}\"&amp;gt;#{content_xhtml}&amp;lt;/a&amp;gt;" 
end
&lt;/code&gt;&lt;/pre&gt;

	&lt;p&gt;In this code, we need to &lt;span class="caps"&gt;HTML&lt;/span&gt;-escape the &lt;span class="caps"&gt;URL&lt;/span&gt; (via the &lt;code&gt;h&lt;/code&gt;
helper) before interpolating it
into the template.  We do not need to escape the content, however,
because it is already in the template&amp;#8217;s language, &lt;span class="caps"&gt;XHTML&lt;/span&gt;.&lt;/p&gt;


	&lt;p&gt;Now, to introduce our syntactic sugar, here&amp;#8217;s &lt;code&gt;link_to&lt;/code&gt;
rewritten in Haskell and using safe strings:&lt;/p&gt;


&lt;div class="typocode"&gt;&lt;pre&gt;&lt;code class="typocode_haskell "&gt;&lt;span class='comment'&gt;-- Haskell code&lt;/span&gt;

&lt;span class='varid'&gt;link_to&lt;/span&gt; &lt;span class='keyglyph'&gt;::&lt;/span&gt; &lt;span class='conid'&gt;Xhtml&lt;/span&gt; &lt;span class='keyglyph'&gt;-&amp;gt;&lt;/span&gt; &lt;span class='conid'&gt;Url&lt;/span&gt; &lt;span class='keyglyph'&gt;-&amp;gt;&lt;/span&gt; &lt;span class='conid'&gt;Xhtml&lt;/span&gt;
&lt;span class='varid'&gt;link_to&lt;/span&gt; &lt;span class='varid'&gt;content&lt;/span&gt; &lt;span class='varid'&gt;url&lt;/span&gt; &lt;span class='keyglyph'&gt;=&lt;/span&gt;
    &lt;span class='varop'&gt;$&lt;/span&gt;&lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;q&lt;/span&gt; &lt;span class='str'&gt;"&amp;lt;a href=\"#{r url}\"&amp;gt;#{=content}&amp;lt;/a&amp;gt;"&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

	&lt;p&gt;The type signature makes clear to everybody that the &lt;em&gt;content&lt;/em&gt;
parameter is &lt;span class="caps"&gt;XHTML&lt;/span&gt;, the &lt;em&gt;url&lt;/em&gt; parameter is a &lt;span class="caps"&gt;URL&lt;/span&gt;, and the result is
&lt;span class="caps"&gt;XHTML&lt;/span&gt;.  The signature isn&amp;#8217;t needed, but &lt;code&gt;link_to&lt;/code&gt; is the
stuff of libraries, and so annotations are good form.&lt;/p&gt;


	&lt;p&gt;The interpolation syntax is like Ruby&amp;#8217;s, but with
slightly different modifiers:&lt;/p&gt;


	&lt;ul&gt;
	&lt;li&gt;The template-quoting syntax is &lt;code&gt;$(q "this is a template")&lt;/code&gt;.  (Mnemonic: &lt;code&gt;q&lt;/code&gt; for quote).&lt;/li&gt;
		&lt;li&gt;Within a template, we can interpolate variables using the familiar &lt;code&gt;#{var}&lt;/code&gt; syntax.&lt;/li&gt;
		&lt;li&gt;If an interpolated variable holds a plain string, it will be escaped into the template automatically.&lt;/li&gt;
		&lt;li&gt;If an interpolated variable holds a safe string, we must use an &lt;em&gt;interpolation modifier&lt;/em&gt; to specify how it should be interpolated (to avoid ambiguity):
	&lt;ul&gt;
	&lt;li&gt;&lt;code&gt;#{r var}&lt;/code&gt; renders the safe string in &lt;em&gt;var&lt;/em&gt; into text, and then interpolates the text into the template, escaping as necessary (mnemonic: &lt;code&gt;r&lt;/code&gt; for &lt;em&gt;render&lt;/em&gt;).&lt;/li&gt;
		&lt;li&gt;&lt;code&gt;#{= var}&lt;/code&gt; inserts the safe string in &lt;em&gt;var&lt;/em&gt; directly into the template, which must be of the same language (mnemonic: &lt;code&gt;=&lt;/code&gt; for &lt;em&gt;equal language types&lt;/em&gt;).&lt;/li&gt;
	&lt;/ul&gt;
	&lt;/li&gt;
		&lt;li&gt;As a bonus, &lt;code&gt;#{s var}&lt;/code&gt; interpolates any &lt;em&gt;Show&lt;/em&gt;-able value in &lt;em&gt;var&lt;/em&gt; into the template as text, escaping as necessary.&lt;/li&gt;
	&lt;/ul&gt;


	&lt;p&gt;It&amp;#8217;s pretty easy to tell which interpolation option is right for any
situation, but late-night coding sessions make fools of us all.
That&amp;#8217;s why the type system is there to catch us when we make a dumb mistake.&lt;/p&gt;


	&lt;p&gt;Let&amp;#8217;s try out the sugary &lt;code&gt;link_to&lt;/code&gt; method:&lt;/p&gt;


&lt;pre&gt;&lt;code&gt;&amp;gt; link_to (text "Tom's Weblog") (url "http://blog.moertel.com/")
xml:"&amp;lt;a href="http://blog.moertel.com/"&amp;gt;Tom's Weblog&amp;lt;/a&amp;gt;" 
&lt;/code&gt;&lt;/pre&gt;

	&lt;p&gt;Let&amp;#8217;s take advantage of type inferencing in the next example:&lt;/p&gt;


&lt;pre&gt;&lt;code&gt;&amp;gt; link_to $(q "&amp;lt;em&amp;gt;Espresso!&amp;lt;/em&amp;gt;")
          $(q "http://google.com/search?q=espresso&amp;#38;oe=utf-8")

xml:"&amp;lt;a href="http://google.com/search?q=espresso&amp;amp;amp;oe=utf-8"&amp;gt;
     &amp;lt;em&amp;gt;Espresso!&amp;lt;/em&amp;gt;&amp;lt;/a&amp;gt;" 
&lt;/code&gt;&lt;/pre&gt;

	&lt;p&gt;In the above example, we supplied templates as input parameters.
Haskell figured out their types and took care of the escaping (or not
escaping) for us.&lt;/p&gt;


	&lt;p&gt;Now that we know what the syntactic sugar looks like, let&amp;#8217;s
see how to implement it.&lt;/p&gt;


	&lt;h3&gt; Implementing the syntactic sugar using Template Haskell&lt;/h3&gt;


	&lt;p&gt;We implement the SafeString library&amp;#8217;s syntactic sugar using Template
Haskell.  A small function &lt;code&gt;q&lt;/code&gt; (for &amp;#8220;quote&amp;#8221;) parses the
sugared syntax at compile time and emits equivalent code using our
safe-string functions &lt;code&gt;frag&lt;/code&gt;, &lt;code&gt;text&lt;/code&gt;, and so on.
For example, the following sugar:&lt;/p&gt;


&lt;div class="typocode"&gt;&lt;pre&gt;&lt;code class="typocode_haskell "&gt;&lt;span class='varop'&gt;$&lt;/span&gt;&lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;q&lt;/span&gt; &lt;span class='str'&gt;"&amp;lt;em&amp;gt;#{mystr}&amp;lt;/em&amp;gt;"&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

	&lt;p&gt;becomes the following code:&lt;/p&gt;


&lt;div class="typocode"&gt;&lt;pre&gt;&lt;code class="typocode_haskell "&gt;&lt;span class='varid'&gt;cat&lt;/span&gt; &lt;span class='keyglyph'&gt;[&lt;/span&gt;&lt;span class='varid'&gt;frag&lt;/span&gt; &lt;span class='str'&gt;"&amp;lt;em&amp;gt;"&lt;/span&gt;&lt;span class='layout'&gt;,&lt;/span&gt; &lt;span class='varid'&gt;text&lt;/span&gt; &lt;span class='varid'&gt;mystr&lt;/span&gt;&lt;span class='layout'&gt;,&lt;/span&gt; &lt;span class='varid'&gt;frag&lt;/span&gt; &lt;span class='str'&gt;"&amp;lt;/em&amp;gt;"&lt;/span&gt;&lt;span class='keyglyph'&gt;]&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

	&lt;p&gt;The code that makes it happen is fairly straightforward if you know
Template Haskell, so I&amp;#8217;ll skip the explanation because this article
is already way too long.  As usual, it&amp;#8217;s library code, so normally we
wouldn&amp;#8217;t see it or care about it.  All we care about is the &lt;code&gt;$(q
"...")&lt;/code&gt; sugar that the code makes available to us.&lt;/p&gt;


	&lt;p&gt;Here it is:&lt;/p&gt;


&lt;div class="typocode"&gt;&lt;pre&gt;&lt;code class="typocode_haskell "&gt;&lt;span class='keyword'&gt;import&lt;/span&gt; &lt;span class='conid'&gt;Language&lt;/span&gt;&lt;span class='varop'&gt;.&lt;/span&gt;&lt;span class='conid'&gt;Haskell&lt;/span&gt;&lt;span class='varop'&gt;.&lt;/span&gt;&lt;span class='conid'&gt;TH&lt;/span&gt;
&lt;span class='keyword'&gt;import&lt;/span&gt; &lt;span class='varid'&gt;qualified&lt;/span&gt; &lt;span class='conid'&gt;Text&lt;/span&gt;&lt;span class='varop'&gt;.&lt;/span&gt;&lt;span class='conid'&gt;ParserCombinators&lt;/span&gt;&lt;span class='varop'&gt;.&lt;/span&gt;&lt;span class='conid'&gt;ReadP&lt;/span&gt; &lt;span class='keyword'&gt;as&lt;/span&gt; &lt;span class='conid'&gt;P&lt;/span&gt;

&lt;span class='comment'&gt;-- Convert template sugar into calls to frag, text, cat, etc.&lt;/span&gt;
&lt;span class='comment'&gt;-- This function is exported by the SafeStrings module.&lt;/span&gt;

&lt;span class='varid'&gt;q&lt;/span&gt; &lt;span class='varid'&gt;spec&lt;/span&gt; &lt;span class='keyglyph'&gt;=&lt;/span&gt;
    &lt;span class='keyglyph'&gt;[&lt;/span&gt;&lt;span class='keyglyph'&gt;|&lt;/span&gt; &lt;span class='varid'&gt;cat&lt;/span&gt; &lt;span class='varop'&gt;$&lt;/span&gt;&lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;parts&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt; &lt;span class='keyglyph'&gt;|&lt;/span&gt;&lt;span class='keyglyph'&gt;]&lt;/span&gt;
  &lt;span class='keyword'&gt;where&lt;/span&gt;
    &lt;span class='varid'&gt;parts&lt;/span&gt; &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='keyword'&gt;case&lt;/span&gt; &lt;span class='varid'&gt;xparse&lt;/span&gt; &lt;span class='varid'&gt;spec&lt;/span&gt; &lt;span class='keyword'&gt;of&lt;/span&gt;
        &lt;span class='keyglyph'&gt;[&lt;/span&gt;&lt;span class='keyglyph'&gt;]&lt;/span&gt;   &lt;span class='keyglyph'&gt;-&amp;gt;&lt;/span&gt; &lt;span class='varid'&gt;error&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='str'&gt;"bad template: "&lt;/span&gt; &lt;span class='varop'&gt;++&lt;/span&gt; &lt;span class='varid'&gt;show&lt;/span&gt; &lt;span class='varid'&gt;spec&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;
        &lt;span class='varid'&gt;ps&lt;/span&gt;&lt;span class='conop'&gt;:&lt;/span&gt;&lt;span class='keyword'&gt;_&lt;/span&gt; &lt;span class='keyglyph'&gt;-&amp;gt;&lt;/span&gt; &lt;span class='varid'&gt;foldr&lt;/span&gt; &lt;span class='varid'&gt;gen&lt;/span&gt; &lt;span class='keyglyph'&gt;[&lt;/span&gt;&lt;span class='keyglyph'&gt;|&lt;/span&gt; &lt;span class='keyglyph'&gt;[&lt;/span&gt;&lt;span class='keyglyph'&gt;]&lt;/span&gt; &lt;span class='keyglyph'&gt;|&lt;/span&gt;&lt;span class='keyglyph'&gt;]&lt;/span&gt; &lt;span class='varid'&gt;ps&lt;/span&gt;
    &lt;span class='varid'&gt;gen&lt;/span&gt; &lt;span class='varid'&gt;p&lt;/span&gt; &lt;span class='varid'&gt;ps'&lt;/span&gt; &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='keyglyph'&gt;\&lt;/span&gt;&lt;span class='varid'&gt;p'&lt;/span&gt; &lt;span class='keyglyph'&gt;-&amp;gt;&lt;/span&gt; &lt;span class='keyglyph'&gt;[&lt;/span&gt;&lt;span class='keyglyph'&gt;|&lt;/span&gt; &lt;span class='varop'&gt;$&lt;/span&gt;&lt;span class='varid'&gt;p'&lt;/span&gt; &lt;span class='conop'&gt;:&lt;/span&gt; &lt;span class='varop'&gt;$&lt;/span&gt;&lt;span class='varid'&gt;ps'&lt;/span&gt; &lt;span class='keyglyph'&gt;|&lt;/span&gt;&lt;span class='keyglyph'&gt;]&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt; &lt;span class='varop'&gt;$&lt;/span&gt; &lt;span class='keyword'&gt;case&lt;/span&gt; &lt;span class='varid'&gt;p&lt;/span&gt; &lt;span class='keyword'&gt;of&lt;/span&gt;
        &lt;span class='conid'&gt;SFrag&lt;/span&gt; &lt;span class='varid'&gt;s&lt;/span&gt;  &lt;span class='keyglyph'&gt;-&amp;gt;&lt;/span&gt; &lt;span class='keyglyph'&gt;[&lt;/span&gt;&lt;span class='keyglyph'&gt;|&lt;/span&gt; &lt;span class='varid'&gt;frag&lt;/span&gt; &lt;span class='varop'&gt;$&lt;/span&gt;&lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;litE&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;stringL&lt;/span&gt; &lt;span class='varid'&gt;s&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;         &lt;span class='keyglyph'&gt;|&lt;/span&gt;&lt;span class='keyglyph'&gt;]&lt;/span&gt;
        &lt;span class='conid'&gt;SIFrag&lt;/span&gt; &lt;span class='varid'&gt;s&lt;/span&gt; &lt;span class='keyglyph'&gt;-&amp;gt;&lt;/span&gt; &lt;span class='keyglyph'&gt;[&lt;/span&gt;&lt;span class='keyglyph'&gt;|&lt;/span&gt; &lt;span class='varop'&gt;$&lt;/span&gt;&lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;varE&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;mkName&lt;/span&gt; &lt;span class='varid'&gt;s&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;               &lt;span class='keyglyph'&gt;|&lt;/span&gt;&lt;span class='keyglyph'&gt;]&lt;/span&gt;
        &lt;span class='conid'&gt;SIShow&lt;/span&gt; &lt;span class='varid'&gt;s&lt;/span&gt; &lt;span class='keyglyph'&gt;-&amp;gt;&lt;/span&gt; &lt;span class='keyglyph'&gt;[&lt;/span&gt;&lt;span class='keyglyph'&gt;|&lt;/span&gt; &lt;span class='varid'&gt;text&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;show&lt;/span&gt; &lt;span class='varop'&gt;$&lt;/span&gt;&lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;varE&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;mkName&lt;/span&gt; &lt;span class='varid'&gt;s&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;   &lt;span class='keyglyph'&gt;|&lt;/span&gt;&lt;span class='keyglyph'&gt;]&lt;/span&gt;
        &lt;span class='conid'&gt;SITxt&lt;/span&gt; &lt;span class='varid'&gt;s&lt;/span&gt;  &lt;span class='keyglyph'&gt;-&amp;gt;&lt;/span&gt; &lt;span class='keyglyph'&gt;[&lt;/span&gt;&lt;span class='keyglyph'&gt;|&lt;/span&gt; &lt;span class='varid'&gt;text&lt;/span&gt; &lt;span class='varop'&gt;$&lt;/span&gt;&lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;varE&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;mkName&lt;/span&gt; &lt;span class='varid'&gt;s&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;          &lt;span class='keyglyph'&gt;|&lt;/span&gt;&lt;span class='keyglyph'&gt;]&lt;/span&gt;
        &lt;span class='conid'&gt;SIRTxt&lt;/span&gt; &lt;span class='varid'&gt;s&lt;/span&gt; &lt;span class='keyglyph'&gt;-&amp;gt;&lt;/span&gt; &lt;span class='keyglyph'&gt;[&lt;/span&gt;&lt;span class='keyglyph'&gt;|&lt;/span&gt; &lt;span class='varid'&gt;text&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;render&lt;/span&gt; &lt;span class='varop'&gt;$&lt;/span&gt;&lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;varE&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;mkName&lt;/span&gt; &lt;span class='varid'&gt;s&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt; &lt;span class='keyglyph'&gt;|&lt;/span&gt;&lt;span class='keyglyph'&gt;]&lt;/span&gt;

&lt;span class='comment'&gt;-- AST for template-specification parts&lt;/span&gt;

&lt;span class='keyword'&gt;data&lt;/span&gt; &lt;span class='conid'&gt;SpecPart&lt;/span&gt;
    &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='conid'&gt;SFrag&lt;/span&gt; &lt;span class='conid'&gt;String&lt;/span&gt;  &lt;span class='comment'&gt;-- ^ language fragment&lt;/span&gt;
    &lt;span class='keyglyph'&gt;|&lt;/span&gt; &lt;span class='conid'&gt;SIFrag&lt;/span&gt; &lt;span class='conid'&gt;String&lt;/span&gt; &lt;span class='comment'&gt;-- ^ insert fragment by variable reference&lt;/span&gt;
    &lt;span class='keyglyph'&gt;|&lt;/span&gt; &lt;span class='conid'&gt;SIShow&lt;/span&gt; &lt;span class='conid'&gt;String&lt;/span&gt; &lt;span class='comment'&gt;-- ^ insert rendered variable via show&lt;/span&gt;
    &lt;span class='keyglyph'&gt;|&lt;/span&gt; &lt;span class='conid'&gt;SITxt&lt;/span&gt; &lt;span class='conid'&gt;String&lt;/span&gt;  &lt;span class='comment'&gt;-- ^ insert literal text variable&lt;/span&gt;
    &lt;span class='keyglyph'&gt;|&lt;/span&gt; &lt;span class='conid'&gt;SIRTxt&lt;/span&gt; &lt;span class='conid'&gt;String&lt;/span&gt; &lt;span class='comment'&gt;-- ^ insert rendered safe string var as text&lt;/span&gt;
  &lt;span class='keyword'&gt;deriving&lt;/span&gt; &lt;span class='conid'&gt;Show&lt;/span&gt;

&lt;span class='comment'&gt;-- Parse a template specification&lt;/span&gt;

&lt;span class='varid'&gt;xparse&lt;/span&gt; &lt;span class='varid'&gt;spec&lt;/span&gt; &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='keyword'&gt;do&lt;/span&gt;

    &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;result&lt;/span&gt;&lt;span class='layout'&gt;,&lt;/span&gt; &lt;span class='str'&gt;""&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt; &lt;span class='keyglyph'&gt;&amp;lt;-&lt;/span&gt; &lt;span class='conid'&gt;P&lt;/span&gt;&lt;span class='varop'&gt;.&lt;/span&gt;&lt;span class='varid'&gt;readP_to_S&lt;/span&gt; &lt;span class='varid'&gt;templateP&lt;/span&gt; &lt;span class='varid'&gt;spec&lt;/span&gt;
    &lt;span class='varid'&gt;return&lt;/span&gt; &lt;span class='varid'&gt;result&lt;/span&gt;
 &lt;span class='keyword'&gt;where&lt;/span&gt;
    &lt;span class='varid'&gt;templateP&lt;/span&gt; &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='keyword'&gt;do&lt;/span&gt;
        &lt;span class='conid'&gt;P&lt;/span&gt;&lt;span class='varop'&gt;.&lt;/span&gt;&lt;span class='varid'&gt;many&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;liftM&lt;/span&gt; &lt;span class='conid'&gt;SFrag&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='conid'&gt;P&lt;/span&gt;&lt;span class='varop'&gt;.&lt;/span&gt;&lt;span class='varid'&gt;munch1&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varop'&gt;/=&lt;/span&gt; &lt;span class='chr'&gt;'#'&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt; &lt;span class='conid'&gt;P&lt;/span&gt;&lt;span class='varop'&gt;.&amp;lt;++&lt;/span&gt;
                &lt;span class='varid'&gt;interpolationP&lt;/span&gt; &lt;span class='conid'&gt;P&lt;/span&gt;&lt;span class='varop'&gt;.&amp;lt;++&lt;/span&gt;
                &lt;span class='varid'&gt;liftM&lt;/span&gt; &lt;span class='conid'&gt;SFrag&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='conid'&gt;P&lt;/span&gt;&lt;span class='varop'&gt;.&lt;/span&gt;&lt;span class='varid'&gt;string&lt;/span&gt; &lt;span class='str'&gt;"#"&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;

    &lt;span class='varid'&gt;interpolationP&lt;/span&gt; &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='keyword'&gt;do&lt;/span&gt;
        &lt;span class='conid'&gt;P&lt;/span&gt;&lt;span class='varop'&gt;.&lt;/span&gt;&lt;span class='varid'&gt;string&lt;/span&gt; &lt;span class='str'&gt;"#{"&lt;/span&gt;
        &lt;span class='varid'&gt;spec&lt;/span&gt; &lt;span class='keyglyph'&gt;&amp;lt;-&lt;/span&gt; &lt;span class='conid'&gt;P&lt;/span&gt;&lt;span class='varop'&gt;.&lt;/span&gt;&lt;span class='varid'&gt;manyTill&lt;/span&gt; &lt;span class='conid'&gt;P&lt;/span&gt;&lt;span class='varop'&gt;.&lt;/span&gt;&lt;span class='varid'&gt;get&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='conid'&gt;P&lt;/span&gt;&lt;span class='varop'&gt;.&lt;/span&gt;&lt;span class='varid'&gt;char&lt;/span&gt; &lt;span class='chr'&gt;'}'&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;
        &lt;span class='varid'&gt;return&lt;/span&gt; &lt;span class='varop'&gt;$&lt;/span&gt; &lt;span class='keyword'&gt;case&lt;/span&gt; &lt;span class='varid'&gt;spec&lt;/span&gt; &lt;span class='keyword'&gt;of&lt;/span&gt;
          &lt;span class='chr'&gt;'r'&lt;/span&gt;&lt;span class='conop'&gt;:&lt;/span&gt;&lt;span class='chr'&gt;' '&lt;/span&gt;&lt;span class='conop'&gt;:&lt;/span&gt;&lt;span class='varid'&gt;var&lt;/span&gt; &lt;span class='keyglyph'&gt;-&amp;gt;&lt;/span&gt; &lt;span class='conid'&gt;SIRTxt&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;strip&lt;/span&gt; &lt;span class='varid'&gt;var&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;
          &lt;span class='chr'&gt;'s'&lt;/span&gt;&lt;span class='conop'&gt;:&lt;/span&gt;&lt;span class='chr'&gt;' '&lt;/span&gt;&lt;span class='conop'&gt;:&lt;/span&gt;&lt;span class='varid'&gt;var&lt;/span&gt; &lt;span class='keyglyph'&gt;-&amp;gt;&lt;/span&gt; &lt;span class='conid'&gt;SIShow&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;strip&lt;/span&gt; &lt;span class='varid'&gt;var&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;
          &lt;span class='chr'&gt;'='&lt;/span&gt;&lt;span class='conop'&gt;:&lt;/span&gt;&lt;span class='varid'&gt;var&lt;/span&gt;     &lt;span class='keyglyph'&gt;-&amp;gt;&lt;/span&gt; &lt;span class='conid'&gt;SIFrag&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;strip&lt;/span&gt; &lt;span class='varid'&gt;var&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;
          &lt;span class='varid'&gt;var&lt;/span&gt;         &lt;span class='keyglyph'&gt;-&amp;gt;&lt;/span&gt; &lt;span class='conid'&gt;SITxt&lt;/span&gt;  &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;strip&lt;/span&gt; &lt;span class='varid'&gt;var&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;

&lt;span class='varid'&gt;strip&lt;/span&gt; &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='varid'&gt;frontAndBack&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;dropWhile&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varop'&gt;==&lt;/span&gt; &lt;span class='chr'&gt;' '&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;
&lt;span class='varid'&gt;frontAndBack&lt;/span&gt; &lt;span class='varid'&gt;f&lt;/span&gt; &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='varid'&gt;reverse&lt;/span&gt; &lt;span class='varop'&gt;.&lt;/span&gt; &lt;span class='varid'&gt;f&lt;/span&gt; &lt;span class='varop'&gt;.&lt;/span&gt; &lt;span class='varid'&gt;reverse&lt;/span&gt; &lt;span class='varop'&gt;.&lt;/span&gt; &lt;span class='varid'&gt;f&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

	&lt;h3&gt;More sugar: defining additional safe-string types&lt;/h3&gt;


	&lt;p&gt;One additional bit of Template Haskell code, which I won&amp;#8217;t reprint
here, defines &lt;em&gt;declareSafeString&lt;/em&gt;.  This function lets us eliminate
the boilerplate code when defining new safe-string types.  For
example, compare our earlier definition of the SafeXml module with the
following implementation of a module for safe &lt;span class="caps"&gt;URL&lt;/span&gt; strings:&lt;/p&gt;


&lt;div class="typocode"&gt;&lt;pre&gt;&lt;code class="typocode_haskell "&gt;&lt;span class='keyword'&gt;module&lt;/span&gt; &lt;span class='conid'&gt;SafeUrl&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='conid'&gt;Url&lt;/span&gt;&lt;span class='layout'&gt;,&lt;/span&gt; &lt;span class='varid'&gt;url&lt;/span&gt;&lt;span class='layout'&gt;,&lt;/span&gt; &lt;span class='varid'&gt;renderUrl&lt;/span&gt;&lt;span class='layout'&gt;,&lt;/span&gt; &lt;span class='keyword'&gt;module&lt;/span&gt; &lt;span class='conid'&gt;SafeStrings&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt; &lt;span class='keyword'&gt;where&lt;/span&gt;
&lt;span class='keyword'&gt;import&lt;/span&gt; &lt;span class='conid'&gt;SafeStrings&lt;/span&gt;
&lt;span class='keyword'&gt;import&lt;/span&gt; &lt;span class='conid'&gt;Text&lt;/span&gt;&lt;span class='varop'&gt;.&lt;/span&gt;&lt;span class='conid'&gt;Printf&lt;/span&gt;
&lt;span class='keyword'&gt;import&lt;/span&gt; &lt;span class='conid'&gt;Data&lt;/span&gt;&lt;span class='varop'&gt;.&lt;/span&gt;&lt;span class='conid'&gt;Char&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;ord&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;

&lt;span class='varid'&gt;escapeUrl&lt;/span&gt; &lt;span class='varid'&gt;xs&lt;/span&gt; &lt;span class='keyglyph'&gt;=&lt;/span&gt;
    &lt;span class='varid'&gt;concatMap&lt;/span&gt; &lt;span class='varid'&gt;esc&lt;/span&gt; &lt;span class='varid'&gt;xs&lt;/span&gt;
  &lt;span class='keyword'&gt;where&lt;/span&gt;
    &lt;span class='varid'&gt;esc&lt;/span&gt; &lt;span class='varid'&gt;x&lt;/span&gt; &lt;span class='keyglyph'&gt;|&lt;/span&gt; &lt;span class='varid'&gt;isReserved&lt;/span&gt; &lt;span class='varid'&gt;x&lt;/span&gt; &lt;span class='varop'&gt;||&lt;/span&gt; &lt;span class='varid'&gt;x&lt;/span&gt; &lt;span class='varop'&gt;&amp;gt;&lt;/span&gt; &lt;span class='chr'&gt;'~'&lt;/span&gt; &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='varid'&gt;urlEncode&lt;/span&gt; &lt;span class='varid'&gt;x&lt;/span&gt;
          &lt;span class='keyglyph'&gt;|&lt;/span&gt; &lt;span class='varid'&gt;x&lt;/span&gt; &lt;span class='varop'&gt;==&lt;/span&gt; &lt;span class='chr'&gt;' '&lt;/span&gt;                &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='str'&gt;"+"&lt;/span&gt;
          &lt;span class='keyglyph'&gt;|&lt;/span&gt; &lt;span class='varid'&gt;otherwise&lt;/span&gt;               &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='keyglyph'&gt;[&lt;/span&gt;&lt;span class='varid'&gt;x&lt;/span&gt;&lt;span class='keyglyph'&gt;]&lt;/span&gt;

&lt;span class='varid'&gt;urlEncode&lt;/span&gt; &lt;span class='varid'&gt;x&lt;/span&gt;  &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='chr'&gt;'%'&lt;/span&gt; &lt;span class='conop'&gt;:&lt;/span&gt; &lt;span class='varid'&gt;printf&lt;/span&gt; &lt;span class='str'&gt;"%02x"&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;ord&lt;/span&gt; &lt;span class='varid'&gt;x&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;
&lt;span class='varid'&gt;isReserved&lt;/span&gt;   &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varop'&gt;`elem`&lt;/span&gt; &lt;span class='str'&gt;"!#$&amp;amp;'()*+,/:;=?@[]"&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;

&lt;span class='varop'&gt;$&lt;/span&gt;&lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;declareSafeString&lt;/span&gt; &lt;span class='str'&gt;"url"&lt;/span&gt; &lt;span class='str'&gt;"Url"&lt;/span&gt; &lt;span class='keyglyph'&gt;[&lt;/span&gt;&lt;span class='keyglyph'&gt;|&lt;/span&gt; &lt;span class='varid'&gt;escapeUrl&lt;/span&gt; &lt;span class='keyglyph'&gt;|&lt;/span&gt;&lt;span class='keyglyph'&gt;]&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

	&lt;p&gt;The final line generates the boilerplate code for the wrapper type,
the language definition, the &lt;em&gt;Url&lt;/em&gt; type synonym, and the &lt;em&gt;url&lt;/em&gt; and
&lt;em&gt;renderUrl&lt;/em&gt; language-specific convenience functions.&lt;/p&gt;


	&lt;h3&gt;One big example to wrap things up&lt;/h3&gt;


	&lt;p&gt;Because we have been discussing mainly library code, let&amp;#8217;s take a step
back and see some typical user-level code that uses safe strings.
After all, that&amp;#8217;s what counts.&lt;/p&gt;


	&lt;p&gt;Here is a Haskellized, safe-strings version of the Ruby (on Rails)
code that I presented at the beginning of the article to add
submit-to-Reddit and submit-to-del.icio.us buttons to my blog:&lt;/p&gt;


&lt;div class="typocode"&gt;&lt;pre&gt;&lt;code class="typocode_haskell "&gt;&lt;span class='keyword'&gt;module&lt;/span&gt; &lt;span class='conid'&gt;Example&lt;/span&gt; &lt;span class='keyword'&gt;where&lt;/span&gt;
&lt;span class='keyword'&gt;import&lt;/span&gt; &lt;span class='conid'&gt;List&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;intersperse&lt;/span&gt;&lt;span class='layout'&gt;,&lt;/span&gt; &lt;span class='varid'&gt;break&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;
&lt;span class='keyword'&gt;import&lt;/span&gt; &lt;span class='conid'&gt;SafeXml&lt;/span&gt;
&lt;span class='keyword'&gt;import&lt;/span&gt; &lt;span class='conid'&gt;SafeUrl&lt;/span&gt;

&lt;span class='keyword'&gt;type&lt;/span&gt; &lt;span class='conid'&gt;Xhtml&lt;/span&gt; &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='conid'&gt;Xml&lt;/span&gt;

&lt;span class='varid'&gt;submit_this_article_links&lt;/span&gt; &lt;span class='keyglyph'&gt;::&lt;/span&gt; &lt;span class='conid'&gt;Article&lt;/span&gt; &lt;span class='keyglyph'&gt;-&amp;gt;&lt;/span&gt; &lt;span class='conid'&gt;Xhtml&lt;/span&gt;
&lt;span class='varid'&gt;submit_this_article_links&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='conid'&gt;Article&lt;/span&gt; &lt;span class='varid'&gt;title&lt;/span&gt; &lt;span class='varid'&gt;url&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt; &lt;span class='keyglyph'&gt;=&lt;/span&gt;
    &lt;span class='varid'&gt;cat&lt;/span&gt; &lt;span class='varop'&gt;.&lt;/span&gt; &lt;span class='varid'&gt;intersperse&lt;/span&gt; &lt;span class='varid'&gt;nbsp&lt;/span&gt; &lt;span class='varop'&gt;$&lt;/span&gt; &lt;span class='keyword'&gt;do&lt;/span&gt;
    &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;submit_title&lt;/span&gt;&lt;span class='layout'&gt;,&lt;/span&gt; &lt;span class='varid'&gt;submit_url&lt;/span&gt; &lt;span class='keyglyph'&gt;::&lt;/span&gt; &lt;span class='conid'&gt;Url&lt;/span&gt;&lt;span class='layout'&gt;,&lt;/span&gt; &lt;span class='varid'&gt;image_tag&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt; &lt;span class='keyglyph'&gt;&amp;lt;-&lt;/span&gt; &lt;span class='varid'&gt;site_list&lt;/span&gt;
    &lt;span class='varid'&gt;return&lt;/span&gt; &lt;span class='varop'&gt;$&lt;/span&gt;&lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;q&lt;/span&gt;
      &lt;span class='str'&gt;"&amp;lt;a href=\"#{r submit_url}\" \
         \title=\"#{submit_title}: &amp;amp;#x201C;#{title}&amp;amp;#x201D;\" \
        \&amp;gt;#{=image_tag}&amp;lt;/a&amp;gt;"&lt;/span&gt; &lt;span class='layout'&gt;)&lt;/span&gt;

  &lt;span class='keyword'&gt;where&lt;/span&gt;

    &lt;span class='varid'&gt;nbsp&lt;/span&gt; &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='varid'&gt;xml&lt;/span&gt; &lt;span class='str'&gt;"&amp;amp;#160;"&lt;/span&gt;

    &lt;span class='varid'&gt;site_list&lt;/span&gt; &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='keyglyph'&gt;[&lt;/span&gt;  &lt;span class='comment'&gt;-- move me into a database table&lt;/span&gt;
      &lt;span class='layout'&gt;(&lt;/span&gt; &lt;span class='str'&gt;"Submit to Reddit.com"&lt;/span&gt;
      &lt;span class='layout'&gt;,&lt;/span&gt; &lt;span class='varop'&gt;$&lt;/span&gt;&lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;q&lt;/span&gt; &lt;span class='str'&gt;"http://reddit.com/submit?url=#{r url}&amp;amp;title=#{title}"&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;
      &lt;span class='layout'&gt;,&lt;/span&gt; &lt;span class='varid'&gt;image_tag&lt;/span&gt; &lt;span class='str'&gt;"reddit.gif"&lt;/span&gt; &lt;span class='str'&gt;"18x18"&lt;/span&gt; &lt;span class='num'&gt;0&lt;/span&gt;
      &lt;span class='layout'&gt;)&lt;/span&gt;&lt;span class='layout'&gt;,&lt;/span&gt;
      &lt;span class='layout'&gt;(&lt;/span&gt; &lt;span class='str'&gt;"Save to del.icio.us"&lt;/span&gt;
      &lt;span class='layout'&gt;,&lt;/span&gt; &lt;span class='varop'&gt;$&lt;/span&gt;&lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;q&lt;/span&gt; &lt;span class='str'&gt;"http://del.icio.us/post?v=2&amp;amp;url=#{r url}&amp;amp;title=#{title}"&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;
      &lt;span class='layout'&gt;,&lt;/span&gt; &lt;span class='varid'&gt;image_tag&lt;/span&gt; &lt;span class='str'&gt;"delicious.gif"&lt;/span&gt; &lt;span class='str'&gt;"16x16"&lt;/span&gt; &lt;span class='num'&gt;0&lt;/span&gt;
      &lt;span class='layout'&gt;)&lt;/span&gt; &lt;span class='keyglyph'&gt;]&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

&lt;p&gt;The code looks fairly similar to the original Ruby code, with the exception
of some extra backslashes, courtesy of Haskell&amp;#8217;s rather-unfortunate
syntax for multi-line string constants. (Perl and Ruby&amp;#8217;s
&lt;code&gt;&amp;lt;&amp;lt;HERE&lt;/code&gt; syntax would be a welcome addition.)&lt;/p&gt;

	&lt;p&gt;The other big difference is that, in this version, the type system has
automatically checked the code for strings-problem errors.&lt;/p&gt;


	&lt;p&gt;For completeness, here is the example&amp;#8217;s supporting code (again modeled
on Ruby on Rails).  This code also makes
extensive use of safe-string templates:&lt;/p&gt;


&lt;div class="typocode"&gt;&lt;pre&gt;&lt;code class="typocode_haskell "&gt;&lt;span class='varid'&gt;image_tag&lt;/span&gt; &lt;span class='keyglyph'&gt;::&lt;/span&gt; &lt;span class='conid'&gt;String&lt;/span&gt; &lt;span class='keyglyph'&gt;-&amp;gt;&lt;/span&gt; &lt;span class='conid'&gt;String&lt;/span&gt; &lt;span class='keyglyph'&gt;-&amp;gt;&lt;/span&gt; &lt;span class='conid'&gt;Int&lt;/span&gt; &lt;span class='keyglyph'&gt;-&amp;gt;&lt;/span&gt; &lt;span class='conid'&gt;Xhtml&lt;/span&gt;
&lt;span class='varid'&gt;image_tag&lt;/span&gt; &lt;span class='varid'&gt;file_name&lt;/span&gt; &lt;span class='varid'&gt;size&lt;/span&gt; &lt;span class='varid'&gt;border&lt;/span&gt; &lt;span class='keyglyph'&gt;=&lt;/span&gt;
    &lt;span class='varop'&gt;$&lt;/span&gt;&lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;q&lt;/span&gt; &lt;span class='str'&gt;"&amp;lt;img src=\"#{r image_url}\" height=\"#{height}\" \
         \width=\"#{width}\" border=\"#{s border}\"/&amp;gt;"&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;
  &lt;span class='keyword'&gt;where&lt;/span&gt;
    &lt;span class='varid'&gt;image_url&lt;/span&gt;         &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='varop'&gt;$&lt;/span&gt;&lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;q&lt;/span&gt; &lt;span class='str'&gt;"#{=site_root}images/#{file_name}"&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;
    &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;width&lt;/span&gt;&lt;span class='layout'&gt;,&lt;/span&gt; &lt;span class='keyword'&gt;_&lt;/span&gt;&lt;span class='conop'&gt;:&lt;/span&gt;&lt;span class='varid'&gt;height&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt; &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='varid'&gt;break&lt;/span&gt; &lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varop'&gt;==&lt;/span&gt;&lt;span class='chr'&gt;'x'&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt; &lt;span class='varid'&gt;size&lt;/span&gt;

&lt;span class='varid'&gt;link_to&lt;/span&gt; &lt;span class='keyglyph'&gt;::&lt;/span&gt; &lt;span class='conid'&gt;Xhtml&lt;/span&gt; &lt;span class='keyglyph'&gt;-&amp;gt;&lt;/span&gt; &lt;span class='conid'&gt;Url&lt;/span&gt; &lt;span class='keyglyph'&gt;-&amp;gt;&lt;/span&gt; &lt;span class='conid'&gt;Xhtml&lt;/span&gt;
&lt;span class='varid'&gt;link_to&lt;/span&gt; &lt;span class='varid'&gt;content&lt;/span&gt; &lt;span class='varid'&gt;url&lt;/span&gt; &lt;span class='keyglyph'&gt;=&lt;/span&gt;
    &lt;span class='varop'&gt;$&lt;/span&gt;&lt;span class='layout'&gt;(&lt;/span&gt;&lt;span class='varid'&gt;q&lt;/span&gt; &lt;span class='str'&gt;"&amp;lt;a href=\"#{r url}\"&amp;gt;#{=content}&amp;lt;/a&amp;gt;"&lt;/span&gt;&lt;span class='layout'&gt;)&lt;/span&gt;

&lt;span class='keyword'&gt;data&lt;/span&gt; &lt;span class='conid'&gt;Article&lt;/span&gt; &lt;span class='keyglyph'&gt;=&lt;/span&gt; &lt;span class='conid'&gt;Article&lt;/span&gt;
  &lt;span class='layout'&gt;{&lt;/span&gt; &lt;span class='varid'&gt;article_title&lt;/span&gt;  &lt;span class='keyglyph'&gt;::&lt;/span&gt; &lt;span class='conid'&gt;String&lt;/span&gt;
  &lt;span class='layout'&gt;,&lt;/span&gt; &lt;span class='varid'&gt;article_url&lt;/span&gt;    &lt;span class='keyglyph'&gt;::&lt;/span&gt; &lt;span class='conid'&gt;Url&lt;/span&gt;
    &lt;span class='comment'&gt;-- more fields here&lt;/span&gt;
  &lt;span class='layout'&gt;}&lt;/span&gt;

&lt;span class='varid'&gt;sample_article&lt;/span&gt; &lt;span class='keyglyph'&gt;=&lt;/span&gt;
    &lt;span class='conid'&gt;Article&lt;/span&gt; &lt;span class='str'&gt;"I love chunky bacon!"&lt;/span&gt; &lt;span class='varop'&gt;$&lt;/span&gt;
    &lt;span class='varid'&gt;url&lt;/span&gt; &lt;span class='str'&gt;"http://blog.moertel.com/permalink/to/article"&lt;/span&gt;

&lt;span class='varid'&gt;site_root&lt;/span&gt; &lt;span class='keyglyph'&gt;::&lt;/span&gt; &lt;span class='conid'&gt;Url&lt;/span&gt;
&lt;span class='varid'&gt;site_root&lt;/span&gt; &lt;span class='keyglyph'&gt;=&lt;/span&gt;  &lt;span class='varid'&gt;url&lt;/span&gt; &lt;span class='str'&gt;"http://blog.moertel.com/"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

	&lt;h3&gt;Have we done it?&lt;/h3&gt;


	&lt;p&gt;Have we rid ourselves of the strings problem?  If we use a programming
language like Haskell and a library like SafeStrings, I think we can
answer yes.&lt;/p&gt;


	&lt;p&gt;To be clear, the fundamental problem of having to manage different
kinds of strings is still with us.  As programmers, we still must
understand the differences between URLs, &lt;span class="caps"&gt;XML&lt;/span&gt;, SQL, untrusted user
input, and so on.  But now, we don&amp;#8217;t have to be perfect.  As long as
we can reliably slap the right type on a string when it first appears,
we can let the computer worry about it from then on.  If we forget to
escape the string later, as it winds its way through the twisty code
of a large web application and interacts with other strings in
potentially dangerous ways, the computer will catch our mistake &amp;#8211; at
compile time, before it can possibly become a live security hole.&lt;/p&gt;


	&lt;p&gt;But if slapping the right types on strings &amp;#8211; certifying them &amp;#8211; is a
pain in the neck, we won&amp;#8217;t do it.  We will happily go back to our days
of winging it, where every string interaction becomes an opportunity
for a perfectly human mistake to give birth to a nasty security
vulnerability.&lt;/p&gt;


	&lt;p&gt;That&amp;#8217;s why syntax matters.  That&amp;#8217;s why Template Haskell, Lisp macros,
and other meta-programming tools are important: they let us craft
friendly syntaxes that encourage the use of programming aids like
SafeStrings.  That&amp;#8217;s why type inferencing is important: it lets us do
away with redundant annotations and makes working with types
convenient, so we can reap the benefits of strong guarantees without
having to pay prohibitive costs.&lt;/p&gt;


If there is a moral to this story, it&amp;#8217;s that modern type systems and
macro systems are powerful tools.  They let us do things that
otherwise would be impractically inconvenient.  They extend our reach
as programmers and let us solve problems that we couldn&amp;#8217;t solve
before.
&lt;div class="update"&gt;
&lt;strong&gt;Update:&lt;/strong&gt; minor edits for clarity.
&lt;/div&gt;</description>
      <pubDate>Wed, 18 Oct 2006 21:40:00 -0400</pubDate>
      <guid isPermaLink="false">urn:uuid:4a7fb02b-a1ba-4c4a-a63b-938a19f3076c</guid>
      <author>Tom Moertel</author>
      <link>http://blog.moertel.com/articles/2006/10/18/a-type-based-solution-to-the-strings-problem</link>
      <category>programming</category>
      <category>programming languages</category>
      <category>haskell</category>
      <category>ruby</category>
      <category>web development</category>
      <category>testing</category>
      <category>rails</category>
      <category>ruby</category>
      <category>haskell</category>
      <category>testing</category>
      <category>strings</category>
      <category>types</category>
      <trackback:ping>http://blog.moertel.com/articles/trackback/186</trackback:ping>
    </item>
    <item>
      <title>If unit testing can't keep Rails safe from string-escaping problems, what makes you think it will keep your projects safe?</title>
      <description>&lt;p&gt;Recently I wrote about &lt;a href="http://blog.moertel.com/articles/2006/10/10/unit-testing-is-a-tool-not-a-goal"&gt;unit testing being a tool, not a goal in
itself&lt;/a&gt;.
I argued that unit testing was not a reliable way to fight
certain kinds of common coding errors and, therefore, that unit testing
ought to be supplemented with other tools.&lt;/p&gt;


	&lt;p&gt;To support my argument, I gave an example of a common, important
coding error that unit testing does a bad job of helping programmers
control.  That error is failing to manage and escape strings
properly: the &amp;#8220;strings problem.&amp;#8221;  It is the mother of &lt;span class="caps"&gt;XSS&lt;/span&gt; and
&lt;span class="caps"&gt;SQL&lt;/span&gt;-injection security vulnerabilities, not to mention the cause of
legions of broken links and bad &lt;span class="caps"&gt;HTML&lt;/span&gt; on the web.&lt;/p&gt;


	&lt;p&gt;If you think I&amp;#8217;m overstating the problem, or if you think that unit
testing is a good way of solving it, let me show you how easy it is
for even smart developers to get it wrong.&lt;/p&gt;


	&lt;p&gt;Consider &lt;a href="http://rubyonrails.com/"&gt;Ruby on
Rails&lt;/a&gt;, a great framework
for developing web applications.
Rails has an extensive suite of unit tests, and the &lt;a href="http://dev.rubyonrails.org/"&gt;Rails development guidelines&lt;/a&gt; require that changes to Rails be accompanied by unit tests that &amp;#8220;prove [the] change works.&amp;#8221;&lt;/p&gt;


	&lt;p&gt;Now consider that one of Rails&amp;#8217;s most-used and &lt;a href="http://blog.moertel.com/articles/2005/05/08/taking-the-unsafe-gets-out-of-rails"&gt;most-scrutinized&lt;/a&gt; methods &amp;#8211; the venerable &lt;code&gt;link_to&lt;/code&gt; helper &amp;#8211; contains a fundamental string-escaping error:&lt;/p&gt;


&lt;pre&gt;&lt;code&gt;require 'rubygems'
require_gem 'rails'
include ActionView::Helpers::UrlHelper

url = "http://example.com?ohms_law?volt=1&amp;#38;amp=3" 
puts link_to("TEST", url)
&lt;/code&gt;&lt;/pre&gt;

	&lt;p&gt;The code, when executed, prints the following &lt;span class="caps"&gt;HTML&lt;/span&gt; snippet:&lt;/p&gt;


&lt;pre&gt;&lt;code&gt;&amp;lt;a href="http://example.com?ohms_law?volt=1&amp;#38;amp=3"&amp;gt;TEST&amp;lt;/a&amp;gt;
&lt;/code&gt;&lt;/pre&gt;

	&lt;p&gt;The &lt;span class="caps"&gt;HTML&lt;/span&gt; snippet represents a hypertext link.  The link should point
to the &lt;span class="caps"&gt;URL&lt;/span&gt; given in the code, but because the &lt;span class="caps"&gt;URL&lt;/span&gt; was not properly
escaped when it was converted into &lt;span class="caps"&gt;HTML&lt;/span&gt; by the &lt;code&gt;link_to&lt;/code&gt; helper, the
link is broken:&lt;/p&gt;


&lt;pre&gt;&lt;code&gt;CORRECT:  http://example.com?ohms_law?volt=1&amp;#38;amp=3
LINK_TO:  http://example.com?ohms_law?volt=1&amp;#38;=3
                                             ^ oops
&lt;/code&gt;&lt;/pre&gt;

	&lt;p&gt;Here&amp;#8217;s what&amp;#8217;s going on.  Because the &lt;span class="caps"&gt;URL&lt;/span&gt; was not escaped, web browsers
misinterpret its &amp;#8220;amp&amp;#8221; parameter as a character-entity reference,
which gets gobbled up when the link&amp;#8217;s &lt;code&gt;href&lt;/code&gt; attribute is parsed.
(To see this for yourself, save the output of the Ruby code into an
&lt;span class="caps"&gt;HTML&lt;/span&gt; file, open the file with your favorite web browser, and see where
the link points.)&lt;/p&gt;


	&lt;p&gt;Now, how come the unit tests didn&amp;#8217;t catch this problem?
It turns out, the tests got it wrong, too, by expecting
broken output:&lt;/p&gt;


&lt;pre&gt;&lt;code&gt;# in url_helper_test.rb

def test_link_tag_with_query
  assert_dom_equal \
    "&amp;lt;a href=\"http://www.example.com?q1=v1&amp;amp;amp;q2=v2\"&amp;gt;Hello&amp;lt;/a&amp;gt;",
    link_to("Hello", "http://www.example.com?q1=v1&amp;amp;amp;q2=v2")
end
&lt;/code&gt;&lt;/pre&gt;

	&lt;p&gt;The point isn&amp;#8217;t that the Rails developers are dumb.  The point is that
the Rails developers are smart.  If &lt;em&gt;they&lt;/em&gt; can&amp;#8217;t get the strings
problem right, even with all their brains and all their unit testing,
what reason does &lt;em&gt;any&lt;/em&gt; programmer have to think that unit testing is going
to solve this problem reliably?&lt;/p&gt;


	&lt;p&gt;If, then, you want to solve the strings problem &amp;#8211; and you really,
seriously &lt;em&gt;ought&lt;/em&gt; to want to solve the strings problem &amp;#8211; you should
consider options beyond unit testing.&lt;/p&gt;


&lt;div class="update"&gt;

	&lt;p&gt;&lt;strong&gt;Update 2007-09-04:&lt;/strong&gt; I just noticed that the documentation for
&lt;em&gt;link_to&lt;/em&gt; has been revised to state that if you pass a
string as its &lt;em&gt;options&lt;/em&gt; parameter, the string will be interpreted not
as a &lt;span class="caps"&gt;URL&lt;/span&gt; but as an &lt;span class="caps"&gt;HTML&lt;/span&gt; &lt;em&gt;href&lt;/em&gt; attribute value, that is, an
&lt;span class="caps"&gt;HTML&lt;/span&gt;-encoded &lt;span class="caps"&gt;URL&lt;/span&gt;.  The old documentation:&lt;/p&gt;


	&lt;blockquote&gt;
		&lt;p&gt; &lt;code&gt;def link_to(name, options = {}, html_options = nil, *parms)&lt;/code&gt;&lt;br/&gt;Creates a link tag of
the given &lt;em&gt;name&lt;/em&gt; using an &lt;span class="caps"&gt;URL&lt;/span&gt; created by the set of &lt;em&gt;options&lt;/em&gt;.... It&amp;#8217;s
also possible to pass a string instead of an options hash to get a
link tag that just points without consideration.&lt;/p&gt;
	&lt;/blockquote&gt;


	&lt;p&gt;The relevant part of the revised documentation:&lt;/p&gt;


	&lt;blockquote&gt;
		&lt;p&gt;It&amp;#8217;s also possible to pass a string instead of an options hash to
get a link tag that uses the value of the string as the href for the
link.&lt;/p&gt;
	&lt;/blockquote&gt;


	&lt;p&gt;So, according to the updated documentation, the test I described in my
article is actually correct.  Does this mean that string-handling code
is Rails is worry free?  The existence of helper methods like &lt;a href="http://dev.rubyonrails.org/changeset/5321"&gt;&lt;em&gt;fix_double_escape&lt;/em&gt;&lt;/a&gt;
suggests the answer is no.&lt;/p&gt;


&lt;/div&gt;</description>
      <pubDate>Thu, 12 Oct 2006 16:06:00 -0400</pubDate>
      <guid isPermaLink="false">urn:uuid:03f6d26c-1207-4022-a970-b80231721ea6</guid>
      <author>Tom Moertel</author>
      <link>http://blog.moertel.com/articles/2006/10/12/if-unit-testing-cant-keep-rails-safe-from-string-escaping-problems-what-makes-you-think-it-will-keep-your-projects-safe</link>
      <category>programming</category>
      <category>testing</category>
      <category>rails</category>
      <category>rails</category>
      <category>testing</category>
      <category>strings</category>
      <category>problem</category>
      <category>escaping</category>
      <trackback:ping>http://blog.moertel.com/articles/trackback/184</trackback:ping>
    </item>
    <item>
      <title>Database connection leak in Typo 4.0.3: problem solved</title>
      <description>&lt;p&gt;In &lt;a href="http://blog.moertel.com/articles/2006/08/24/typo-4-0-3-instability-and-a-minor-patch-for-sqlite3-ruby"&gt;an earlier post&lt;/a&gt; I wrote about stability
problems that have plagued my blog since upgrading from &lt;a href="http://typosphere.org"&gt;Typo&lt;/a&gt; 4.0.0 to 4.0.3.  I have finally traced the problem to its source, and here&amp;#8217;s the deal:&lt;/p&gt;


	&lt;p&gt;&lt;em&gt;If you&amp;#8217;re serving Typo up via &lt;a href="http://mongrel.rubyforge.org/index.html"&gt;Mongrel&lt;/a&gt;, do not configure ActiveRecord to allow concurrency.&lt;/em&gt;&lt;/p&gt;


	&lt;p&gt;One of the changes between Typo 4.0.0 and 4.0.3 is this
addition to the &lt;code&gt;environment.rb&lt;/code&gt; file:&lt;/p&gt;


&lt;pre&gt;&lt;code&gt;config.active_record.allow_concurrency = true
&lt;/code&gt;&lt;/pre&gt;

	&lt;p&gt;&lt;del&gt;Comment out this line, restart Typo, and the problem is solved.&lt;/del&gt;
Apply Changeset 1255, and the problem is solved.  (See
&lt;a href="#article165-update2"&gt;Update 2&lt;/a&gt;, below.)&lt;/p&gt;


	&lt;h3&gt;Discussion&lt;/h3&gt;


&lt;p&gt;When &lt;code&gt;ActiveRecord::Base.allow_concurrency&lt;/code&gt; is set to
&lt;code&gt;true&lt;/code&gt;, AR will give each thread its own database
connections and cache them in thread-localized storage.  The idea is
that, in a multi-threaded environment, this simple policy prevents
unsafe interactions between threads and the database.  (Imagine what
would happen if one thread &amp;#8220;borrowed&amp;#8221; a connection over which
another thread had opened a transaction.  Oops, there goes
transactional isolation.)&lt;/p&gt;

	&lt;p&gt;This policy, however, does place a burden on the owner of the threads to
make sure that each thread&amp;#8217;s local connection cache is cleared when
the thread is joined, a burden that is not, it would seem, being
carried by Typo under Mongrel.  As a result, Typo rapidly chews
through the allotment of file descriptors that the operating system
kindly had reserved for Mongrel:&lt;/p&gt;


	&lt;p&gt;&lt;img src="http://community.moertel.com/~thor/pix/20060824/blog-fd-usage-vs-time.png" title="Typo 4.0.3 on Mongrel w/ SQLite3 consumes about 1.7 file descriptors per minute when ActiveRecord is configured to allow concurrency" alt="Typo 4.0.3 on Mongrel w/ SQLite3 consumes about 1.7 file descriptors per minute when ActiveRecord is configured to allow concurrency" /&gt;&lt;/p&gt;


	&lt;p&gt;(On my Linux server, the Mongrel process gets an allotment of 1024
file descriptors.)&lt;/p&gt;


	&lt;p&gt;Lucky for us, this each-thread-gets-its-own-connections policy is unnecessary under
Mongrel because Mongrel, while being multi-threaded itself, serializes
all access to the Rails-based applications it serves up:&lt;/p&gt;


&lt;blockquote&gt;&lt;p&gt;&lt;strong&gt;Q: Is [Mongrel] multi-threaded or can it handle concurrent requests?&lt;/strong&gt;&lt;/p&gt;

	&lt;p&gt;Mongrel is uses a pool of thread workers to do it&amp;#8217;s processing. This means that it is able to handle concurrent access and should be thread safe. This also means that you have to be more careful about how you use Mongrel. You can&amp;#8217;t just write your application assuming that there are no threads involved. ...&lt;/p&gt;


	&lt;p&gt;Ruby on Rails is not thread safe so there is a synchronized block around the calls to Dispatcher.dispatch. This means that everything is threaded right before and right after Rails runs. While Rails is running there is only one controller in operation at a time.&lt;/p&gt;


(Source: &lt;a href="http://mongrel.rubyforge.org/faq.html"&gt;Mongrel &lt;span class="caps"&gt;FAQ&lt;/span&gt; list&lt;/a&gt;)
&lt;/blockquote&gt;

Thus we can safely turn off (i.e., comment out in Typo&amp;#8217;s
&lt;code&gt;environment.rb&lt;/code&gt; file) ActiveRecord&amp;#8217;s allow-currency option
without having to worry about nasty concurrency or performance issues:

&lt;pre&gt;&lt;code&gt;# the following line is commented out
# config.active_record.allow_concurrency = true
&lt;/code&gt;&lt;/pre&gt;

	&lt;p&gt;For more on this subject, see &lt;a href="http://dev.rubyonrails.org/ticket/2162"&gt;Rails ticket
#2162&lt;/a&gt; and &lt;a href="http://dev.rubyonrails.org/ticket/2742"&gt;Rails ticket
#2742&lt;/a&gt;.&lt;/p&gt;


	&lt;p&gt;Now, here&amp;#8217;s my question: Are there any environments in which
Typo can run with the allow-concurrency option enabled and &lt;em&gt;not&lt;/em&gt;
leak database connections?  Inquiring minds want to know.&lt;/p&gt;


&lt;div class="update"&gt;

	&lt;p&gt;&lt;strong&gt;Update:&lt;/strong&gt; Upon further investigation, turning off
concurrency might not be altogether without risk.  Some of the Typo
code that handles potentially long tasks, such as making trackbacks
and pings, spawns new threads in which to carry out its work.  I&amp;#8217;m
looking further into this risk.  Updates to come.&lt;/p&gt;


&lt;p id="article165-update2"&gt;&lt;strong&gt;Update 2:&lt;/strong&gt; Piers Cawley added &lt;a href="http://www.typosphere.org/trac/changeset/1255"&gt;Changeset
1255&lt;/a&gt;, which turns AR&amp;#8217;s
allow-concurrency flag back off and revises the ping code so that
it does not attempt concurrent database access.  Apply &lt;a href="http://www.typosphere.org/trac/changeset/1255?format=diff&amp;#38;new=1255"&gt;the patch version of
1255&lt;/a&gt;
and restart Typo to get the fix.  A tip of the hat to Piers for making
the quick fix when he was supposed to be on holiday.&lt;/p&gt;

&lt;/div&gt;</description>
      <pubDate>Thu, 24 Aug 2006 15:41:00 -0400</pubDate>
      <guid isPermaLink="false">urn:uuid:ef03f59b-8bc4-4744-b94d-2966da53dca2</guid>
      <author>Tom Moertel</author>
      <link>http://blog.moertel.com/articles/2006/08/24/database-connection-leak-in-typo-4-0-3-problem-solved</link>
      <category>ruby</category>
      <category>typo</category>
      <category>rails</category>
      <category>typo</category>
      <category>sqlite3</category>
      <category>rails</category>
      <category>activerecord</category>
      <category>concurrency</category>
      <trackback:ping>http://blog.moertel.com/articles/trackback/165</trackback:ping>
    </item>
    <item>
      <title>Typo-4.0.3 instability and a minor patch for sqlite3-ruby</title>
      <description>&lt;p&gt;Since I upgraded my blog from &lt;a href="http://typosphere.org/"&gt;Typo&lt;/a&gt; 4.0.0 to
4.0.3, it has been somewhat unstable.  About once a day it starts
responding with &amp;#8220;500 Internal Server Error&amp;#8221; and stays that way until I
restart it.&lt;/p&gt;


	&lt;p&gt;The root of the problem seems to be the database
connection, as evidenced by this exception showing up in the
production log:&lt;/p&gt;


&lt;pre&gt;&lt;code&gt;SQLite3::CantOpenException (could not open database)
&lt;/code&gt;&lt;/pre&gt;

	&lt;p&gt;Unfortunately, the exception doesn&amp;#8217;t provide anything specific
to go on.&lt;/p&gt;


	&lt;p&gt;A quick look at the
&lt;a href="http://rubyforge.org/projects/sqlite-ruby/"&gt;sqlite3-ruby&lt;/a&gt; code
suggested that I was not going to get the specifics, either.  The Ruby-based wrapper
never calls &lt;a href="http://www.sqlite.org/capi3ref.html#sqlite3_errmsg"&gt;sqlite3_errmsg&lt;/a&gt; after a call to &lt;a href="http://www.sqlite.org/capi3ref.html#sqlite3_open"&gt;sqlite3_open&lt;/a&gt; fails on behalf of SQLite3::Database.new.&lt;/p&gt;


	&lt;p&gt;A quick patch, however, fixed the problem:&lt;/p&gt;


&lt;pre&gt;&lt;code&gt;--- sqlite3-ruby-1.1.0.orig/lib/sqlite3/database.rb
+++ sqlite3-ruby-1.1.0/lib/sqlite3/database.rb
@@ -109,7 +109,7 @@
       @statement_factory = options[:statement_factory] || Statement

       result, @handle = @driver.open( file_name, utf16 )
-      Error.check( result, nil, "could not open database" )
+      Error.check( result, self, "could not open database" )

       @closed = false
       @results_as_hash = options.fetch(:results_as_hash,false)
&lt;/code&gt;&lt;/pre&gt;

	&lt;p&gt;(Submitted as &lt;a href="http://rubyforge.org/tracker/index.php?func=detail&amp;#38;aid=5504&amp;#38;group_id=254&amp;#38;atid=1043"&gt;Ticket 5504&lt;/a&gt; on &lt;a href="http://rubyforge.org/"&gt;RubyForge&lt;/a&gt;.)&lt;/p&gt;


	&lt;p&gt;Before applying the patch, opening a database at a nonexistent path results in
a generic error message:&lt;/p&gt;


&lt;pre&gt;&lt;code&gt;$ ruby -r rubygems -e 'require_gem "sqlite3-ruby";
    SQLite3::Database.new("/no/such/path/db")'

&lt;/code&gt;... could not open database (SQLite3::CantOpenException) ...
&lt;/pre&gt;

	&lt;p&gt;After applying the patch, we get additional error information:&lt;/p&gt;


&lt;pre&gt;... could not open database: unable to open database file
    (SQLite3::CantOpenException) ...
&lt;/pre&gt;

	&lt;p&gt;With the patch in place, all I have to do is wait for Typo to start
acting up again.  Then I&amp;#8217;ll have some interesting information in the
log.&lt;/p&gt;


	&lt;p&gt;Until then, I&amp;#8217;m relying on &lt;a href="http://en.wikipedia.org/wiki/Crontab"&gt;cron&lt;/a&gt;
and a short monitoring script to restart Typo when it tips into
foolishness:&lt;/p&gt;


&lt;pre&gt;&lt;code&gt;#!/bin/bash

url=http://blog.moertel.com/admin
addrs=tom@moertel.com

response=$(GET -sd $url 2&amp;gt;&amp;#38;1)

if [ "$response" != "200 OK" ]; then
    { echo "Response was: $response"; echo; service typo restart; } |
    mail -s "Blog site not responding! (Restarting)" $addrs
fi
&lt;/code&gt;&lt;/pre&gt;

	&lt;p&gt;We&amp;#8217;ll see how it goes.&lt;/p&gt;


&lt;div class="update"&gt; &lt;strong&gt;Update:&lt;/strong&gt; That was fast.  The error popped up
again and this time the log told me something useful: &amp;#8220;unable to open
database file.&amp;#8221;  Now, why couldn&amp;#8217;t Typo open the database file,
especially since the file is perfectly fine and had been opened
successfully (many times) by the very same Typo process earlier?  Here&amp;#8217;s
a hint:

&lt;pre&gt;&lt;code&gt;$ ls /proc/28788/fd | wc -l
&lt;/code&gt;1023
&lt;/pre&gt;

	&lt;p&gt;Seems like there&amp;#8217;s a resource leak in Typo 4.0.3 (or Rails 1.1.6).
Under some conditions, instead of reusing existing database
connections, Typo keeps trying to open new ones.  Eventually, it uses
up its allotment of file descriptors and the operating system is forced
to say, &amp;#8220;That&amp;#8217;s enough, pal,&amp;#8221; (&lt;a href="http://www.wlug.org.nz/EMFILE"&gt;&lt;code&gt;EMFILE&lt;/code&gt;&lt;/a&gt;).&lt;/p&gt;


	&lt;p&gt;I&amp;#8217;ll look in to it more in the morning.&lt;/p&gt;


&lt;strong&gt;Update 2:&lt;/strong&gt; &lt;a href="http://blog.moertel.com/articles/2006/08/24/database-connection-leak-in-typo-4-0-3-problem-solved"&gt;Problem solved&lt;/a&gt;.
&lt;/div&gt;</description>
      <pubDate>Thu, 24 Aug 2006 00:41:00 -0400</pubDate>
      <guid isPermaLink="false">urn:uuid:2e527a1f-3415-4322-9f0f-244b45a3b695</guid>
      <author>Tom Moertel</author>
      <link>http://blog.moertel.com/articles/2006/08/24/typo-4-0-3-instability-and-a-minor-patch-for-sqlite3-ruby</link>
      <category>ruby</category>
      <category>typo</category>
      <category>rails</category>
      <category>sysadmin</category>
      <category>typo</category>
      <category>sqlite3</category>
      <category>rails</category>
      <trackback:ping>http://blog.moertel.com/articles/trackback/163</trackback:ping>
    </item>
    <item>
      <title>The button_to helper is now part of Rails!</title>
      <description>&lt;p&gt;I am delighted to report that the &lt;a href="http://blog.moertel.com/articles/2005/05/08/taking-the-unsafe-gets-out-of-rails"&gt;button_to
helper&lt;/a&gt;
has been added to the &lt;a href="http://www.rubyonrails.com/"&gt;Ruby on Rails&lt;/a&gt;
web-development framework.  &lt;a href="http://www.loudthinking.com/"&gt;David&lt;/a&gt;
applied &lt;a href="http://dev.rubyonrails.org/changeset/1437"&gt;the patch&lt;/a&gt; earlier
today, and so &lt;em&gt;button_to&lt;/em&gt; will be in the much-anticipated Rails 1.0
release.&lt;/p&gt;


	&lt;p&gt;David&amp;#8217;s change-log entry summarizes the patch well:&lt;/p&gt;


	&lt;blockquote&gt;
		&lt;p&gt;Added &lt;em&gt;button_to&lt;/em&gt; as a form-based solution to deal with harmful
actions that should be hidden behind POSTs. This makes it just as
easy as &lt;em&gt;link_to&lt;/em&gt; to create a safe trigger for actions like destroy,
although it&amp;#8217;s limited by being a block element, the fixed look,
and a no-no inside other forms.&lt;/p&gt;
	&lt;/blockquote&gt;


	&lt;p&gt;David does a good job of highlighting the helper&amp;#8217;s limitations. I&amp;#8217;ll
take this opportunity to elaborate on each.&lt;/p&gt;


	&lt;h3&gt;It is a block element&lt;/h3&gt;


	&lt;p&gt;The &lt;em&gt;button_to&lt;/em&gt; helper creates a small form, which in &lt;span class="caps"&gt;HTML&lt;/span&gt; is considered
&lt;a href="http://www.w3.org/TR/html4/sgml/dtd.html#block"&gt;block content&lt;/a&gt;, just
like the &lt;em&gt;p&lt;/em&gt;, &lt;em&gt;div&lt;/em&gt;, and &lt;em&gt;blockquote&lt;/em&gt; elements are. Basically, block
content cannot be mixed into runs of text. But links can: links are
&lt;a href="http://www.w3.org/TR/html4/sgml/dtd.html#inline"&gt;inline content&lt;/a&gt;. Thus
&lt;em&gt;button_to&lt;/em&gt; cannot be used as a drop-in replacement for every
occurrence of &lt;em&gt;link_to&lt;/em&gt; that might be unsafe; it works only for those
occurrences within block-accepting contexts.&lt;/p&gt;


	&lt;p&gt;Luckily for us, when designers use links to trigger unsafe actions,
they rarely slip such links into the middle of ordinary looking
text. Naughty uses of &lt;em&gt;link_to&lt;/em&gt; almost always occur within contexts
that accept block content. In Rails-generated scaffolding code, for
instance, the unsafe uses of &lt;em&gt;link_to&lt;/em&gt; occur within table cells, and
table cells have a &lt;a href="http://www.w3.org/TR/html4/sgml/dtd.html#flow"&gt;flow content
model&lt;/a&gt;, which accepts
both inline and block content. So &lt;em&gt;button_to&lt;/em&gt; works great for the
default cases in Rails.&lt;/p&gt;


	&lt;h3&gt;It has a fixed look&lt;/h3&gt;


	&lt;p&gt;As its name implies, &lt;em&gt;button_to&lt;/em&gt; creates buttons. Buttons don&amp;#8217;t look
like links and aren&amp;#8217;t styled the same way that links are. For some
design scenarios, this might be a problem.&lt;/p&gt;


	&lt;p&gt;(My view is that links should not be used to trigger unsafe
actions. In the same way that action-triggering &lt;span class="caps"&gt;GET&lt;/span&gt; requests violate
the spirit of the &lt;span class="caps"&gt;HTTP&lt;/span&gt; standards, action-triggering hypertext links
violate the spirit of the &lt;span class="caps"&gt;HTML&lt;/span&gt; standards. For this reason, I view this
limitation as a feature.)&lt;/p&gt;


	&lt;h3&gt;It is a no-no inside other forms&lt;/h3&gt;


	&lt;p&gt;Forms cannot be nested, and so &lt;em&gt;button_to&lt;/em&gt; cannot be used inside of
forms.&lt;/p&gt;


	&lt;p&gt;Fortunately, this limitation usually doesn&amp;#8217;t matter because when we
are inside of a form, we can use its buttons instead of
&lt;em&gt;button_to&lt;/em&gt;-created buttons to trigger actions. Still, there are some
circumstances where it does matter, such as the &amp;#8220;Amazon.com wish list&amp;#8221; 
scenario. In this scenario, we should consider &lt;a href="http://blog.moertel.com/articles/2005/05/08/taking-the-unsafe-gets-out-of-rails#comment-110"&gt;other
options&lt;/a&gt;.&lt;/p&gt;


	&lt;h3&gt;The bottom line: Pick the low-hanging fruit&lt;/h3&gt;


	&lt;p&gt;While &lt;em&gt;button_to&lt;/em&gt; has its limitations, it does provide a simple solution
to the unsafe-GET problem for most real-world cases. I am glad that it
is now a part of Rails, and I offer a big thank-you to David for
accepting the patch.&lt;/p&gt;</description>
      <pubDate>Thu, 16 Jun 2005 12:00:00 -0400</pubDate>
      <guid isPermaLink="false">urn:uuid:29f013421357d69f430f725d21062807</guid>
      <author>Tom Moertel</author>
      <link>http://blog.moertel.com/articles/2005/06/16/the-button_to-helper-is-now-part-of-rails</link>
      <category>web development</category>
      <category>rails</category>
      <category>rails</category>
      <category>get</category>
      <category>gwa</category>
      <category>safe</category>
      <category>unsafe</category>
      <category>post</category>
      <category>link_to</category>
      <trackback:ping>http://blog.moertel.com/articles/trackback/46</trackback:ping>
    </item>
    <item>
      <title>Taking the unsafe GETs out of Rails</title>
      <description>&lt;div class="update"&gt;

	&lt;p&gt;&lt;em&gt;Update 2005-06-17:&lt;/em&gt; The &lt;em&gt;button_to&lt;/em&gt; helper, introduced below, has been incorporated into the Rails framework and will be a part of the Rails 1.0 release. See &lt;a href="http://community.moertel.com/ss/space/start/2005-06-16/1"&gt;Good news: The button_to helper is now part of Rails!&lt;/a&gt; for more.&lt;/p&gt;


	&lt;p&gt;&lt;em&gt;Update 2005-05-28:&lt;/em&gt; I now have &lt;a href="http://community.moertel.com/ss/space/start/2005-05-08/1/button_to.rb"&gt;a more-recent version of the &lt;em&gt;button_to&lt;/em&gt; code&lt;/a&gt;, which adds support for the disabled &lt;span class="caps"&gt;HTML&lt;/span&gt; attribute. Thanks to Sean T Allen for the great idea and initial implementation.&lt;/p&gt;


&lt;/div&gt;

	&lt;p&gt;As I &lt;a href="http://community.moertel.com/ss/space/start/2005-05-06/1#Google_Web_Accelerator_offers_web_developers_an_important_opportunity"&gt;wrote earlier&lt;/a&gt;, it&amp;#8217;s time for web developers to do away with the fundamentally broken practice of using hypertext links to trigger dangerous events such as deleting things. One of the first places we ought to clean house is in the burgeoning &lt;a href="http://www.rubyonrails.org/"&gt;Rails web-application framework&lt;/a&gt;, where this practice is pervasive.&lt;/p&gt;


	&lt;p&gt;The primary culprit in Rails is the all-too-easy &lt;em&gt;link_to&lt;/em&gt; method, which is (presently) the orthodox means of creating links to any action, even unsafe ones. For example:&lt;/p&gt;


&lt;pre&gt;&lt;code&gt;link_to "Destroy", :controller =&amp;gt; 'accounts',
        :action =&amp;gt; 'destroy', :id =&amp;gt; 6
&lt;/code&gt;&lt;/pre&gt;

	&lt;p&gt;The above code generates the following &lt;span class="caps"&gt;HTML&lt;/span&gt; hypertext link, which when followed will merrily delete account number 6:&lt;/p&gt;


&lt;pre&gt;&lt;code&gt;&amp;lt;a href="/accounts/destroy/6"&amp;gt;Destroy&amp;lt;/a&amp;gt;
&lt;/code&gt;&lt;/pre&gt;

	&lt;p&gt;Because this practice is dangerous and contrary to the decade-old convention that links be safe, the &lt;em&gt;link_to&lt;/em&gt; method thoughtfully lets us request that a Javascript confirmation dialog be tacked onto the link for added protection:&lt;/p&gt;


&lt;pre&gt;&lt;code&gt;link_to "Destroy", ...,  :confirm =&amp;gt; "Are you sure?" 
&lt;/code&gt;&lt;/pre&gt;

	&lt;p&gt;The resulting &amp;#8220;safe&amp;#8221; &lt;span class="caps"&gt;HTML&lt;/span&gt;:&lt;/p&gt;


&lt;pre&gt;&lt;code&gt;&amp;lt;a href="/accounts/destroy/6" 
   onclick="return confirm('Are you sure?');"&amp;gt;Destroy&amp;lt;/a&amp;gt;
&lt;/code&gt;&lt;/pre&gt;

	&lt;p&gt;Unfortunately, the Javascript protection doesn&amp;#8217;t work. First, not all web browsers care about it. Lots of people surf with Javascript turned off. Second, a whole slew of things besides web browsers live on the Internet, and almost all of them are oblivious to Javascript. Web crawlers fall into this category. They will be more than happy to follow any link you feed to them. &amp;#8220;Hey, Googlebot just deleted every account in our database!&amp;#8221; Oops.&lt;/p&gt;


	&lt;p&gt;Thus another layer of protection is commonly used: authorization. The theory is that dangerous links can be safely corralled in the private parts of a web application, where the public and web crawlers cannot go. Only authorized users can get into those parts, and those users will be smart enough not to click on the truly dangerous links unless they really mean it.&lt;/p&gt;


	&lt;p&gt;The problem is, any number of intermediary agents can be operating &lt;em&gt;on behalf of an authorized user&lt;/em&gt;, and these agents are free to do anything the user is allowed to do, such as follow dangerous links. Google&amp;#8217;s Web Accelerator is one such agent. It tries to make your surfing faster by (among other things) pre-fetching the resources that are linked to on the pages you visit. And what happens if you, an authorized user, visit a page containing dangerous links? That&amp;#8217;s right, Web Accelerator will fetch the &amp;#8220;resources&amp;#8221; those links point to &amp;#8211; and delete a bunch of your stuff.&lt;/p&gt;


	&lt;p&gt;I hope by this point that I have argued convincingly that using links for unsafe actions is a bad idea. Even if you feel justified in ignoring the applicable parts of the &lt;span class="caps"&gt;HTTP&lt;/span&gt; RFCs, it&amp;#8217;s a bad idea. Even if you tack on Javascript confirmations and hide your links in authorization-protected zones of your site, it&amp;#8217;s a bad idea. It is, all around, a bad idea. Don&amp;#8217;t do it.&lt;/p&gt;


	&lt;p&gt;So what alternatives are there?  Read on for one possibility, &lt;em&gt;button_to&lt;/em&gt;.&lt;/p&gt;&lt;h3&gt;A &lt;em&gt;link_to&lt;/em&gt; alternative: &lt;em&gt;button_to&lt;/em&gt;&lt;/h3&gt;


	&lt;p&gt;If you shouldn&amp;#8217;t use links for unsafe actions, what should you use instead? Form buttons. Forms can be submitted via &lt;span class="caps"&gt;HTTP POST&lt;/span&gt; requests, and &lt;span class="caps"&gt;POST&lt;/span&gt; requests are understood to do potentially unsafe things. Web crawlers will not try to click your buttons. Intermediary user agents will not try to pre-submit your forms.&lt;/p&gt;


	&lt;p&gt;So, how do we make doing the right thing as easy as creating a link? My answer is 
&lt;em&gt;button_to&lt;/em&gt;, a method that takes the same parameters as the ever-popular &lt;em&gt;link_to&lt;/em&gt; but creates a tiny form that contains a single button instead of a link:&lt;/p&gt;


&lt;pre&gt;&lt;code&gt;button_to "Destroy", { :action =&amp;gt; 'destroy', :id =&amp;gt; 6 },
          :confirm =&amp;gt; "Are you sure?" 
&lt;/code&gt;&lt;/pre&gt;

	&lt;p&gt;The resulting &lt;span class="caps"&gt;HTML &lt;/span&gt;(reformatted for your viewing pleasure):&lt;/p&gt;


&lt;pre&gt;&lt;code&gt;&amp;lt;form method="post" action="/accounts/destroy/6" class="button-to"&amp;gt;
  &amp;lt;div&amp;gt;&amp;lt;input onclick="return confirm('Are you sure?');" 
              value="Destroy" type="submit"&amp;gt;
  &amp;lt;/div&amp;gt;
&amp;lt;/form&amp;gt;
&lt;/code&gt;&lt;/pre&gt;

	&lt;p&gt;The forms I create are given the class &lt;em&gt;button-to&lt;/em&gt;, which makes it easy to apply styles to them. With a little work, the buttons can look pretty darn good:&lt;/p&gt;


	&lt;p&gt;&lt;img src="http://community.moertel.com/ss/space/start/2005-05-08/1/button_to.png" title="screen capture showing Edit and Destroy buttons created with the button_to method" alt="screen capture showing Edit and Destroy buttons created with the button_to method" /&gt;&lt;/p&gt;


	&lt;p&gt;So that&amp;#8217;s my plea: Use a button. It&amp;#8217;s a simple solution to a potentially ugly problem. There&amp;#8217;s no need for Ajax or other non-portable Javascript trickery. Just use a button.&lt;/p&gt;


	&lt;p&gt;And it&amp;#8217;s easy, too. In a few minutes, I was able to &amp;#8220;clean house&amp;#8221; on the Rails application I&amp;#8217;m developing.&lt;/p&gt;


	&lt;h3&gt;The code&lt;/h3&gt;


	&lt;p&gt;If you&amp;#8217;re interested, here&amp;#8217;s the code for &lt;em&gt;button_to&lt;/em&gt;. It&amp;#8217;s only ten lines, but the docs make it look much longer.&lt;/p&gt;


&lt;pre&gt;&lt;code&gt;# Generates a form containing a sole button that submits to the URL
# given by _options_.  Use this method instead of +link_to+ for
# dangerous actions that do not have the safe HTTP GET semantics
# implied by using a hypertext link.
#
# The parameters are the same as for +url_to+.  Any _html_options_
# that you pass will be applied to the inner +input+ element.  The
# generated form element is given the class 'button-to', to which
# you can attach CSS styles for display purposes.
#
# Example 1:
#
#   # inside of controller 'feeds'
#   button_to "Edit", :action =&amp;gt; 'edit', :id =&amp;gt; 3
#
# Generates the following HTML (sans formatting):
#
#   &amp;lt;form method="post" action="/feeds/edit/3" class="button-to"&amp;gt;
#     &amp;lt;div&amp;gt;&amp;lt;input value="Edit" type="submit"&amp;gt;&amp;lt;/div&amp;gt;
#   &amp;lt;/form&amp;gt;
#
# Example 2:
#
#   button_to "Destroy", { :action =&amp;gt; 'destroy', :id =&amp;gt; 3 },
#             :confirm =&amp;gt; "Are you sure?" 
#
# Generates the following HTML (sans formatting):
#
#   &amp;lt;form method="post" action="/feeds/destroy/3" class="button-to"&amp;gt;
#     &amp;lt;div&amp;gt;&amp;lt;input onclick="return confirm('Are you sure?');" 
#                 value="Destroy" type="submit"&amp;gt;
#     &amp;lt;/div&amp;gt;
#   &amp;lt;/form&amp;gt;
# 
# *NOTE*: This method generates HTML code that represents a form.
# Forms are "block" content, which means that you should not try to
# insert them into your HTML where only inline content is expected.
# For example, you can legally insert a form inside of a +div+ or +td+
# element or in between +p+ elements, but not in the middle of a run
# of text.  (Bottom line:  Always validate your HTML before going
# public, especially if this paragraph seems confusing.)

def button_to(name, options = {}, html_options = nil)
  html_options = (html_options || {}).stringify_keys
  convert_confirm_option_to_javascript!(html_options)
  url, name = options.is_a?(String) ? 
    [ options,  name || options ] :
    [ url_for(options), name || url_for(options) ]
  html_options.merge!("type" =&amp;gt; "submit", "value" =&amp;gt; name)
  "&amp;lt;form method='post' action='#{h url}' class='button-to'&amp;gt;&amp;lt;div&amp;gt;" +
    tag("input", html_options) + "&amp;lt;/div&amp;gt;&amp;lt;/form&amp;gt;" 
end
&lt;/code&gt;&lt;/pre&gt;

	&lt;p&gt;Thanks for reading and happy unsafe-link hunting!&lt;/p&gt;</description>
      <pubDate>Sun, 08 May 2005 12:00:00 -0400</pubDate>
      <guid isPermaLink="false">urn:uuid:2e55c892774276d8ec6a19d9921e39d7</guid>
      <author>Tom Moertel</author>
      <link>http://blog.moertel.com/articles/2005/05/08/taking-the-unsafe-gets-out-of-rails</link>
      <category>ruby</category>
      <category>web development</category>
      <category>rails</category>
     