diff doc/templates.txt @ 720:f0bb2c5ea0ff experimental-newctxt

newctxt branch: Merged revisions [678:835] via svnmerge from [source:trunk].
author cmlenz
date Fri, 11 Apr 2008 08:42:11 +0000
parents 6e21c89d9255
children
line wrap: on
line diff
--- a/doc/templates.txt
+++ b/doc/templates.txt
@@ -116,9 +116,12 @@
   >>> from genshi.template import MarkupTemplate
   >>> tmpl = MarkupTemplate('<h1>Hello, $name!</h1>')
   >>> stream = tmpl.generate(name='world')
-  >>> print stream.render()
+  >>> print stream.render('xhtml')
   <h1>Hello, world!</h1>
 
+.. note:: See the Serialization_ section of the `Markup Streams`_ page for
+          information on configuring template output options.
+
 Using a text template is similar:
 
 .. code-block:: pycon
@@ -126,13 +129,15 @@
   >>> from genshi.template import TextTemplate
   >>> tmpl = TextTemplate('Hello, $name!')
   >>> stream = tmpl.generate(name='world')
-  >>> print stream.render()
+  >>> print stream
   Hello, world!
 
-.. note:: See the Serialization_ section of the `Markup Streams`_ page for
-          information on configuring template output options.
+.. note:: If you want to use text templates, you should consider using the
+          ``NewTextTemplate`` class instead of simply ``TextTemplate``. See
+          the `Text Template Language`_ page.
 
 .. _serialization: streams.html#serialization
+.. _`Text Template Language`: text-templates.html
 .. _`Markup Streams`: streams.html
 
 Using a template loader provides the advantage that “compiled” templates are
@@ -203,8 +208,8 @@
 Code Blocks
 ===========
 
-XML templates also support full Python code blocks using the ``<?python ?>``
-processing instruction:
+Templates also support full Python code blocks, using the ``<?python ?>``
+processing instruction in XML templates:
 
 .. code-block:: genshi
 
@@ -212,21 +217,38 @@
     <?python
         from genshi.builder import tag
         def greeting(name):
-            return tag.b('Hello, %s!' % name') ?>
+            return tag.b('Hello, %s!' % name) ?>
     ${greeting('world')}
   </div>
 
 This will produce the following output:
 
-.. code-block:: genshi
+.. code-block:: xml
 
   <div>
     <b>Hello, world!</b>
   </div>
 
+In text templates (although only those using the new syntax introduced in
+Genshi 0.5), code blocks use the special ``{% python %}`` directive:
+
+.. code-block:: genshitext
+
+  {% python
+      from genshi.builder import tag
+      def greeting(name):
+          return 'Hello, %s!' % name
+  %}
+  ${greeting('world')}
+
+This will produce the following output::
+
+  Hello, world!
+
+
 Code blocks can import modules, define classes and functions, and basically do
 anything you can do in normal Python code. What code blocks can *not* do is to
-produce content that is included directly in the generated page.
+produce content that is emitted directly tp the generated output.
 
 .. note:: Using the ``print`` statement will print to the standard output
           stream, just as it does for other Python code in your application.
@@ -248,7 +270,11 @@
 into a sandboxable template engine; there are sufficient ways to do harm even
 using plain expressions.
 
-.. note:: Code blocks are not currently supported in text templates.
+.. warning:: Unfortunately, code blocks are severely limited when running
+             under Python 2.3: For example, it is not possible to access
+             variables defined in outer scopes. If you plan to use code blocks
+             extensively, it is strongly recommended that you run Python 2.4
+             or later.
 
 
 .. _`error handling`:
@@ -256,13 +282,56 @@
 Error Handling
 ==============
 
-By default, Genshi allows you to access variables that are not defined, without
-raising a ``NameError`` exception as regular Python code would:
+By default, Genshi raises an ``UndefinedError`` if a template expression
+attempts to access a variable that is not defined:
 
 .. code-block:: pycon
 
   >>> from genshi.template import MarkupTemplate
   >>> tmpl = MarkupTemplate('<p>${doh}</p>')
+  >>> tmpl.generate().render('xhtml')
+  Traceback (most recent call last):
+    ...
+  UndefinedError: "doh" not defined
+
+You can change this behavior by setting the variable lookup mode to "lenient".
+In that case, accessing undefined variables returns an `Undefined` object,
+meaning that the expression does not fail immediately. See below for details.
+
+If you need to check whether a variable exists in the template context, use the
+defined_ or the value_of_ function described below. To check for existence of
+attributes on an object, or keys in a dictionary, use the ``hasattr()``,
+``getattr()`` or ``get()`` functions, or the ``in`` operator, just as you would
+in regular Python code:
+
+  >>> from genshi.template import MarkupTemplate
+  >>> tmpl = MarkupTemplate('<p>${defined("doh")}</p>')
+  >>> print tmpl.generate().render('xhtml')
+  <p>False</p>
+
+.. note:: Lenient error handling was the default in Genshi prior to version 0.5.
+          Strict mode was introduced in version 0.4, and became the default in
+          0.5. The reason for this change was that the lenient error handling
+          was masking actual errors in templates, thereby also making it harder
+          to debug some problems.
+
+
+.. _`lenient`:
+
+Lenient Mode
+------------
+
+If you instruct Genshi to use the lenient variable lookup mode, it allows you
+to access variables that are not defined, without raising an ``UndefinedError``.
+
+This mode can be chosen by passing the ``lookup='lenient'`` keyword argument to
+the template initializer, or by passing the ``variable_lookup='lenient'``
+keyword argument to the ``TemplateLoader`` initializer:
+
+.. code-block:: pycon
+
+  >>> from genshi.template import MarkupTemplate
+  >>> tmpl = MarkupTemplate('<p>${doh}</p>', lookup='lenient')
   >>> print tmpl.generate().render('xhtml')
   <p></p>
 
@@ -272,7 +341,7 @@
 .. code-block:: pycon
 
   >>> from genshi.template import MarkupTemplate
-  >>> tmpl = MarkupTemplate('<p>${doh.oops}</p>')
+  >>> tmpl = MarkupTemplate('<p>${doh.oops}</p>', lookup='lenient')
   >>> print tmpl.generate().render('xhtml')
   Traceback (most recent call last):
     ...
@@ -284,42 +353,14 @@
 .. code-block:: pycon
 
   >>> from genshi.template import MarkupTemplate
-  >>> tmpl = MarkupTemplate('<p>${type(doh) is not Undefined}</p>')
+  >>> tmpl = MarkupTemplate('<p>${type(doh) is not Undefined}</p>',
+  ...                       lookup='lenient')
   >>> print tmpl.generate().render('xhtml')
   <p>False</p>
 
 Alternatively, the built-in functions defined_ or value_of_ can be used in this
 case.
 
-Strict Mode
------------
-
-In addition to the default "lenient" error handling, Genshi lets you use a less
-forgiving mode if you prefer errors blowing up loudly instead of being ignored
-silently.
-
-This mode can be chosen by passing the ``lookup='strict'`` keyword argument to
-the template initializer, or by passing the ``variable_lookup='strict'`` keyword
-argument to the ``TemplateLoader`` initializer:
-
-.. code-block:: pycon
-
-  >>> from genshi.template import MarkupTemplate
-  >>> tmpl = MarkupTemplate('<p>${doh}</p>', lookup='strict')
-  >>> print tmpl.generate().render('xhtml')
-  Traceback (most recent call last):
-    ...
-  UndefinedError: "doh" not defined
-
-When using strict mode, any reference to an undefined variable, as well as
-trying to access an non-existing item or attribute of an object, will cause an
-``UndefinedError`` to be raised immediately.
-
-.. note:: While this mode is currently not the default, it may be promoted to
-          the default in future versions of Genshi. In general, the default
-          lenient error handling mode can be considered dangerous as it silently
-          ignores typos.
-
 Custom Modes
 ------------
 
Copyright (C) 2012-2017 Edgewall Software