Tokenize a str.format() format string. The core function parse_format_value() is shared with mypy. With these specifiers, we then parse the literal substrings of the original format string and convert `ConversionSpecifier` to `FormatOp`. Return: A list of string literal
(format_str: str)
| 95 | |
| 96 | |
| 97 | def tokenizer_format_call(format_str: str) -> tuple[list[str], list[FormatOp]] | None: |
| 98 | """Tokenize a str.format() format string. |
| 99 | |
| 100 | The core function parse_format_value() is shared with mypy. |
| 101 | With these specifiers, we then parse the literal substrings |
| 102 | of the original format string and convert `ConversionSpecifier` |
| 103 | to `FormatOp`. |
| 104 | |
| 105 | Return: |
| 106 | A list of string literals and a list of FormatOps. The literals |
| 107 | are interleaved with FormatOps and the length of returned literals |
| 108 | should be exactly one more than FormatOps. |
| 109 | Return None if it cannot parse the string. |
| 110 | """ |
| 111 | # Creates an empty MessageBuilder here. |
| 112 | # It wouldn't be used since the code has passed the type-checking. |
| 113 | specifiers = parse_format_value( |
| 114 | format_str, EMPTY_CONTEXT, MessageBuilder(Errors(Options()), {}) |
| 115 | ) |
| 116 | if specifiers is None: |
| 117 | return None |
| 118 | format_ops = generate_format_ops(specifiers) |
| 119 | if format_ops is None: |
| 120 | return None |
| 121 | |
| 122 | literals: list[str] = [] |
| 123 | last_end = 0 |
| 124 | for spec in specifiers: |
| 125 | # Skip { and } |
| 126 | literals.append(format_str[last_end : spec.start_pos - 1]) |
| 127 | last_end = spec.start_pos + len(spec.whole_seq) + 1 |
| 128 | literals.append(format_str[last_end:]) |
| 129 | # Deal with escaped {{ |
| 130 | literals = [x.replace("{{", "{").replace("}}", "}") for x in literals] |
| 131 | |
| 132 | return literals, format_ops |
| 133 | |
| 134 | |
| 135 | def convert_format_expr_to_str( |
no test coverage detected
searching dependent graphs…