Thanks for the summary, Julien.
Since I'm one of the Grinches that closed ticket #1105 :-), let me try
to explain the motivation behind that action.
I'm in complete agreement that template tags are too hard to write
from scratch, and I'm interested in discussing any proposal that
addresses this.
However, my concern with modifications like the one proposed by #1105
is that simple_tag becomes more complex, yet still fails to hit a
range of 'simple' use cases -- or, at least, fails to hit them in a
way that is broadly useful.
I can't deny that adding 'takes_context' would open up opportunities
to simple_tag that aren't currently available. But there are also some
fairly major practical limitations that are born out of the
fundamental framework that simple_tag provides.
As an example of what I'm talking about -- #14262 is a manifestation
of a use case that is undeniably simple: "get_function() as var". This
pattern is used in several places in Django's own codebase.
However, adding "takes_context" to simple_tag won't allow you to
completely hit the #14262 use case without dropping the ability to
specify the context variable that get_function() is stored. Although
this may seem like a little detail, it's a fairly important part of
the API if you want your tag to be useful to a broad audience --
without this capability, your template tag must always insert the same
context variable. This limits the ways that you can use your tag
without inducing collisions -- for example, you can't call the tag
twice in the same template.
This gets even more acute when you consider takes_nodelist. From a
quick audit, the only builtin tags that could be replaced with a
'simple_tag with takes_nodelist' are comment, spaceless, and the
old-style ifequal family of tags, which is hardly a compelling list of
use cases. In all other tags, there is a need to do some sort of
parsing of the input tokens to provide 'as' placeholders and the like.
So - the reason #1105 was closed was because simple_tag should be
simple. Adding complexity to simple_tag in an attempt to do an end run
around the difficulties of writing custom tags just leaves us with a
hideously complex simple tag, and misses the real underlying problem
-- that writing custom tag parsers is difficult, and shouldn't be.
Now, the one piece of the puzzle that undermines my argument here is
inclusion_tag, which provides a 'takes_context' argument, providing
precedent. I'm also hamstrung by the fact that I don't have a good
counterproposal.
To that end, I'm willing to be practical and concede that adding
takes_context would at the very least be consistent, even if it still
fails to hit a large range of test cases.
However, this is orthogonal to #14262, because of the inability to
define a tag that is assigned to an arbitrary context variable that I
mentioned earlier. There is also the broader (and completely nebulous)
proposal regarding making tag parsers easier to write. That's a *much*
bigger can of worms.
However, as with all things, I'm also interested in hearing community opinion.
Yours,
Russ Magee %-)
As an example of what I'm talking about -- #14262 is a manifestation
of a use case that is undeniably simple: "get_function() as var". This
pattern is used in several places in Django's own codebase.
To that end, I'm willing to be practical and concede that adding takes_context would at the very least be consistent, even if it still fails to hit a large range of test cases.
There is also the broader (and completely nebulous)
proposal regarding making tag parsers easier to write. That's a *much*
bigger can of worms.
What you've described is essentially what the current proposal *is* -
i.e., add takes_context to context_tag (#1105), but also add a
`get_function() as var` shortcut (#14262). The exact color of #14262
hasn't been picked, but assignment_tag is as good as any I've heard.
Yours,
Russ Magee %-)
I'm only one voice, but I'm *really* not a fan of decorators changing
function signatures like that. I don't deny it works; it just grates
me the wrong way.
I've already indicated my preferred approach -- consistency with inclusion_tag.
Yours
Russ Magee %-)