Using HTML Templates with Perl CGI Applications

This demonstrates how Perl CGI applications that display a web page can be developed and maintained more efficiently by using HTML templates rather than hard-coded "print" statements.

Our sample application gets the hostname and ip address of the user, then returns a simple greeting which includes the sum of the octets of the user's ip address.

Typically this Perl CGI application would be coded like this...

#!/usr/bin/perl -w
use strict;

my $remote_host = $ENV{'REMOTE_HOST'};
my $remote_addr = $ENV{'REMOTE_ADDR'};
my @octet = split(/\./, $remote_addr);
my $secret_number = $octet[0] + $octet[1] + $octet[2] + $octet[3];

print "Content-type: text/html\n\n";
print "<html>\n";
print "<head>\n";
print "<title>Your secret number</title>\n";
print "</head>\n";
print "<body bgcolor=\"#FFFFCC\">\n";
print "Hello, visitor from <font color=\"green\"><b>$remote_host</b></font>.\n";
print "<p>\n";
print "Your ip address is <font color=\"purple\"><b>$remote_addr</b></font>.\n";
print "<p>\n";
print "Your secret number is <font color=\"red\"><b>$secret_number</b></font>.\n";
print "</body>\n";
print "</html>\n";
exit;

See the results

This does the job, but anything more than the simplest web page is difficult to design and maintain with this technique. And turning this over to a web designer who only knows how to use a WYSIWYG editor is impossible. This could be coded more efficiently using a "here document", but you still do not want to give your carefully coded Perl programs to your web designer every time a change to the page design is required.

A better solution is to separate the data from the presentation of the data by using an HTML template. All data processing is done within the Perl script, then the results are merged with an HTML template. The template is a standard HTML page that can be easily designed and modified with any text editor or most WYSIWYG editors.

Here is what an HTML template for our example would look like...

<html>
<head>
<title>Your secret number</title>
</head>
<body bgcolor="#FFFFCC">
Hello, visitor from <font color="green"><b><<$remote_host>></b></font>.
<p>
Your ip address is <font color="purple"><b><<$remote_addr>></b></font>.
<p>
Your secret number is <font color="red"><b><<$secret_number>></b></font>.
</body>
</html>

This template can be easily maintained by a web designer. You can even view it as a regular web page. Substitutable parameters are placed within double angle brackets: <<...>>. Program variables or even expressions can be placed within the angle brackets.

Here is our new script...

#!/usr/bin/perl -w
use strict;

my $remote_host = $ENV{'REMOTE_HOST'};
my $remote_addr = $ENV{'REMOTE_ADDR'};
my @octet = split(/\./, $remote_addr);
my $secret_number = $octet[0] + $octet[1] + $octet[2] + $octet[3];

print "Content-type: text/html\n\n";

# Read HTML from template.
merge_file("hello_template.html");
exit;

sub merge_file {
  # Read HTML from template.
  my $template_file = shift;
  open(TEMPLATE, $template_file) or print "Error opening $template_file. $!";
  # temporarily disable "uninitialized value" warnings
  $^W = 0;
  while (<TEMPLATE>) {s/<<(.*?)>>/$1/eeg; print;}
  $^W = 1;
  close(TEMPLATE);
}

See the results

Using HTML templates separates data processing functions from the presentation of the data. This allows us to easily use complex HTML pages for the presentation of our data. The templates can be edited by a web designer using either a text or WYSIWYG editor, while the back-end processing is managed by the software developer.

©2005 Greg McCann