4 ms·
First, I'm really glad you took a look at this and thought deeply about how to improve it. It is possible to do import star, and if you really know what you're
by ljlolel 16y ago
First, I'm really glad you took a look at this and thought deeply about how to improve it.
It is possible to do import star, and if you really know what you're doing, you can. But, you quickly start running into issues with polluting the namespace (which is why Guido says not to do it). For example, one HTML tag is p, so now we have to use a different accumulator. I find p very natural because I think "print" every time, I used 't' for a while (months) but it just never clicked. Furthermore, HTML has other tags like a, so now you can't use either p or a as one-off variables anywhere without weird bugs or confusing reads of the code, not to mention other common names.
Moreover, I even tried using import html as h to save typing. It actually made the templates less readable (I think because of less long explicitness). It can take a few minutes, but actually you quickly get used to the repeated p(html( and it just becomes a useful guidepost when reading through a template quickly.
Your second suggestion of a language is nice and clean, but you lose a lot in terms of flexibility and power. For example, you cannot easily loop, or insert a readable conditional, and you definitely cannot assign a helper variable which even Django now acknowledges can be useful.
I have been using these templates in production on medium-sized, complex sites for years. I have added enough functionality and simplicity so that I can do everything I need to do, plus it is obvious how to do it. A lot of toy template languages have not seen extensive use in a variety of applications with heavy load, so they are missing subtle, key elements which can be show-stopper issues in practice. Finally, languages keep snowballing massive APIs (to patch up these issues) which become so difficult to completely learn that easy things become hard.
- anthonyb 16y ago> I find p very natural because I think "print" every time ... I can do everything I need to do, plus it is obvious how to do it Probably more because you've used it for a while. I generally prefer longer variable names to help with readability, which makes the accumulator/with technique more verbose and harder to read. If you don't like import * , you can use a combination of from ...lib.html import p, h1, h2 and from ...lib import html, but as long as your namespace is clean (ie. use __all__) and you're clear that the module is designed to be imported that way, I don't see that it's a huge issue, particularly if it clears up a lot of clutter. There's also nothing in that API that prevents you looping, or assigning helper variables - you just store local variables before you generate your template or create sections of your template a bit at a time. Or use list/generator comprehensions, which would fit the functional paradigm a bit better. A couple of examples: ul( *[li(option.name) for option in options], style="dropdown", ...) def index_page(request): my_name = reqest.GET.get('name', 'Bob') head = html.head( title('Hello, %s' % my_name)) body = html.body( h1('...'), p('..')) return html.html(head, body) Of course, all of this is developed using the POOMA methodology, so there might be some hideous limitation, but I can't see any from a few minutes thought.