Abstract

Active Lisp Pages (ALP) is a server scripting environment for creating dynamic pages and interactive applications over the Web. These pages can then be used in conjunction with any Web server, since the output of the ALP processor can be an HTML page. An ALP script runs when a client (most likely a browser) requests an ALP file/page from the server. The server calls the ALP engine, which reads through the requested file, generates a Lisp response function that will build the page (when run), and compiles it. Finally, the ALP engine executes the response function (which will send the page back to the client). The preliminary processing occurs only the first time the page is hit or, alternatively ALP pages can be preprocessed. Since the server does the processing, there is no need to worry about whether a browser can process scripts. The server transmits standard HTML to the browser. Server-side scripts cannot be copied, because only the result of the script is returned to the browser. Since users cannot view the script commands that created the pages they are viewing, the system is secure.

Motivation

In today's Internet-pervaded world, Web applications are becoming more and more important. We call a Web application a computer program that interacts with the user via Web pages. Construction of Web applications started with CGI-BIN-type interactions. Today they are built in many different fashions such as PHP, Active Server Pages (ASP), Java Servlets, direct server APIs, or Apache Server modules.

Some of these systems share a trait with ALP: the use of server pages. Since browsers understand only static HTML, the server must find a way to generate that. One good solution is to embed scripts in the HTML pages with the help of a programming language. For example, Microsoft's ASP uses Visual Basic, Sun's Java Server Pages (JSP) uses Java, and ALP uses Lisp. The solution that many people used before server pages made their debut was to write a program that then wrote the HTML page.

ALP offers a server page engine that allows the embedding of Lisp scripts within HTML code. The ALP server page engine solution has several advantages (many of these are shared with other server page solutions):

The Lisp server page approach has advantages over other server page solutions:

Active Lisp Pages

An Active Lisp Pages (ALP) file is a text file containing any combination of text, HTML tags, and ALP script commands. A script is a series of commands or expressions written in Lisp. Scripts must be differentiated from plain page text by delimiters. A delimiter is a character or sequence of characters marking the beginning or end of a unit. In the case of HTML, these delimiters are the less than (<) and the greater than (>) symbols, which enclose HTML tags. ALP uses the (two character) delimiters <% and %> to enclose scripts code. Any expression that is valid in the scripting language (in this case Lisp) is valid inside the ALP delimiters.

By using a translated example from [McPherson:2000], multiple features from ALP can be explained. The following example illustrates a dynamic Web page that prints a first paragraph with today's date and a second paragraph with either Good Morning or Good Afternoon, depending on the time of the day. The example shows three important concepts: the binding of variables (as in the multiple-value-bind line), the automatic evaluation and display of expressions (as in <%= d %>), and the conditional selection of page segments.

<html> 
  <body> 
    <%-- uses lisp's time --%>
    <% (multiple-value-bind (s min h d m y) 
         (decode-universal-time 
            (get-universal-time)) %>

    <h1>Welcome</h1> 

    <p>
      Today's date: 
      <%= d %> - 
      <%= m %> - 
      <%= y %>.
    </p>

    <p> 
      <% (cond ((less-than h 12) %>
      Good Morning 
      <% ) (t %>
      Good Afternoon 
      <% )) %>
    </p>

    <% ) %>
  </body>
</html>
    

Tags

Different scripting delimiters meet special needs when a Web page is written. The scripting types are:

Expressions

ALP tags are of the two types described above. Logic tags are directly transcribed to the engine, and expression tags are transcribed in such a way that they are evaluated and printed. Three special types of expressions escape characters. On each special type, the = character in the <= delimiter is replaced by some other character.

The following table shows various examples of expression, and the possible escapings:

Expression Result
<%= "andres" > andres
<%= (+ (* 3 3) (* 4 4)) > 25
<%= "7 > 4" > 7 > 4
<%& "7 > 4" > 7 &gt; 4
<%% "http://www/menlo park" > http://www/menlo%20park

Parameters

A URL can contain a number of parameters, usually called CGI parameters. Those parameters form a list of key/value pairs, and are available at the ALP page level. They are accessed through the function get-parameter. The following example illustrates an ALP page that adds two numbers given as parameters a and b:

<html> 
  <body> 
    <% (let ((a (read-from-string 
                 (get-parameter "a"))) 
             (b (read-from-string 
                 (get-parameter "b")))) %>
    <p>
      Sum: <%= a %> + <%= b %> = 
      <b><%= (+ a b) %></b>
    </p>

    <% ) %>
  </body>
</html>
    

If the previous page is requested through a hypothetical URL http://www.ai.sri.com/alp/add.alp?a=3&b=4 the resulting page would contain the line:

Sum: 3 + 4 = 7
    

Parameters can be extracted with the shorthand macro with-parameters. They can also be set with set-parameter.

Inclusion and Page Parameters

To be true to the reusability promise, ALP provides a way of including ALP pages inside other pages. It also is able to pass arguments between different pages. Otherwise the inclusion mechanism can provide only static reuse. An include function in ALP allows the developer to include other pages. Pages to be included normally do not have surrounding <html> and <body> tags. All ALP pages can declare arguments that are expected by using the declaration delimiters. These declarations must be the first non-comment to be present in the page. Consider the following example of an inclusion page add-inc.alp that has the same basic structure as the previous example:

<%-- parameters are integers --%>
<%@ (x y) %>
<p>
  Sum: <%= x %> + <%= y %> = 
  <b><%= (+ x y) %></b>
</p>
    

Another page can reuse add-inc.alp. The following example shows a reuse with the parameters coming from the URL and a reuse with literal integers:

<html> 
  <body> 
    <%-- Use CGI parameters --%>
    <% (let ((a (read-from-string 
                 (get-parameter "a"))) 
             (b (read-from-string 
                 (get-parameter "b")))) %>
    <% (include "add-inc.alp" a b) %>
    <% ) %>
    <%-- Use two literals --%>
    <% (include "add-inc.alp" 234 567) %>
  </body>
</html>
    

XML Syntax

One of the limitations of the previous approach to writing ALP pages is that they are not well-formed XML pages. The advantage of having well-formed XML is the use that one can make of many available tools for such format, such as validators, schemas, and XSLT stylesheets. By adopting the strategy of [XSP:1999] of exchanging the special delimiters for normal XML tags, ALP achieves the objective of having an alternative syntax that is equivalent to the syntax shown earlier, while being well-formed XML. The following code shows the first example with XSP syntax:

<html> 
  <body> 
    <xsp:comment>uses lisp's time</xsp:comment>
    <xsp:logic>(multiple-value-bind (s min h d m y) 
                  (decode-universal-time (get-universal-time))</xsp:logic>

    <h1>Welcome</h1> 

    <p>
      Today's date: 
      <xsp:expression>d</xsp:expression> - 
      <xsp:expression>m</xsp:expression> - 
      <xsp:expression>y</xsp:expression>.
    </p>

    <p> 
      <xsp:logic>(cond ((less-than h 12)</xsp:logic>
      Good Morning 
      <xsp:logic>) (t</xsp:logic>
      Good Afternoon 
      <xsp:logic>))</xsp:logic>
    </p>

    <xsp:logic>)</xsp:logic>
  </body>
</html>
    

A disadvantage of this syntax is that it is much more verbose, so the resulting ALP pages might be longer. Nevertheless, there is a one-to-one correspondence between the two syntaxes, so it is possible to build an automated translator (in fact, a four- or five-line sed program should do the trick).

ALP Engine

The ALP engine is in charge of the following tasks:

The usual cyle ALP goes through when responding to an ALP page URL request is as follows:

Conclusions

The development of the Active Lisp Pages (ALP) framework brings to the Lisp environment the advantage of having server pages. Although Lisp servers such as CL-HTTP and AllegroServe already exist, no well-known alternatives exist for developing server pages. The current design and implementation conform to most of the better-known server pages alternatives in other languages (such as ASP and JSP) but preserve a Lisp nature. The design is clean in the sense that it integrates gracefully with any Lisp environment and with any Lisp Web server. The dynamic nature of Lisp makes for a very easy implementation, the only hard step being the construction of a parser for the extended HTML syntax. The advantages of having an ALP tool are a complete Lisp development toolset leveraging of HTML knowledge and very rapid prototyping.

References

Tim Berners-Lee, Hypertext Markup Language - 2.0, p. 12, November 1995.

Tim Berners-Lee, Uniform Resource Identifiers (URI): Generic Syntax, p. 6-10, August 1998.

Brendan Eich, JavaScript Language Specification, November 1996.

Scott McPherson, JavaServer Pages: A Developer's Perspective, April 2000.

XSP Logicsheet Guide, 1999.

ent="\end{thebibliography}"/>