10.6 Example

Now we are going to illustrate STL with a more complex example. Building up on the Task Tracker from the Chapter 5.4, we are going to write a method that produces an HTML page showing all the tasks.

The Template

    <?xml version="1.0" encoding="UTF-8"?>
    <html xmlns="http://www.w3.org/1999/xhtml"
      xmlns:stl="http://xml.itools.org/namespaces/stl">
      <head></head>
      <body>
        <h2>Task Tracker</h2>
        <stl:block repeat="task tasks">
          <h4>
            #${task/id}: ${task/title} (<em>${task/state}</em>)
          </h4>
          <p>${task/description}</p>
        </stl:block>
      </body>
    </html>

The Namespace

    # Import from itools
    from itools.handlers import get_handler
    from itools.stl import stl

    # Build the namespace
    namespace = {}
    tasks = []
    for i, task in enumerate(self.tasks):
        tasks.append({'id': i,
                      'title': task.title,
                      'description': task.description,
                      'state': task.state,
                      'is_open': task.state == 'open'})
    namespace['tasks'] = tasks

    # Load the template
    handler = get_handler('template.xml')

    # Process the template and return the output
    return stl(handler, namespace, mode='xhtml')

The Output

The output may be something like (depends on the content of self.tasks):

    <?xml version="1.0" encoding="UTF-8"?>
    <html xmlns:stl="http://xml.itools.org/namespaces/stl"
      xmlns="http://www.w3.org/1999/xhtml">
      <head></head>
      <body>
        <h2>Task Tracker</h2>
        <h4>
          #0: Re-write the chapter about writing handler classes.
          (<em>closed</em>)
        </h4>
        <p>A new chapter...

The Figure 10.2 shows how the HTML may look with a browser.

\includegraphics[width=\textwidth ]{figures/task_tracker}
Figure 10.2: The task tracker view

Modes

In the latter example, we have called STL with a mode parameter. By default STL returns a stream of events like "element is opening", "text", element is closing". When using the xhtml mode, STL will return a valid XHTML document as a Python string. There is also an html mode returning an HTML document with forbidden end tags omitted, e.g. <br> instead of the invalid <br/>.

The reason we use the stream mode by default is that STL will not accept to interpret (X)HTML content by default, thus protecting from unexpected code injection. STL will however accept streams and merge them into the ouput. To inject an (X)HTML string, you must first parse it using the XMLParser or HTMLParser.

In the real world, we compute and combine several templates, for instance a generated form into a page into a website layout, and only the final stl call would be asked for an html output (valid XHTML support is still little spreaded).

If you are interested in streams, see the Section 16.1 in the XML chapter.