[Zope] Testing multiple values for existance - still
Paul Winkler
slinkp23@yahoo.com
Tue, 25 Sep 2001 13:42:49 -0400
On Tue, Sep 25, 2001 at 11:54:33AM +0200, Oliver Sturm wrote:
> On 25.09.2001 10:24:48 -0400 Phil Harris <phil.harris@zope.co.uk> wrote:
> > The first statement tests first for existence, and only then for value.
> > The second assumes existence and only tests for value.
>
> I got that at last :-). But WHY? I reckon it may be as simple as that the
> "'s render the whole thing a Python expression instead of something that can
> be handled directly by Zope. Is that so?
Exactly. Inside a dtml tag, anything in quotes is treated as python code.
> If yes, I'd consider that a large
> drawback and inconsistency... and does Python syntax for the test have to be
> so complicated?
It's not "complicated" in normal python programming, which is usually
easy, flexible, and powerful. But when you're limited to what you can
fit between quotes in a dtml tag, you can't really take advantage of
python effectively. It was never meant to be a language for
one-liners.
But of course, we have python scripts and external methods, which are
much better for jobs like this.
If all you want is to know if any of a bunch of zope objects exist in
this folder, or if any of some properties has a true value, it's ugly
and hard to read if you do it in the dtml-if tag:
<dtml-if "(_.hasattr('foo') and foo) or (_.hasattr('bar') and bar)">
... and it just gets worse if you want to test for more names!
So I'd make a python script like this:
## Script (Python) "check_for_any"
##bind container=container
##bind context=context
##bind script=script
##bind subpath=traverse_subpath
##parameters=*args
##title=
##
found = None
for a in args:
try:
x=getattr(context, a)
if x:
found = 1
break # Jump out of the loop, no more tests needed
except AttributeError:
continue
return found
The key thing to notice is that the one argument is *args. In python,
that means that this function takes a variable number of arguments,
and they will be stored in a list of the given name (in this case,
args).
Now you can do this in your dtml:
<p>Checking for one thing...
<dtml-if "check_for_any('foo')">
...
</dtml-if>
<p>Checking for more things...
<dtml-if "check_for_any('foo', 'bar', 'baz', 'bat', 'baf')">
...
</dtml-if>
Much nicer, eh?
--
................ paul winkler ................
custom calendars: http://www.calendargalaxy.com
A member of ARMS: http://www.reacharms.com
home page: http://www.slinkp.com