GeezerVisonThe World Wide Web, restored to 800 pixels of glory. | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Home|About|Gaming cabinet|Archives|How it works|Starter sites | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
GeezerVison is showing github.com — gh-132661: Document t-strings and `templatelib` by davepeck · Pull Request #135229 · python/cpython Conversation
| ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
@hugovk Thank you for the review and the helpful early feedback! Useful to know about linking. (FWIW this is very early stage still, so I expect plenty more linting and other issues that we'll eventually resolve.) |
Sorry, something went wrong.
There was an error while loading. Please reload this page.
There was an error while loading. Please reload this page.
There was an error while loading. Please reload this page.
|
At EuroPython sprints, @AA-Turner says he still wants to review this. As release manager, I've given him until the first release candidate on Tuesday when I'll merge this. We can always make further updates, but let's at least have something for RC1. |
Sorry, something went wrong.
There was an error while loading. Please reload this page.
There was a problem hiding this comment.
The reason will be displayed to describe this comment to others. Learn more.
I would adivse against using !class.attr in Sphinx roles as this would also make class being rendered, and instead, I suggest using regular double-backticks instead or use attr + ~, although this would create a link that we may not want it.
On Sphinx' side, I think we should really do something for supporting !~ because it becomes annoying to lose semantics.
Sorry, something went wrong.
There was an error while loading. Please reload this page.
There was an error while loading. Please reload this page.
There was an error while loading. Please reload this page.
There was an error while loading. Please reload this page.
There was an error while loading. Please reload this page.
There was an error while loading. Please reload this page.
There was an error while loading. Please reload this page.
|
Thanks @picnixz for the feedback! Think I took care of all your suggestions.
That would be really nice! |
Sorry, something went wrong.
There was an error while loading. Please reload this page.
There was an error while loading. Please reload this page.
There was a problem hiding this comment.
The reason will be displayed to describe this comment to others. Learn more.
As a sphinx maintainer I'm happy to see that directives are used but I fear that it could make the text a bit too "heavy to read". My main concern is that the theme we use actually creates lots of boxes and only a few online pages relies on directives, and prefer indicating the parameter type or the attribute type in the text directly (for instance for "expression", we would rather say "The text of a valid Python expression as a str, possibly empty".
I won't block this PR because of this choice as it's an entirely new page but in the future we may want to remove parameter boxes from the documentation.
If we don't have time until the RC release to fix the links/refs/inline code, we can do it later. For the content itself, I'm mostly good.
Sorry, something went wrong.
There was an error while loading. Please reload this page.
|
|
||
| .. attribute:: expression | ||
|
|
||
| :returns: The text of a valid Python expression, or an empty string. |
There was a problem hiding this comment.
The reason will be displayed to describe this comment to others. Learn more.
No need for :returns: You can write the attribute directive body the same way you did for Template.interpolations for instance.
Sorry, something went wrong.
There was an error while loading. Please reload this page.
There was a problem hiding this comment.
The reason will be displayed to describe this comment to others. Learn more.
Sorry for the delay, I abandoned my review and started over as various things had gotten out of date. I'll apply the simple fixes manually for time.
A
Sorry, something went wrong.
There was an error while loading. Please reload this page.
| @@ -462,7 +462,7 @@ Glossary | |||
| core and with user code. | |||
|
|
|||
| f-string | |||
There was a problem hiding this comment.
The reason will be displayed to describe this comment to others. Learn more.
| f-string | |
| f-string | |
| f-strings |
Sorry, something went wrong.
There was an error while loading. Please reload this page.
|
|
||
| See also :term:`borrowed reference`. | ||
|
|
||
| t-string |
There was a problem hiding this comment.
The reason will be displayed to describe this comment to others. Learn more.
| t-string | |
| t-string | |
| t-strings |
Sorry, something went wrong.
There was an error while loading. Please reload this page.
| * 115 (``ord('s')``): ``!s`` string formatting | ||
| * 114 (``ord('r')``): ``!r`` repr formatting | ||
| * 97 (``ord('a')``): ``!a`` ASCII formatting |
There was a problem hiding this comment.
The reason will be displayed to describe this comment to others. Learn more.
| * 115 (``ord('s')``): ``!s`` string formatting | |
| * 114 (``ord('r')``): ``!r`` repr formatting | |
| * 97 (``ord('a')``): ``!a`` ASCII formatting | |
| * 97: ``!a`` :func:`ASCII <ascii>` formatting (``ord('a')``) | |
| * 114: ``!r`` :func:`repr` formatting (``ord('r')``) | |
| * 115: ``!s`` :func:`string <str>` formatting (``ord('s')``) |
Sorry, something went wrong.
There was an error while loading. Please reload this page.
| .. class:: TemplateStr(values) | ||
|
|
||
| A t-string, comprising a series of :class:`Interpolation` and :class:`Constant` | ||
| nodes. |
There was a problem hiding this comment.
The reason will be displayed to describe this comment to others. Learn more.
Add a note on AST node ordering
| .. class:: TemplateStr(values) | |
| A t-string, comprising a series of :class:`Interpolation` and :class:`Constant` | |
| nodes. | |
| .. class:: TemplateStr(values, /) | |
| Node representing a template string literal, comprising a series of | |
| :class:`Interpolation` and :class:`Constant` nodes. | |
| These nodes may be any order, and do not need to be interleaved. |
Sorry, something went wrong.
There was an error while loading. Please reload this page.
| .. versionadded:: 3.14 | ||
|
|
||
|
|
||
| .. class:: Interpolation(value, str, conversion, format_spec) |
There was a problem hiding this comment.
The reason will be displayed to describe this comment to others. Learn more.
| .. class:: Interpolation(value, str, conversion, format_spec) | |
| .. class:: Interpolation(value, str, conversion, format_spec=None) |
Sorry, something went wrong.
There was an error while loading. Please reload this page.
| - Rather than evaluating to a ``str`` object, t-strings evaluate to a | ||
| :class:`~string.templatelib.Template` object from the |
There was a problem hiding this comment.
The reason will be displayed to describe this comment to others. Learn more.
| - Rather than evaluating to a ``str`` object, t-strings evaluate to a | |
| :class:`~string.templatelib.Template` object from the | |
| * Rather than evaluating to a ``str`` object, template string literals evaluate | |
| to a :class:`~string.templatelib.Template` object from the |
Sorry, something went wrong.
There was an error while loading. Please reload this page.
| :class:`~string.templatelib.Template` object from the | ||
| :mod:`string.templatelib` module. | ||
|
|
||
| - The :func:`format` protocol is not used. Instead, the format specifier and |
There was a problem hiding this comment.
The reason will be displayed to describe this comment to others. Learn more.
| - The :func:`format` protocol is not used. Instead, the format specifier and | |
| * The :func:`format` protocol is not used. Instead, the format specifier and |
Sorry, something went wrong.
There was an error while loading. Please reload this page.
| processes the resulting :class:`~string.templatelib.Template` object to | ||
| decide how to handle format specifiers and conversions. | ||
|
|
||
| - Format specifiers containing nested replacement fields are evaluated eagerly, |
There was a problem hiding this comment.
The reason will be displayed to describe this comment to others. Learn more.
| - Format specifiers containing nested replacement fields are evaluated eagerly, | |
| * Format specifiers containing nested replacement fields are evaluated eagerly, |
Sorry, something went wrong.
There was an error while loading. Please reload this page.
| attribute of the resulting :class:`!Interpolation` object; if ``precision`` | ||
| is (for example) ``2``, the resulting format specifier will be ``'.2f'``. |
There was a problem hiding this comment.
The reason will be displayed to describe this comment to others. Learn more.
| attribute of the resulting :class:`!Interpolation` object; if ``precision`` | |
| is (for example) ``2``, the resulting format specifier will be ``'.2f'``. | |
| attribute of the resulting :class:`!Interpolation` object. | |
| For example, if ``precision`` is ``2``, the resulting format specifier | |
| will be ``'.2f'``. |
Sorry, something went wrong.
There was an error while loading. Please reload this page.
| attribute of the resulting :class:`!Interpolation` object; if ``precision`` | ||
| is (for example) ``2``, the resulting format specifier will be ``'.2f'``. | ||
|
|
||
| - When the equal sign ``'='`` is provided in an interpolation expression, the |
There was a problem hiding this comment.
The reason will be displayed to describe this comment to others. Learn more.
| - When the equal sign ``'='`` is provided in an interpolation expression, the | |
| * When the equals sign ``'='`` is provided in an interpolation expression, the |
Sorry, something went wrong.
There was an error while loading. Please reload this page.
|
@davepeck @lysnikolaou this PR is from an organisation fork (@t-strings), so we can't apply suggestions or push commits. Please would you be able to do so? Hugo wants to get this PR in before starting RC1 later today. A |
Sorry, something went wrong.
There was an error while loading. Please reload this page.
There was a problem hiding this comment.
The reason will be displayed to describe this comment to others. Learn more.
Part 2 (briefer as we can't apply suggestions)
Sorry, something went wrong.
There was an error while loading. Please reload this page.
| .. seealso:: | ||
|
|
||
| * :ref:`Format strings <f-strings>` | ||
| * :ref:`T-string literal syntax <t-strings>` |
There was a problem hiding this comment.
The reason will be displayed to describe this comment to others. Learn more.
| * :ref:`T-string literal syntax <t-strings>` | |
| * :ref:`Template string literal (t-string) syntax <t-strings>` |
Sorry, something went wrong.
There was an error while loading. Please reload this page.
|
|
||
| * :ref:`Format strings <f-strings>` | ||
| * :ref:`T-string literal syntax <t-strings>` | ||
|
|
There was a problem hiding this comment.
The reason will be displayed to describe this comment to others. Learn more.
| * :pep:`750` | |
Sorry, something went wrong.
There was an error while loading. Please reload this page.
| Template strings are a formatting mechanism that allows for deep control over | ||
| how strings are processed. You can create templates using | ||
| :ref:`t-string literal syntax <t-strings>`, which is identical to | ||
| :ref:`f-string syntax <f-strings>` but uses a ``t`` instead of an ``f``. | ||
| While f-strings evaluate to ``str``, t-strings create a :class:`Template` | ||
| instance that gives you access to the static and interpolated (in curly braces) | ||
| parts of a string *before* they are combined. |
There was a problem hiding this comment.
The reason will be displayed to describe this comment to others. Learn more.
| Template strings are a formatting mechanism that allows for deep control over | |
| how strings are processed. You can create templates using | |
| :ref:`t-string literal syntax <t-strings>`, which is identical to | |
| :ref:`f-string syntax <f-strings>` but uses a ``t`` instead of an ``f``. | |
| While f-strings evaluate to ``str``, t-strings create a :class:`Template` | |
| instance that gives you access to the static and interpolated (in curly braces) | |
| parts of a string *before* they are combined. | |
| Template strings are a mechanism for custom string processing. | |
| They have the full flexibility of Python's :ref:`f-strings`, | |
| but return a :class:`Template` instance that gives access | |
| to the static and interpolated (in curly braces) parts of a string | |
| *before* they are combined. | |
| To write a t-string, use a ``'t'`` prefix instead of an ``'f'``, like so: | |
| .. code-block:: pycon | |
| >>> pi = 3.14 | |
| >>> t't-strings are new in Python {pi!s}!' | |
| Template( | |
| strings=('t-strings are new in Python ', '!'), | |
| interpolations=(Interpolation(3.14, 'pi', 's', ''),) | |
| ) |
Sorry, something went wrong.
There was an error while loading. Please reload this page.
| The :class:`!Template` class describes the contents of a template string. | ||
|
|
||
| :class:`!Template` instances are immutable: their attributes cannot be | ||
| reassigned. | ||
|
|
There was a problem hiding this comment.
The reason will be displayed to describe this comment to others. Learn more.
| The :class:`!Template` class describes the contents of a template string. | |
| :class:`!Template` instances are immutable: their attributes cannot be | |
| reassigned. | |
| The :class:`!Template` class describes the contents of a template string. | |
| It is immutable, meaning that attributes of a template cannot be reassigned. |
Sorry, something went wrong.
There was an error while loading. Please reload this page.
| Create a new :class:`!Template` object. | ||
|
|
||
| :param args: A mix of strings and :class:`Interpolation` instances in any order. | ||
| :type args: str | Interpolation | ||
|
|
||
| The most common way to create a :class:`!Template` instance is to use the | ||
| :ref:`t-string literal syntax <t-strings>`. This syntax is identical to that of | ||
| :ref:`f-strings <f-strings>` except that it uses a ``t`` instead of an ``f``: | ||
|
|
||
| >>> name = "World" | ||
| >>> template = t"Hello {name}!" | ||
| >>> type(template) | ||
| <class 'string.templatelib.Template'> |
There was a problem hiding this comment.
The reason will be displayed to describe this comment to others. Learn more.
I think this should be moved later; most users won't need to create Template objects by calling the class, but will need to know what the class is for and does. Perhaps you could separately document Template.__init__()?
Sorry, something went wrong.
There was an error while loading. Please reload this page.
| .. attribute:: values | ||
| :type: tuple[Any, ...] | ||
|
|
||
| A tuple of all interpolated values in the template. |
There was a problem hiding this comment.
The reason will be displayed to describe this comment to others. Learn more.
| A tuple of all interpolated values in the template. | |
| A tuple of the values of every interpolation in the template. |
Sorry, something went wrong.
There was an error while loading. Please reload this page.
| Iterate over the template, yielding each string and | ||
| :class:`Interpolation` in order. |
There was a problem hiding this comment.
The reason will be displayed to describe this comment to others. Learn more.
"in order" here I think could do with more exposition, or reference to the "proper" order of a Template
Sorry, something went wrong.
There was an error while loading. Please reload this page.
| Create a new :class:`!Interpolation` object. | ||
|
|
||
| :param value: The evaluated, in-scope result of the interpolation. | ||
| :type value: object | ||
|
|
||
| :param expression: The text of a valid Python expression, or an empty string. | ||
| :type expression: str | ||
|
|
||
| :param conversion: The optional :ref:`conversion <formatstrings>` to be used, one of r, s, and a. | ||
| :type conversion: ``Literal["a", "r", "s"] | None`` | ||
|
|
||
| :param format_spec: An optional, arbitrary string used as the :ref:`format specification <formatspec>` to present the value. | ||
| :type format_spec: str |
There was a problem hiding this comment.
The reason will be displayed to describe this comment to others. Learn more.
As with Template, I think direct construction should be moved to Interpolation.__init__()
Sorry, something went wrong.
There was an error while loading. Please reload this page.
| * ``'s'`` which calls :func:`str` on the value, | ||
| * ``'r'`` which calls :func:`repr`, and | ||
| * ``'a'`` which calls :func:`ascii`. |
There was a problem hiding this comment.
The reason will be displayed to describe this comment to others. Learn more.
Added the exclamation-mark forms for people doing a Ctrl-F search
| * ``'s'`` which calls :func:`str` on the value, | |
| * ``'r'`` which calls :func:`repr`, and | |
| * ``'a'`` which calls :func:`ascii`. | |
| * ``'s'`` which calls :func:`str` on the value (like ``!s``), | |
| * ``'r'`` which calls :func:`repr` (like ``!r``), and | |
| * ``'a'`` which calls :func:`ascii` (like ``!a``). |
Sorry, something went wrong.
There was an error while loading. Please reload this page.
| Interpolations support pattern matching, allowing you to match against | ||
| their attributes with the :ref:`match statement <match>`: | ||
|
|
||
| >>> from string.templatelib import Interpolation | ||
| >>> interpolation = Interpolation(3.0, "1 + 2", None, ".2f") | ||
| >>> match interpolation: | ||
| ... case Interpolation(value, expression, conversion, format_spec): | ||
| ... print(value, expression, conversion, format_spec) | ||
| ... | ||
| 3.0 1 + 2 None .2f |
There was a problem hiding this comment.
The reason will be displayed to describe this comment to others. Learn more.
This should be moved up into the main body description of Interpolation
Sorry, something went wrong.
There was an error while loading. Please reload this page.
|
Let's merge and add the updates in a followup. Thanks all! 🫖🧵📚🚀 |
Sorry, something went wrong.
There was an error while loading. Please reload this page.
(cherry picked from commit 22c8658) Co-authored-by: Dave Peck <[email protected]> Co-authored-by: Petr Viktorin <[email protected]> Co-authored-by: Hugo van Kemenade <[email protected]> Co-authored-by: Loïc Simon <[email protected]> Co-authored-by: pauleveritt <[email protected]>
|
GH-136974 is a backport of this pull request to the 3.14 branch. |
Sorry, something went wrong.
There was an error while loading. Please reload this page.
…136974) Co-authored-by: Dave Peck <[email protected]> Co-authored-by: Petr Viktorin <[email protected]> Co-authored-by: Hugo van Kemenade <[email protected]> Co-authored-by: Loïc Simon <[email protected]> Co-authored-by: pauleveritt <[email protected]> Co-authored-by: Lysandros Nikolaou <[email protected]>
|
See #137020 for the promised followup. A |
Sorry, something went wrong.
There was an error while loading. Please reload this page.
Co-authored-by: Petr Viktorin <[email protected]> Co-authored-by: Hugo van Kemenade <[email protected]> Co-authored-by: Loïc Simon <[email protected]> Co-authored-by: pauleveritt <[email protected]>
Co-authored-by: Petr Viktorin <[email protected]> Co-authored-by: Hugo van Kemenade <[email protected]> Co-authored-by: Loïc Simon <[email protected]> Co-authored-by: pauleveritt <[email protected]>
…H-135229) (python#136974) Co-authored-by: Dave Peck <[email protected]> Co-authored-by: Petr Viktorin <[email protected]> Co-authored-by: Hugo van Kemenade <[email protected]> Co-authored-by: Loïc Simon <[email protected]> Co-authored-by: pauleveritt <[email protected]> Co-authored-by: Lysandros Nikolaou <[email protected]>
There was an error while loading. Please reload this page.
Successfully merging this pull request may close these issues.
There was an error while loading. Please reload this page.