[Zope] DTML Syntax contd.

Martijn Faassen m.faassen@vet.uu.nl
Tue, 09 Nov 1999 17:24:24 +0100


Oliver Frommel wrote:

>could anyone explain the semantics of the various DTML constructs like ..
 
> foo
> _[foo]
> "_[foo]"
> "_['foo']"

First of all, we have the difference between this:

<dtml-var foo>

and this:

<dtml-var "foo">

These things actually mean:

<dtml-var name="foo">

and

<dtml-var expr="foo">

which makes things somewhat clearer. <dtml-var foo> tries to show the
object *named* foo. Showing an object means translating it to HTML
representation; in case of a property this simply means the value of the
property, in case of a DTML method this means executing the DTML
statements and returning the HTML result.

<dtml-var "foo"> does something else; it tries to evaluate the python
expression 'foo'. So you could say "foo + bar" or whatever.

Now, we'll get to _. Some ids in Zope which are valid in Zope are not
valid variable names in Python. Basically, Python variable names must
start with an underscore or a letter, and may contain letters,
underscores and numbers. Python variables may not contain '-' or '.',
however, as they have special meanings in Python. 

As an aside, I sometimes wonder if it hadn't been a better design
decision to disallow any non-Python name as a Zope id. The advantage of
the current scheme is that you can make objects with ids with 'foo.pdf'
which will result in a nice download, but perhaps a separate 'alias'
name for objects like that would've been a better idea. I don't know.
Maybe in Zope 3. ;)

So, sometimes you'd still like to access variables which contain special
characters. 'sequence-item' is such a weird freak; I seriously don't
know what possessed whomever came up with it not to call it
'sequence_item' as it'd make a lot of DTML look a *lot* cleaner.
Luckily, '_' comes to the rescue.

'_' is a special magic variable which is always accessible in DTML, and
it contains in a dictionary all the variables in the current 'namespace'
(and thus it would contain 'foo' and also 'sequence-item'. You get to
the elements of the dictionary in the normal Python way, with the []
subscript:

<dtml-var "_['sequence-item']">

Note that we want the variable with the name 'sequence-item', so we have
to put quotes around it (we use single quotes as we used double quotes
around the whole expression). If we *hadn't* put quotes around
sequence-item, it would've looked for the variable with a name equal to
the *contents* of 'sequence-item', whatever that may be. We can exploit
this in some cases.

Imagine that it depends on certain conditions whether we want to show
variable 'foo' or 'bar'. In fact, we've set the variable 'hoi' with the
name of the variable we want to display:

<dtml-call "REQUEST.set('hoi', 'bar')">

Alternatively we could've used the 'let' tag around it all:

<dtml-let hoi="'bar'">
..
</dtml-let>

(we need to put extra quotes around 'bar' here because the let tag
expects an expression, and this expression is a string).

Now, when we want to display any variable that's currently in 'hoi', we
use the _ trick:

<dtml-var "_[hoi]">

This will evaluate to:

<dtml-var "_['bar']">

which is the same as:

<dtml-var "bar">

so that accomplishes our trick.

> I think I read through most of the docs but there is no extensive description
> of the exact syntax (not even in the DTML ref).. Please correct me if I am wrong 

Though there is documentation, there are plenty of sections of DTML
which remain rather dark and mysterious. More documentation needs to be
written. :)

I hope this helped!

Regards,

Martijn