
Thanks for the comments, Paul and Paul. On Sun, Jun 27, 2021 at 1:14 AM Paul Moore <p.f.moore@gmail.com> wrote:
On Sun, 27 Jun 2021 at 08:11, Paul Bryan <pbryan@anode.ca> wrote:
It looks like you're suggesting hard-coding specific language escape
conventions into f-strings?
That's how I understood the proposal too. Hard coding specific conventions shouldn't be part of a language construct IMO.
Yes, I am. I understand the objection that the language shouldn't know too much about html or sql. My viewpoint is that injection attacks have been on the OWASP Top Ten list since the inception of that list and it is unlikely that it's going to fall off the top ten anytime soon. In my opinion "practicality beats purity". There's a reason why many template languages include built-in escaping operators.
What if instead you were to allow delegation to some filter function? Then, it's generic and extensible.
def html(value: Any): filtered = ... # filter here return filtered
f'{!!html}<a href="{url}">...<a>'
As I mentioned in a footnote, a mechanism for adding conversions would be advantageous. The specific mechanism you describe would work for f-strings but not work for str.format. Furthermore, someone reading my suggested {!!html}} would know what it meant while someone reading yours would have to go read the referenced function to be sure what it did. I'm not against such a mechanism. I'm just not sure it sufficiently addresses the injection risk. Well, there's already a way of handling that:
f'<a href="{html(url)}">...<a>'
That does not work for str.format, only for f-strings. So all you're saving is a bit of typing. I believe that this provides more clarity than your version, which of course, I am already aware of. I also know that people are much more likely to remember to add a single {!!html} at the front of each template than to add {html()} everywhere. Furthermore, projects could adopt a convention of marking all html strings (because EIBTI) and have a linter flag strings that did not include {!!html}} or {!!}. --- Bruce