Introducing HTML::Template

The Comprehensive Perl Archive Network (CPAN) contains a vast array of modules that make a developer’s life much easier. You would do well to browse the treasures at before embarking on any new project.

As an example, in this tutorial I’ll provide a brief overview of how to install the HTML::Template module. But first, let’s see how you can install a Perl module on your system.

Installing Perl

Perl Installation on Windows

Perl for Windows is available as a free download at Installing a module is surprisingly simple; however, it does require that the module is in ActiveState’s ppd format.

Installation can be performed from the ppm shell:

C:>ppm  PPM - Programmer's Package Manager version 3.1.  Copyright (c) 2001 ActiveState SRL. All Rights Reserved. 

Entering interactive shell. Using Term::ReadLine::Stub as readline library. 

Type 'help' to get started. 

ppm> install HTML-Template

It’s as simple as that. If any dependencies exist, they will be installed first. Note that not all Perl modules have been packaged for ppm. To find out if a module is available, type search <module> in the shell.

If you require a module that’s not in ActiveState’s repository, it’s possible that someone else has packaged it. You can find a list of additional repositories by installing the PPM::Repositories module, then running this code:

use PPM::Repositories; 

for my $rep ( keys %Repositories ) {      next unless $Repositories{$rep}->{Active};      next unless grep { $_ == 5.8 } @{ $Repositories{$rep}->{PerlV} };      print $rep, $/, $Repositories{$rep}->{location}, $/,        $Repositories{$rep}->{Notes}, $/, $/;  }

Failing all else, you could install the module by hand. We discuss how to do this in the Unix/Linux section below.

Perl Installation on Unix/Linux

Perl installation on Unix and Linux can be achieved in two ways: manually, or automatically.

The Manual Way

Download the module, unzip and untar it.

$ tar zxvf HTML-Template-xx.tar.gz  $ cd HTML-Template-x.x  $ perl Makefile.PL  $ make  $ make test  $ make install

If you wish to install the file manually under Windows, you’ll need to download nmake.exe from Microsoft. Then, simply replace make with nmake in the instructions above.

While the majority of modules are pure Perl, some may contain C code, in which case you will need a C compiler. (A compiler is never required for ppm packages).

Make sure that you peruse the README file before you install a module.

The Automatic Way

Some modules are dependent on other modules, which in turn may have other dependencies. Installing all these modules can be a bit tedious, but there is an alternative: install the CPAN package. Then, simply invoke the cpan shell from the command line:

$ cpan

The first time cpan is run, it will configure itself. Answer the prompts, and when the configuration is complete, you can install your package:

cpan> install HTML::Template

If any dependencies exist, cpan can fetch and install them.

Now that you know how to install Perl modules, let’s take a closer look at one of Perl’s templating solutions: HTML::Template.

Introducing HTML::Template

Perl is great as a prototyping language because it’s very expressive: developers can do a lot in a few lines. A corollary of this is that it’s easy for a small application to morph into something much bigger than anticipated. Maintaining and extending such an application can become quite onerous.

Writing large Web applications using traditional CGI techniques is an approach that doesn’t scale very well. If you’re the only developer, mixing your HTML with your Perl may be tolerable, but this approach doesn’t work when you’re part of a team. Your typical Web designer won’t want to start changing your Perl code if the design needs to be changed.

Most Web languages provide some means to separate the application code from the markup code. In most cases, the HTML is placed in separate template files, which then act as containers for dynamic data. With languages like PHP, the templates can be thought of as an extension of the core language itself, although, if you’re like me, you’ll still prefer third-party template solutions like Smarty.

Perl has a number of templating solutions. HTML::Mason and the Template Toolkit are two of the most popular solutions, and offer powerful capabilities. Developers can place sophisticated logic in their templates, but unless they’re disciplined, they can undo many of the benefits of using templates in the first place, including the separation of the business logic from the interface.

HTML::Template is a lightweight alternative. It aims to provide the most basic functionality for creating Web pages, and no more. The philosophy is to keep your Perl and your HTML separate.

A Simple Example

Below is an example of a simple template, template1.tmpl. Note that it consists mainly of standard HTML with a single non-standard tag, tmpl_var, where the attribute name is set to day.

<html>  <head>    <title>Template 1</title>  </head>  <body>  Today is <tmpl_var name=day>  </body>  </html>

Using the template template from Perl is very simple:

1.  #!c:/perl/bin/perl -T  2.  use CGI qw(:all);  3.  use HTML::Template;  4.  use POSIX;  5.  print header;  6.  my $template = HTML::Template->new(filename => 'template1.tmpl');  7.  $template->param(day => strftime('%A', localtime()) );  8.  print $template->output();

Line 1 simply states where the Perl interpreter is located. The -T switch means we’re in taint mode. This provides an extra level of security to Web applications by telling Perl that we should not trust any user input unless we explicitly state otherwise. This is good practice: you should always include this switch as a matter of course.

Line 2 imports the module. This isn’t 100% necessary: we could write out own CGI functions by hand, but this risks introducing all sorts of bugs and security issues. The CGI module is very well-tested, and you should always use it when writing CGI applications.

At line 3, we import the HTML::Template module. Line 4 brings in the standard /POSIX functionality. This allows us easily to determine the day of the week later on. Keep in mind Perl’s philosophy of There’s More Than One Way to do It (TMTOWTDI) — we could have done this using any number of date modules.

Line 5 is CGI shorthand for print "Content-Type: text/htmlnn". We need to return the content type before we output the rest of the Web page. On line 6, we create the template object. The file name of our template is supplied as the only parameter.

Line 7 sets the <tmpl_var> tag with the name of "day" to the day of the week. If you’re not familiar with the POSIX strftime function, %A is shorthand for returning the day of the week. The same formatting masks are available to PHP and C.

And finally, at line 8, we display the Web page.

So now we’ve been introduced to the basic HTML::Template philosophy: we create mostly HTML code, and we intersperse some <tmpl> placeholders for dynamic content. The syntax is kept deliberately simple; your Web designers can simply maintain the site’s look and feel through standard HTML and a small number of additional tags.


Although the <tmpl_var> tag is extremely useful, it isn’t sufficient by itself. Often, we’ll need to present a set of data in a tabular format. This is where the <tmpl_loop> tag comes in:

<html>   <head>   <title>Template 2</title>   </head>   <body>   <table>     <tr>       <th>Language</th>       <th>Description</th>     </tr>     <tmpl_loop name="language">     <tr>       <td><tmpl_var name="language_name"></td>       <td><tmpl_var name="description"></td>     </tr>     </tmpl_loop>   </table>   </body>   </html>

Essentially, we have a loop called language, and we have two variables inside it, called language_name and description. On the Perl side of things, HTML::Template expects loops to be passed as an array reference of hash (associative array) references:

1.  #!c:/perl/bin/perl -T   2.  use CGI qw(:all);   3.  use HTML::Template;   4.  my @languages = (   5.      {   6.          language_name => 'Perl',   7.          description   => 'Practical Extraction and Report Language'   8.      },   9.      {   10.          language_name => 'PHP',   11.          description   => 'Hypertext Preprocessor'   12.      },   13.      {   14.          language_name => 'ASP',   15.          description   => 'Active Server Pages'   16.      },   17.  );   18.  print header;   19.  my $template = HTML::Template->new( filename => 'template2.tmpl' );   20.  $template->param( language => @languages );   21.  print $template->output();

Lines 4-17 define the array of hash references. The hash key names must be the same as the template <tmpl_var> names inside <tmpl_loop>. At line 20, a reference to the languages array is passed to the template tag <tmpl_loop name=language>.

Setting the loop data in our Perl script by hand is simple enough, but in the real world, we’re likely to retrieve our template data from a database. Let’s say we have a table called "languages", with a column called "language_name" and another called "description." We can just as easily generate the output from a query:

1.  #!c:/perl/bin/perl -T   2.  use CGI qw(:all);   3.  use HTML::Template;   4.  use DBI;  

5.  my $dbh = DBI->connect('dbi:<driver>:<my db>', '<user>', '<password>');  

6.  my $sql = "select * from languages";   7.  my $sth = $dbh->prepare($sql);   8.  $sth->execute();  

9.  my $languages = $sth->fetchall_arrayref({   10.     language_name => 1,    11.     description   => 1}   12.  );  

13.  print header;   14.  my $template = HTML::Template->new( filename => 'template2.tmpl' );   15.  $template->param( language => $languages );   16.  print $template->output();

At line 4, we bring in the DBI, Perl’s database module. Line 5 connects to the MySQL database. Replace <driver>, <my db>, <user> and <password> with whatever is appropriate for your system. This isn’t production code — we wouldn’t normally hard-code this information, and we would typically include checks to see if any of our database interactions failed.

Lines 6-8 prepare our SQL select statement and execute it. In lines 9-12 we fetch the entire result set. DBI offers many different formats for the data. An array reference is best for us, because this is the format that HTML::Template expects. We can specify in a hash reference the columns that we wish to name in our array.


Finally, we may wish to alter the output based on certain conditions. HTML::Template offers both an IF and an UNLESS tag. Suppose, for example, that we want to present a special message if no languages are found:

<html>   <head>   <title>Template 3</title>   </head>   <body>   <table>       <tmpl_if name=language>     <tr>       <th>Language</th>       <th>Description</th>     </tr>     <tmpl_loop name="language">     <tr>       <td><tmpl_var name="language_name"></td>       <td><tmpl_var name="description"></td>     </tr>     </tmpl_loop>       <tmpl_else>     Sorry, no languages were found       </tmpl_if>   </table>   </body>   </html>

All that we’ve done here is wrap our loop in a conditional. If the language parameter is true, the results are displayed; otherwise, we’ll let the person viewing the page know that no records were found.

UNLESS is similar to IF, except that instead of checking if a condition is true, we're seeing if it isn't (i.e. "unless true, do this").  Multiple Templates Per Page  Unless your page is trivial, you'll most likely want to add headers, footers and even some form of navigation. You can include other templates quite easily:
<tmpl_include name="menu.tmpl">
 Is that It? We've covered the basics of HTML::Template here. Sam Tregar, its author, was very careful not to include any bells and whistles that might undermine the philosophy of keeping the business logic separate from the user interface. Despite the limited template syntax, I've never had a requirement for anything more sophisticated. However, against Sam's better judgment, he created an extension called HTML::Template::Expr, which allows a developer to add expression and function support. Lastly, for the PHP and Python programmers out there, HTML::Template has been ported to your language of choice. More information can be found at


Category: perl Time: 2005-04-22 Views: 2

Related post

  • Whether to abstract small repeating code segments in HTML templates? 2015-04-26

    (The framework used in question is AngularJS so the question can be translated as "Whether to introduce Directives for small repeating code segments in Views") As a developer who focuses on Java backend development, I am very used to the DRY pri

  • drupal_add_js in html template file 2012-01-24

    I am using a zen subtheme and I am trying to add some javascript using the drupal_add_js on a certain node. When I use the drupal_add_js from within the html--node--XX.tpl.php file, it does not work. But when I use it in the page--node--XX.tpl.php it

  • Create Your Own WordPress Theme from an HTML Template 2012-08-07

    WordPress has become the most widely used blogging platform in the world, estimated to be used on a quarter of a billion websites online today. WordPress works as a blog, but also as a straightforward content management system, ready to use with sear

  • How to convert static HTML template to drupal theme 2012-12-06

    Is there any tools available to convert html template to drupal theme and is there any modules that make drupal 7 theming much easier ? --------------Solutions------------- There is no such tool that converts HTML to Drupal theme. But there are servi

  • How to override the default zen html template depending on a node type? 2012-12-24

    I have a themes which inherit from zen template. The zen template has an html.tpl.php, and I would like to override that html.tpl.php for one content type. Let's say my theme name is test and my content type is called foo, I have tried the following

  • How to integrate premium responsive html template to umbraco? 2013-01-14

    How to integrate premium responsive html template to umbraco? I have been wondering, that whether there is any kind of set of standards OR Any additional code to integrate my premium html web template to umbraco cms? --------------Solutions----------

  • HTML template for Custom Content Type 2013-01-17

    I'm reasonably new to Drupal... I've known about it for quite a number of years and have played around with it in the past, but only in the past 4 months have I started to make a serious website with it. Possibly a bit harder to configure than say Wo

  • How to define HTML templates with QGIS Server? 2013-08-07

    I usually use HTML templates in map files to show nicely formatted popups on my WMS layers with Openlayers. Here is the doc on templating with mapserver I'd like to know if it is possible to do the same in GQIS Server and if yes how? Thanks. --------

  • couldn't load site name in html template 2014-01-14

    <?php print $site_name; ?> Why I couldn't perform the above code in 'html.tpl.php'. This works find in page template. Please suggest how to load this in html template --------------Solutions------------- There's no $site_name variable added to html.

  • Rich Text column - How to add HTML Template 2014-08-21

    I must add a HTML Template to reach Text Column, and it schould be Visible always. How Could I done it ? Only to give a template rich text to html, that nowan schould edit it --------------Solutions------------- You could use an announcements list to

  • How to properly specify font size and face in a classified Ads HTML template? 2014-12-23

    How to properly specify font size and face in a classified Ads HTML template without html, body and head tags (these tags will be cutted), when template will be put in iframe on page? The classifieds website will use mixed styles which will come part

  • Apex Email: Html template 2015-09-23

    I am using the following code to send an email to user using HTML template. This issue which i am facing is i am getting email but the body of the email is blank. Am I doing any mistake in the code. List<String> sendTo = new List<String>(); Em

  • Visualforce page shows CSS errors for the same styling used by a html template 2015-09-26

    I downloaded a free html responsive template from the web and trying to convert it to a visualforce page. The page I am trying to reproduce is blank, so there is no content except css, js and nav bar. I copy-pasted the content body to my new visualfo

  • Unable to access merge field in html template in salesforce 2015-11-03

    I have created HTML template with merge field. But I am unable to access that field value. I am using contact First name as a merge field. After sending mail it looks: Hi {!Contact.FirstName}, Can anyone please help me for this.

  • Turning an HTML template into a Django template 2015-11-06

    When you purchase an HTML template, usually everything is mixed in together... html, css, images and js. An example template may look like this: account.html category.html contact.html /fonts /img item-detail.html media.html register.html style.css a

  • Remove comments from HTML templates using Maven 2016-01-15

    Is there a standard and easy way how to remove comments from HTML templates (Thymeleaf) using a Maven plugin ? It would be nice if it can do this conventionally only for <body> content and leave browser hints in <head untouched. I know I can filt

  • Javascript variables in Django HTML templates 2016-01-17

    I'm writing a Django app and while somewhat familiar with Django I'm pretty unfamiliar with JavaScript. I'm adding a few lines of JavaScript into one of my pages in order to include a map. The script simply encompasses initializing the map and then a

  • Customizing Django Forms in html template 2016-01-18

    I have an django model with ManytoManyfield relationship and created model form for the same. Please provide me the solution how to render this modelform in Html Template as Table format.

  • HTML Templates and HTML Import - Inner Script not Executing in Firefox 2016-01-27

    I am using webcomponents.js to polyfill Firefox support of web components. When loading an HTML template through an HTML import, a script within the template does not execute once the custom-element based on the template is added to the DOM of the ma

iOS development

Android development

Python development

JAVA development

Development language

PHP development

Ruby development


Front-end development


development tools

Open Platform

Javascript development

.NET development

cloud computing


Copyright (C), All Rights Reserved.

processed in 1.341 (s). 13 q(s)