]> git.madduck.net Git - etc/vim.git/commitdiff

madduck's git repository

Every one of the projects in this repository is available at the canonical URL git://git.madduck.net/madduck/pub/<projectpath> — see each project's metadata for the exact URL.

All patches and comments are welcome. Please squash your changes to logical commits before using git-format-patch and git-send-email to patches@git.madduck.net. If you'd read over the Git project's submission guidelines and adhered to them, I'd be especially grateful.

SSH access, as well as push access can be individually arranged.

If you use my repositories frequently, consider adding the following snippet to ~/.gitconfig and using the third clone URL listed for each project:

[url "git://git.madduck.net/madduck/"]
  insteadOf = madduck:

Parenthesize conditional expressions (#2278)
authorJordan Ephron <j@jephron.com>
Thu, 29 Dec 2022 23:13:15 +0000 (18:13 -0500)
committerGitHub <noreply@github.com>
Thu, 29 Dec 2022 23:13:15 +0000 (15:13 -0800)
Co-authored-by: Jordan Ephron <JEphron@users.noreply.github.com>
Co-authored-by: Richard Si <63936253+ichard26@users.noreply.github.com>
Co-authored-by: Jelle Zijlstra <jelle.zijlstra@gmail.com>
CHANGES.md
src/black/__init__.py
src/black/linegen.py
src/black/mode.py
tests/data/conditional_expression.py [new file with mode: 0644]

index 587ca8a2a0dd532805a9005c2aed28fec4f5ff2b..2da0fb4720c1bc12cc2a01c75f117f700a47aa9d 100644 (file)
@@ -16,6 +16,7 @@
 
 <!-- Changes that affect Black's preview style -->
 
+- Add parentheses around `if`-`else` expressions (#2278)
 - Improve the performance on large expressions that contain many strings (#3467)
 - Fix a crash in preview style with assert + parenthesized string (#3415)
 - Fix crashes in preview style with walrus operators used in function return annotations
index f00749aaed81146dbadc7778cf49bad23af6e3c5..9f44722bfaee89373932ad062dedf52ac145eacc 100644 (file)
@@ -478,16 +478,20 @@ def main(  # noqa: C901
             )
 
             normalized = [
-                (source, source)
-                if source == "-"
-                else (normalize_path_maybe_ignore(Path(source), root), source)
+                (
+                    (source, source)
+                    if source == "-"
+                    else (normalize_path_maybe_ignore(Path(source), root), source)
+                )
                 for source in src
             ]
             srcs_string = ", ".join(
                 [
-                    f'"{_norm}"'
-                    if _norm
-                    else f'\033[31m"{source} (skipping - invalid)"\033[34m'
+                    (
+                        f'"{_norm}"'
+                        if _norm
+                        else f'\033[31m"{source} (skipping - invalid)"\033[34m'
+                    )
                     for _norm, source in normalized
                 ]
             )
index 2e75bc945066d148f1cc03f673107cc0918e6f22..4da75b28235c96b2d96204d532d7cd6552a0e9d4 100644 (file)
@@ -140,6 +140,22 @@ class LineGenerator(Visitor[Line]):
                 self.current_line.append(node)
         yield from super().visit_default(node)
 
+    def visit_test(self, node: Node) -> Iterator[Line]:
+        """Visit an `x if y else z` test"""
+
+        if Preview.parenthesize_conditional_expressions in self.mode:
+            already_parenthesized = (
+                node.prev_sibling and node.prev_sibling.type == token.LPAR
+            )
+
+            if not already_parenthesized:
+                lpar = Leaf(token.LPAR, "")
+                rpar = Leaf(token.RPAR, "")
+                node.insert_child(0, lpar)
+                node.append_child(rpar)
+
+        yield from self.visit_default(node)
+
     def visit_INDENT(self, node: Leaf) -> Iterator[Line]:
         """Increase indentation level, maybe yield a line."""
         # In blib2to3 INDENT never holds comments.
index a104d1b9862da1e194f4ba096e9872e5726dea68..775805ae9600a30c0001ce1f67dff27a4b2ff122 100644 (file)
@@ -161,6 +161,7 @@ class Preview(Enum):
     # NOTE: string_processing requires wrap_long_dict_values_in_parens
     # for https://github.com/psf/black/issues/3117 to be fixed.
     string_processing = auto()
+    parenthesize_conditional_expressions = auto()
     skip_magic_trailing_comma_in_subscript = auto()
     wrap_long_dict_values_in_parens = auto()
 
diff --git a/tests/data/conditional_expression.py b/tests/data/conditional_expression.py
new file mode 100644 (file)
index 0000000..620a12d
--- /dev/null
@@ -0,0 +1,160 @@
+long_kwargs_single_line = my_function(
+    foo="test, this is a sample value",
+    bar=some_long_value_name_foo_bar_baz if some_boolean_variable else some_fallback_value_foo_bar_baz,
+    baz="hello, this is a another value",
+)
+
+multiline_kwargs_indented = my_function(
+    foo="test, this is a sample value",
+    bar=some_long_value_name_foo_bar_baz
+    if some_boolean_variable
+    else some_fallback_value_foo_bar_baz,
+    baz="hello, this is a another value",
+)
+
+imploding_kwargs = my_function(
+    foo="test, this is a sample value",
+    bar=a
+    if foo
+    else b,
+    baz="hello, this is a another value",
+)
+
+imploding_line = (
+    1
+    if 1 + 1 == 2
+    else 0
+)
+
+exploding_line = "hello this is a slightly long string" if some_long_value_name_foo_bar_baz else "this one is a little shorter"
+
+positional_argument_test(some_long_value_name_foo_bar_baz if some_boolean_variable else some_fallback_value_foo_bar_baz)
+
+def weird_default_argument(x=some_long_value_name_foo_bar_baz
+        if SOME_CONSTANT
+        else some_fallback_value_foo_bar_baz):
+    pass
+
+nested = "hello this is a slightly long string" if (some_long_value_name_foo_bar_baz if
+                                                    nesting_test_expressions else some_fallback_value_foo_bar_baz) \
+    else "this one is a little shorter"
+
+generator_expression = (
+    some_long_value_name_foo_bar_baz if some_boolean_variable else some_fallback_value_foo_bar_baz for some_boolean_variable in some_iterable
+)
+
+
+def limit_offset_sql(self, low_mark, high_mark):
+    """Return LIMIT/OFFSET SQL clause."""
+    limit, offset = self._get_limit_offset_params(low_mark, high_mark)
+    return " ".join(
+        sql
+        for sql in (
+            "LIMIT %d" % limit if limit else None,
+            ("OFFSET %d" % offset) if offset else None,
+        )
+        if sql
+    )
+
+
+def something():
+    clone._iterable_class = (
+        NamedValuesListIterable
+        if named
+        else FlatValuesListIterable
+        if flat
+        else ValuesListIterable
+    )
+
+# output
+
+long_kwargs_single_line = my_function(
+    foo="test, this is a sample value",
+    bar=(
+        some_long_value_name_foo_bar_baz
+        if some_boolean_variable
+        else some_fallback_value_foo_bar_baz
+    ),
+    baz="hello, this is a another value",
+)
+
+multiline_kwargs_indented = my_function(
+    foo="test, this is a sample value",
+    bar=(
+        some_long_value_name_foo_bar_baz
+        if some_boolean_variable
+        else some_fallback_value_foo_bar_baz
+    ),
+    baz="hello, this is a another value",
+)
+
+imploding_kwargs = my_function(
+    foo="test, this is a sample value",
+    bar=a if foo else b,
+    baz="hello, this is a another value",
+)
+
+imploding_line = 1 if 1 + 1 == 2 else 0
+
+exploding_line = (
+    "hello this is a slightly long string"
+    if some_long_value_name_foo_bar_baz
+    else "this one is a little shorter"
+)
+
+positional_argument_test(
+    some_long_value_name_foo_bar_baz
+    if some_boolean_variable
+    else some_fallback_value_foo_bar_baz
+)
+
+
+def weird_default_argument(
+    x=(
+        some_long_value_name_foo_bar_baz
+        if SOME_CONSTANT
+        else some_fallback_value_foo_bar_baz
+    ),
+):
+    pass
+
+
+nested = (
+    "hello this is a slightly long string"
+    if (
+        some_long_value_name_foo_bar_baz
+        if nesting_test_expressions
+        else some_fallback_value_foo_bar_baz
+    )
+    else "this one is a little shorter"
+)
+
+generator_expression = (
+    (
+        some_long_value_name_foo_bar_baz
+        if some_boolean_variable
+        else some_fallback_value_foo_bar_baz
+    )
+    for some_boolean_variable in some_iterable
+)
+
+
+def limit_offset_sql(self, low_mark, high_mark):
+    """Return LIMIT/OFFSET SQL clause."""
+    limit, offset = self._get_limit_offset_params(low_mark, high_mark)
+    return " ".join(
+        sql
+        for sql in (
+            "LIMIT %d" % limit if limit else None,
+            ("OFFSET %d" % offset) if offset else None,
+        )
+        if sql
+    )
+
+
+def something():
+    clone._iterable_class = (
+        NamedValuesListIterable
+        if named
+        else FlatValuesListIterable if flat else ValuesListIterable
+    )