Hi all,

I started work replacing Django's if with the "smart-if" template tag 
by Chris Beaven ( http://www.djangosnippets.org/snippets/1350/ ) 

Of course, it is not as simple as it looks...

4 issues:

1) Handling non-existent variables
==================================

The current smart-if does not handle the case of non-existent 
variables like Django does.  (For example, something like

 {% if foo or bar %}

when one of foo or bar is not defined in the context.)

To do this properly, I think the best approach would be something like 
"almost three valued logic", which would work as follows:

1) variables that don't exist are represented by Null
2) all operators return either True or False, never Null
3) for 'not', 'and' and 'or', Null effectively acts like False
   (so "not Null" == True, "Null or True" == True etc)
4) for all comparison operators, if either argument is Null then
   the result is False e.g. "Null == Null" is False
   "Null > 1" is False, "Null <= 1" is False, except
   "!=", which should return true if either value is Null.

Any comments on this approach? I've started to implement this, and it 
works OK so far, just needs a bit more work.

2) TEMPLATE_STRING_IF_INVALID breaks everything
===============================================

The smart 'if' tag allows for filters:

{% if articles|length >= 5 %}

To achieve this, it puts its arguments through FilterExpression.  If 
settings.TEMPLATE_STRING_IS_INVALID is not an empty string, this means 
that:

{% if foo %}blah{% endif %}

will render 'blah' instead of '' if 'foo' is not in the context.  This 
causes test failures at the moment.  We could change the tests, but 
that is a backwards incompatibility, and it highlights a fundamental 
change in the behaviour of {% if %}, which basically makes 
TEMPLATE_STRING_IF_INVALID useless for even its stated purpose of 
debugging, because the logic of a template will now be changed.

Personally, I care nothing for TEMPLATE_STRING_IF_INVALID, as there 
are other things that it breaks, and I never use it. But obviously I 
can't just think of myself here.

If there was an easy solution that didn't change the behaviour of the 
if tag in this case that would be great, but I can't see one.

3) Behaviour of 'x and b or y'
==============================

Previously this was a syntax error.  In Chris's code, it is fine and 
works like Python. I would vote for keeping the smart-if as it is, as 
I don't see the value of complicating the implementation to disallow 
something that could be useful sometimes.

4) Behaviour of 'not'
=====================
Current Django will interpret 'not' as a variable if there is no 
ambiguity e.g.

   {% if not %}blah{% endif %}

This is not documented, but the behaviour is specified in detail in 
the tests, so changing it would be a backwards incompatibility. The 
smart-if is different (the above is a syntax error), and I suspect 
that making the smart-if behave like current Django could complicate 
things a lot.

IMO, current Django behaviour here is complete misfeature! I don't 
know of any other language where keywords can be treated as variables 
if the keyword doesn't make sense in that position...

Regards,

Luke

-- 
"He knows the way I take: when he has tried me, I shall come forth 
as gold" (Job 23:10).

Luke Plant || http://lukeplant.me.uk/

--

You received this message because you are subscribed to the Google Groups 
"Django developers" group.
To post to this group, send email to django-develop...@googlegroups.com.
To unsubscribe from this group, send email to 
django-developers+unsubscr...@googlegroups.com.
For more options, visit this group at 
http://groups.google.com/group/django-developers?hl=en.


Reply via email to