string.templatelib --- 模板字符串支持

本模块为 PEP 750 中定义的模板字符串(t-string)提供支持。模板字符串使用 t 前缀创建,在字面字符串部分与插值值被组合之前即可对两者进行访问。

可用性: 模板字符串在基于 STM32 的 OpenMV Cam 上 受支持。它们仅在基于 Alif 和 i.MX RT 的 OpenMV Cam 上可用。

class string.templatelib.Template(*args)

表示一个模板字符串。Template 对象通常由 t-string 语法(t"...")创建,但也可以使用构造函数直接构造。

strings

出现在各插值之间的字符串字面量组成的元组。

interpolations

由表示各插值表达式的 Interpolation 对象组成的元组。

values

一个只读属性,返回一个元组,其中包含模板中每个插值的 value 属性。

__iter__() Iterator

遍历模板内容,按字符串部分和 Interpolation 对象在模板中出现的顺序逐个产出。空字符串会被省略。

__add__(other: Template) Template

拼接两个模板。返回一个新的 Template,它合并了两个模板中的字符串和插值。

抛出:

TypeError -- 若 other 不是 Template

禁止将模板与 str 拼接,以避免对该字符串应被视为字面量还是插值产生歧义:

t1 = t"Hello "
t2 = t"World"
result = t1 + t2  # Valid

# TypeError: cannot concatenate str to Template
result = t1 + "World"
class string.templatelib.Interpolation(value: Any, expression: str = '', conversion: str | None = None, format_spec: str = '')

表示模板字符串中的一个插值表达式。所有参数都可以作为关键字参数传递。

value

插值表达式求值后的值。

expression

表达式在模板字符串中所呈现样子的字符串表示。

conversion

转换说明符('s''r'),若存在则给出,否则为 None。请注意 MicroPython 不支持 'a' 转换。

format_spec

格式说明字符串,若存在则给出,否则为空字符串。

模板字符串语法

模板字符串使用与 f-string 相同的语法,但带有 t 前缀:

name = "World"
template = t"Hello {name}!"

# Access template components
print(template.strings)        # ('Hello ', '!')
print(template.values)         # ('World',)
print(template.interpolations[0].expression)  # 'name'

转换说明符

模板字符串将转换说明符存储为元数据。与 f-string 不同,转换不会自动应用:

value = "test"
t = t"{value!r}"
# t.interpolations[0].value == "test" (not repr(value))
# t.interpolations[0].conversion == "r"

处理代码必须在需要时显式地应用转换。

格式说明

格式说明作为元数据存储在 Interpolation 对象中。与 f-string 不同,格式化不会自动应用:

pi = 3.14159
t = t"{pi:.2f}"
# t.interpolations[0].value == 3.14159 (not formatted)
# t.interpolations[0].format_spec == ".2f"

根据 PEP 750,处理代码并非必须使用格式说明,但当格式说明存在时,应予以遵循,并尽可能与 f-string 的行为保持一致。

调试格式

支持调试格式 {expr=}:

x = 42
t = t"{x=}"
# t.strings == ("x=", "")
# t.interpolations[0].expression == "x"
# t.interpolations[0].conversion == "r"

重要

根据 PEP 750,与 f-string 不同,模板字符串不会自动应用转换或格式说明。这是有意为之的设计,目的是让处理代码能够控制这些内容的处理方式。处理代码必须显式地处理这些属性。

MicroPython 不提供 format() 内置函数。请改用诸如 str.format() 之类的字符串格式化方法。

用法示例

不支持格式时的基本处理:

def simple_process(template):
    """Simple template processing"""
    parts = []
    for item in template:
        if isinstance(item, str):
            parts.append(item)
        else:
            parts.append(str(item.value))
    return "".join(parts)

支持格式时的模板处理:

from string.templatelib import Template, Interpolation

def convert(value, conversion):
    """Apply conversion specifier to value"""
    if conversion == "r":
        return repr(value)
    elif conversion == "s":
        return str(value)
    return value

def process_template(template):
    """Process template with conversion and format support"""
    result = []
    for part in template:
        if isinstance(part, str):
            result.append(part)
        else:  # Interpolation
            value = convert(part.value, part.conversion)
            if part.format_spec:
                # Apply format specification using str.format
                value = ("{:" + part.format_spec + "}").format(value)
            else:
                value = str(value)
            result.append(value)
    return "".join(result)

pi = 3.14159
name = "Alice"
t = t"{name!r}: {pi:.2f}"
print(process_template(t))
# Output: "'Alice': 3.14"

# Other format specifications work too
value = 42
print(process_template(t"{value:>10}"))  # "        42"
print(process_template(t"{value:04d}"))  # "0042"

HTML 转义示例:

def html_escape(value):
    """Escape HTML special characters"""
    if not isinstance(value, str):
        value = str(value)
    return value.replace("&", "&amp;").replace("<", "&lt;").replace(">", "&gt;")

def safe_html(template):
    """Convert template to HTML-safe string"""
    result = []
    for part in template:
        if isinstance(part, str):
            result.append(part)
        else:
            result.append(html_escape(part.value))
    return "".join(result)

user_input = "<script>alert('xss')</script>"
t = t"User said: {user_input}"
print(safe_html(t))
# Output: "User said: &lt;script&gt;alert('xss')&lt;/script&gt;"

另请参阅