[Barry] > And to make effbot and Raymond happy, it won't auto-promote to unicode > if everything's an 8bit string. Glad to see that my happiness now ranks as a development objective ;-) > There will be updated unit tests, and I will update the documentation > and the PEP as appropriate -- if we've reached agreement on it. +1 Beautiful job. Barry asked me to bring up one remaining implementation issue for discussion on python-dev. The docs clearly state that only python identifiers are allowed as placeholders: [_A-Za-z][_A-Za-z0-9]* The challenge is that templates can be exposed to non-programmer end-users with no reason to suspect that one letter of their alphabet is different from another. So, as it stands right now, there is a usability issue with placeholder errors passing silently: >>> fechas = {u'hoy':u'lunes', u'mañana':u'martes'} >>> t = Template(u'¿Puede volver $hoy o $mañana?') >>> t.safe_substitute(fechas) u'¿Puede volver lunes o $mañana?' The substitution failed silently (no ValueError as would have occurred with $@ or a dangling $). It may be especially baffling for the user because one placeholder succeeded and the other failed without a hint of why (he can see the key in the mapping, it just won't substitute). No clue is offered that the Template was looking for $ma, a partial token, and didn't find it (the situation is even worse if it does find $ma and substitutes an unintended value). I suggest that the above should raise an error: ValueError: Invalid token $mañana on line 1, column 24 It is easily possible to detect and report such errors (see an example in nondist/sandbox/string/curry292.py). The arguments against such reporting are: * Raymond is smoking crack. End users will never make this mistake. * The docs say python identifiers only. You blew it. Tough. Not a bug. * For someone who understands exactly what they are doing, perhaps $ma is the intended placeholder -- why force them to uses braces: ${ma}ñana. In addition to the above usability issue, there is one other nit. The new invocation syntax offers us the opportunity for to also accept keyword arguments as mapping alternatives: def substitute(self, mapping=None, **kwds): if mapping is None: mapping == kwds . . . When applicable, this makes for beautiful, readable calls: t.substitute(who="Barry", what="mailmeister", when=now()) This would be a simple and nice enchancement to Barry's excellent implementation. I recommend that keyword arguments be adopted. Raymond
RetroSearch is an open source project built by @garambo | Open a GitHub Issue
Search and Browse the WWW like it's 1997 | Search results from DuckDuckGo
HTML:
3.2
| Encoding:
UTF-8
| Version:
0.7.4