Something I don't understand is whether there is anything about this
proposed feature that can't be accomplished with a simple function.
IIUC, the proposal turns this:
foo = "spam & eggs"
`Here, have some {foo}.`
...into something like this (I am making up a more readable repr):
TemplateLiteral(
template = " Here, have some {foo}.",
tokens = (("Here, have some ", True), ("spam & eggs", False)),
)
What is it about this task that cannot be accomplished with a class and
function? Skeleton might look like:
@dataclass
class TemplateLiteral:
template: str
tokens: Sequence(Tuple(str, bool)) = field(init = False)
def templify(s: str) -> TemplateLiteral:
...
And use it like this:
>>> templify("Here, have some {foo}.")
TemplateLiteral(template = " Here, have some {foo}.", tokens = (("Here,
have some ", True), ("spam & eggs", False)))
What is it about this task that requires it being handled at the language
level...?
---
Ricky.
"I've never met a Kentucky man who wasn't either thinking about going home
or actually going home." - Happy Chandler
On Thu, Jun 10, 2021 at 9:36 AM David Mertz <[email protected]> wrote:
> Strong -1
>
> As others noted in prior discussion, even if this existed, it works be an
> anti-pattern for SQL. So basically, it's just baking in an HTML-only
> template language into the language syntax.
>
> Python already had excellent HTML templating in libraries. The fact Django
> has a function with a long name just suggests importing it with a shorter
> name.
>
> Python has many uses having nothing to do with web pages. This could make
> sense for PHP (does anyone use that still?). It's a poor for for Python.
>
> On Thu, Jun 10, 2021, 2:31 AM Thomas Güttler <[email protected]>
> wrote:
>
>> Thank you Guido, Chris, Matt and Richard for your feedback to my last
>> email.
>>
>> Here is an updated version called "Template Literals".
>>
>> I am looking for a core developer who can sponsor this PEP.
>>
>> Please speak up if you want to help me.
>>
>> Regards,
>> Thomas Güttler
>>
>> Source and updates: Pre-PEP 9999
>> <https://github.com/guettli/peps/blob/master/pep-9999.rst>
>>
>> PEP: 9999
>> Title: Template Literals
>> Author: Thomas Güttler <info at thomas-guettler.de>
>> Sponsor: TODO
>> Status: Draft
>> Type: Standards Track
>> Content-Type: text/x-rst <http:///dev/peps/pep-0012>
>> Created: 08-Jun-2021
>> Python-Version: TODO
>> Post-History: 08-Jun-2021
>> ------------------------------
>>
>> Contents
>>
>> - Abstract <#m_2818986526677889823_m_-138379983175526697_abstract>
>> - Motivation <#m_2818986526677889823_m_-138379983175526697_motivation>
>> - Rationale <#m_2818986526677889823_m_-138379983175526697_rationale>
>> - Specification
>> <#m_2818986526677889823_m_-138379983175526697_specification>
>> - Security Implications
>> <#m_2818986526677889823_m_-138379983175526697_security-implications>
>> - Reference Implementation
>> <#m_2818986526677889823_m_-138379983175526697_reference-implementation>
>> - Alternative Ideas
>> <#m_2818986526677889823_m_-138379983175526697_alternative-ideas>
>> - Rejected Ideas
>> <#m_2818986526677889823_m_-138379983175526697_rejected-ideas>
>> - Open Issues
>> <#m_2818986526677889823_m_-138379983175526697_open-issues>
>> - References <#m_2818986526677889823_m_-138379983175526697_references>
>> - Copyright <#m_2818986526677889823_m_-138379983175526697_copyright>
>>
>> Abstract <#m_2818986526677889823_m_-138379983175526697_id6>
>>
>> This PEP adds Template Literals to Python.
>>
>> To avoid code injection like XSS or SQL-injection Template Literals can
>> help you to write save Python code.
>>
>> Template Literals provide an easy way to access the local and global
>> variables (like f-strings), so that passing a dictionary to the Template is
>> not necessary.
>> Motivation <#m_2818986526677889823_m_-138379983175526697_id7>
>>
>> In the context of web development Python can do more than providing REST
>> APIs via http. With the trend to Server-Side-Rendering, we face a
>> fundamental question:
>>
>> How to create HTML with Python?
>>
>> If you use the FrOW pattern (HTML fragments over the wire) [1]
>> <#m_2818986526677889823_m_-138379983175526697_frow>, then you will be
>> writing small methods returning small HTML fragments.
>>
>> As a developer I want to pass escaped data into template literals to be
>> as simple as possible.
>> Rationale <#m_2818986526677889823_m_-138379983175526697_id8>
>>
>> Imagine you want to create a small HTML fragment in Python, and return it
>> as HTTP-Response:
>>
>> HttpResponse(f'''
>> <h1>Hi {name}</h1>
>> Your messages: {messages}''')
>>
>> The problem in above example is, that no escaping gets done.
>>
>> In above example "name" and "messages" should be treated differently.
>>
>> The variable "name" should get escaped. For example if the name is "Mary
>> & Bob", the result should be "Mary & Bob".
>>
>> The variable "messages" contains HTML which is already escaped. It should
>> not be escaped again.
>>
>> Most frameworks have a way to do this conditional escaping.
>>
>> For example Django uses conditional_escape()
>> <https://docs.djangoproject.com/en/3.2/ref/utils/#django.utils.html.conditional_escape>
>> [2] <#m_2818986526677889823_m_-138379983175526697_id2>
>>
>> With the help of conditional_escape() the above problem could be solved
>> like this:
>>
>> HttpResponse(f'''
>> <h1>Hi {conditional_escape(name)}</h1>
>> Your messages: {conditional_escape(messages)}''')
>>
>> This solution has two drawbacks:
>>
>> 1. It is too verbose. Typing "conditional_escape(...)" again and
>> again is cumbersome.
>> 2. If a conditional_escape() gets forgotten Cross-site scripting
>> attacks could be possible, since malicious users could inject HTML.
>>
>> Specification <#m_2818986526677889823_m_-138379983175526697_id9>
>>
>> Template Literals use backticks (like JavaScript Template Literals
>> <https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Template_literals>
>> [3] <#m_2818986526677889823_m_-138379983175526697_id4>)
>>
>> Example:
>>
>> name = 'Mary & Bob'
>> messages = `<ul><li>message1</li><li>message2</li></ul>`
>> return HttpResponse(`
>> <h1>Hi {name}</h1>
>> Your messages: {messages}
>>
>> Today: {datetime.date.today()}`)
>>
>> Expressions within curly braces get handled liked in f-strings (PEP-498).
>>
>> The Template Literal creates an instance of the new class
>> types.TemplateLiteral.
>>
>> types.TemplateLiteral has two attributes:
>>
>> - template: The raw string inside the backticks.
>> - tokens: A list of tuples: (value, is_literal).
>>
>> For above example this would mean:
>>
>> template = '''
>> <h1>Hi {name}</h1>
>> Your messages: {messages}
>>
>> Today: {datetime.date.today()}'''
>>
>> tokens = [
>> ('\n <h1>Hi ', True),
>> ('Mary & Bob', False),
>> ('</h1>\n Your messages: ', True),
>> (<TemplateLiteral "<ul><li>message1</li><li>message2</li></ul>">, False),
>> ('\n\n Today: ', True),
>> (<datetime.date(2021, 6, 9)>, False)
>> ]
>>
>> It is outside this PEP how a consumer of TemplateLiteral handles this
>> data structure.
>>
>> For example the Django web framework could transform a TemplateLiteral to
>> a SafeString like this:
>>
>> def template_literal_to_safestring(template_literal):
>> return mark_safe(
>> ''.join(
>> [
>> conditional_escape(value) if not is_literal else value
>> for (value, is_literal) in template_literal.tokens
>> ]
>> )
>> )
>>
>> This PEP is not related or constraint to the Django framework. It is even
>> not related to HTML. It can be used for any kind of templating.
>> Security Implications <#m_2818986526677889823_m_-138379983175526697_id10>
>>
>> Template Literals can execute arbitrary code (like f-strings).
>>
>> Template Literals get created by Python developers, not by users. If you
>> want to make templates available for users (for example if you develop a
>> CMS), then please use a different solution.
>> Reference Implementation
>> <#m_2818986526677889823_m_-138379983175526697_id11>
>>
>> TODO
>> Alternative Ideas <#m_2818986526677889823_m_-138379983175526697_id12>
>>
>> Instead of backticks for example t'...' could be used.
>> Rejected Ideas <#m_2818986526677889823_m_-138379983175526697_id13>
>>
>> TODO
>> Open Issues <#m_2818986526677889823_m_-138379983175526697_id14>
>>
>> TODO
>> References <#m_2818986526677889823_m_-138379983175526697_id15>
>> [1] <#m_2818986526677889823_m_-138379983175526697_id1> FrOW, "HTML
>> Fragments Over the Wire". Frameworks like Unpoly, Hotwire or htmx.
>> [2] <#m_2818986526677889823_m_-138379983175526697_id3>
>> https://docs.djangoproject.com/en/3.2/ref/utils/#django.utils.html.conditional_escape
>> [3] <#m_2818986526677889823_m_-138379983175526697_id5>
>> https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Template_literals
>> Copyright <#m_2818986526677889823_m_-138379983175526697_id16>
>>
>> This document is placed in the public domain or under the
>> CC0-1.0-Universal license, whichever is more permissive.
>> _______________________________________________
>> Python-ideas mailing list -- [email protected]
>> To unsubscribe send an email to [email protected]
>> https://mail.python.org/mailman3/lists/python-ideas.python.org/
>> Message archived at
>> https://mail.python.org/archives/list/[email protected]/message/LYAC7JC5253QISKDLRMUCN27GZVIUWZC/
>> Code of Conduct: http://python.org/psf/codeofconduct/
>>
> _______________________________________________
> Python-ideas mailing list -- [email protected]
> To unsubscribe send an email to [email protected]
> https://mail.python.org/mailman3/lists/python-ideas.python.org/
> Message archived at
> https://mail.python.org/archives/list/[email protected]/message/6MMGTZL7VGXXLYL6UZMQ3MRHJW6EA74L/
> Code of Conduct: http://python.org/psf/codeofconduct/
>
_______________________________________________
Python-ideas mailing list -- [email protected]
To unsubscribe send an email to [email protected]
https://mail.python.org/mailman3/lists/python-ideas.python.org/
Message archived at
https://mail.python.org/archives/list/[email protected]/message/XZ22MH2RU643HHYMYYEDOC3F7H22XBBW/
Code of Conduct: http://python.org/psf/codeofconduct/