(values: Vec<TemplateStrPart>)
| 104 | } |
| 105 | |
| 106 | fn normalize_template_str_parts(values: Vec<TemplateStrPart>) -> Vec<TemplateStrPart> { |
| 107 | let mut output = Vec::with_capacity(values.len()); |
| 108 | let mut pending: Option<(String, StringLiteralPrefix, TextRange)> = None; |
| 109 | |
| 110 | for part in values { |
| 111 | match part { |
| 112 | TemplateStrPart::Constant(constant) => { |
| 113 | let ConstantLiteral::Str { value, prefix } = constant.value else { |
| 114 | push_template_str_literal(&mut output, &mut pending); |
| 115 | output.push(TemplateStrPart::Constant(constant)); |
| 116 | continue; |
| 117 | }; |
| 118 | let value: String = value.into(); |
| 119 | if let Some((pending_value, _, _)) = pending.as_mut() { |
| 120 | pending_value.push_str(&value); |
| 121 | } else { |
| 122 | pending = Some((value, prefix, constant.range)); |
| 123 | } |
| 124 | } |
| 125 | TemplateStrPart::Interpolation(value) => { |
| 126 | push_template_str_literal(&mut output, &mut pending); |
| 127 | output.push(TemplateStrPart::Interpolation(value)); |
| 128 | } |
| 129 | } |
| 130 | } |
| 131 | |
| 132 | push_template_str_literal(&mut output, &mut pending); |
| 133 | output |
| 134 | } |
| 135 | |
| 136 | fn warn_invalid_escape_sequences_in_format_spec( |
| 137 | vm: &VirtualMachine, |
no test coverage detected