diff --git a/lib/astunparse/unparser.py b/lib/astunparse/unparser.py index 71a9456..87cc866 100644 --- a/lib/astunparse/unparser.py +++ b/lib/astunparse/unparser.py @@ -444,8 +444,7 @@ def _Str(self, tree): format_conversions = {97: 'a', 114: 'r', 115: 's'} - def _FormattedValue(self, t): - # FormattedValue(expr value, int? conversion, expr? format_spec) + def _generic_FormattedValue(self, t): self.write("{") self.dispatch(t.value) if t.conversion is not None and t.conversion != -1: @@ -455,17 +454,33 @@ def _FormattedValue(self, t): if t.format_spec is not None: self.write(":") if isinstance(t.format_spec, ast.Str): + # It's ast.Str in 3.6.0 self.write(t.format_spec.s) + elif isinstance(t.format_spec, ast.JoinedStr): + # It's ast.JoinedStr in 3.6.1+ + for value in t.format_spec.values: + if isinstance(value, ast.Str): + self.write(value.s) + else: + self.dispatch(value) else: self.dispatch(t.format_spec) self.write("}") + def _FormattedValue(self, t): + # FormattedValue(expr value, int? conversion, expr? format_spec) + self.write("f'''") + self._generic_FormattedValue(t) + self.write("'''") + def _JoinedStr(self, t): # JoinedStr(expr* values) self.write("f'''") for value in t.values: if isinstance(value, ast.Str): self.write(value.s) + elif isinstance(value, ast.FormattedValue): + self._generic_FormattedValue(value) else: self.dispatch(value) self.write("'''") diff --git a/tests/common.py b/tests/common.py index f930308..baeba34 100644 --- a/tests/common.py +++ b/tests/common.py @@ -288,6 +288,13 @@ def test_raise_from(self): def test_bytes(self): self.check_roundtrip("b'123'") + @unittest.skipIf(sys.version_info < (3, 6), "Not supported < 3.6") + def test_formatted_value(self): + self.check_roundtrip('f"{value}"') + self.check_roundtrip('f"{value!s}"') + self.check_roundtrip('f"{value:4}"') + self.check_roundtrip('f"{value!s:4}"') + @unittest.skipIf(sys.version_info < (3, 6), "Not supported < 3.6") def test_joined_str(self): self.check_roundtrip('f"{key}={value!s}"')