From 4ffca0ba57726b7499d09e1143e1affeac516ed9 Mon Sep 17 00:00:00 2001 From: Shivansh-007 Date: Fri, 14 Jan 2022 11:30:40 +0530 Subject: [PATCH 1/6] Use parenthesis with equality check in walrus/assigment statements Closes #449 --- src/black/linegen.py | 21 ++++++ tests/data/paren_eq_check_in_assigments.py | 83 ++++++++++++++++++++++ 2 files changed, 104 insertions(+) create mode 100644 tests/data/paren_eq_check_in_assigments.py diff --git a/src/black/linegen.py b/src/black/linegen.py index 6008c773f94..3152360d551 100644 --- a/src/black/linegen.py +++ b/src/black/linegen.py @@ -99,6 +99,27 @@ def visit_default(self, node: LN) -> Iterator[Line]: self.current_line.append(node) yield from super().visit_default(node) + def visit_comparison(self, node: Node) -> Iterator[Line]: + parent: Optional[Node] = node.parent + grandparent: Optional[Node] = parent.parent if parent else None + if ( + parent is not None + and Leaf(token.EQEQUAL, "==") in node.children + and ( + parent.type == syms.namedexpr_test + or ( + grandparent is not None + and grandparent.type in (syms.expr_stmt, syms.annassign) + ) + ) + ): + lpar = Leaf(token.LPAR, "(") + rpar = Leaf(token.RPAR, ")") + node.insert_child(0, lpar) + node.insert_child(len(node.children), 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. diff --git a/tests/data/paren_eq_check_in_assigments.py b/tests/data/paren_eq_check_in_assigments.py new file mode 100644 index 00000000000..2cbb64ceafb --- /dev/null +++ b/tests/data/paren_eq_check_in_assigments.py @@ -0,0 +1,83 @@ +match_count += new_value == old_value + +if on_windows := os.name == "nt": + ... + +on_windows: bool = (os.name == "nt") + +implementation_version = ( + platform.python_version() if platform.python_implementation() == "CPython" else "Unknown" +) + +is_mac = platform.system() == 'Darwin' + +s = y == 2 + y == 4 + +name1 = name2 = name3 + +name1 == name2 == name3 + +check_sockets(on_windows=os.name == "nt") + +if a := b == c: + pass + +a = [y := f(x) == True, y ** 2, y ** 3] + +a = lambda line: (m := re.match(pattern, line) == True) + +a = b in c and b == d + +a = b == c == d + +a = b == c in d + +a = b >= c == True + +a = b in c + +a = b > c + +# output + +match_count += (new_value == old_value) + +if on_windows := (os.name == "nt"): + ... + +on_windows: bool = (os.name == "nt") + +implementation_version = ( + platform.python_version() + if platform.python_implementation() == "CPython" + else "Unknown" +) + +is_mac = (platform.system() == "Darwin") + +s = (y == 2 + y == 4) + +name1 = name2 = name3 + +name1 == name2 == name3 + +check_sockets(on_windows=os.name == "nt") + +if a := (b == c): + pass + +a = [y := (f(x) == True), y ** 2, y ** 3] + +a = lambda line: (m := (re.match(pattern, line) == True)) + +a = b in c and b == d + +a = (b == c == d) + +a = (b == c in d) + +a = (b >= c == True) + +a = b in c + +a = b > c From a2ea516fef7d499fc3dfb50fa86f1717ccc015ff Mon Sep 17 00:00:00 2001 From: Shivansh-007 Date: Fri, 14 Jan 2022 11:31:06 +0530 Subject: [PATCH 2/6] Format black source with new formatting change --- src/black/__init__.py | 2 +- src/black/parsing.py | 2 +- src/black/trans.py | 2 +- src/black_primer/lib.py | 6 +++--- src/blackd/middlewares.py | 2 +- tests/test_format.py | 1 + 6 files changed, 8 insertions(+), 7 deletions(-) diff --git a/src/black/__init__.py b/src/black/__init__.py index 405a01082e7..daf5d31d689 100644 --- a/src/black/__init__.py +++ b/src/black/__init__.py @@ -1062,7 +1062,7 @@ def format_ipynb_string(src_contents: str, *, fast: bool, mode: Mode) -> FileCon Operate cell-by-cell, only on code cells, only for Python notebooks. If the ``.ipynb`` originally had a trailing newline, it'll be preserved. """ - trailing_newline = src_contents[-1] == "\n" + trailing_newline = (src_contents[-1] == "\n") modified = False nb = json.loads(src_contents) validate_metadata(nb) diff --git a/src/black/parsing.py b/src/black/parsing.py index 6b63368871c..ca4ab642ead 100644 --- a/src/black/parsing.py +++ b/src/black/parsing.py @@ -24,7 +24,7 @@ ast3: Any -_IS_PYPY = platform.python_implementation() == "PyPy" +_IS_PYPY = (platform.python_implementation() == "PyPy") try: from typed_ast import ast3 diff --git a/src/black/trans.py b/src/black/trans.py index cb41c1be487..d805f7742e3 100644 --- a/src/black/trans.py +++ b/src/black/trans.py @@ -1397,7 +1397,7 @@ def passes_all_checks(i: Index) -> bool: True iff ALL of the conditions listed in the 'Transformations' section of this classes' docstring would be be met by returning @i. """ - is_space = string[i] == " " + is_space = (string[i] == " ") is_not_escaped = True j = i - 1 diff --git a/src/black_primer/lib.py b/src/black_primer/lib.py index 13724f431ce..99181c75295 100644 --- a/src/black_primer/lib.py +++ b/src/black_primer/lib.py @@ -29,7 +29,7 @@ TEN_MINUTES_SECONDS = 600 -WINDOWS = system() == "Windows" +WINDOWS = (system() == "Windows") BLACK_BINARY = "black.exe" if WINDOWS else "black" GIT_BINARY = "git.exe" if WINDOWS else "git" LOG = logging.getLogger(__name__) @@ -158,7 +158,7 @@ async def black_run( ) return - stdin_test = project_name.upper() == "STDIN" + stdin_test = (project_name.upper() == "STDIN") cmd = [str(which(BLACK_BINARY))] if "cli_arguments" in project_config and project_config["cli_arguments"]: cmd.extend(_flatten_cli_args(project_config["cli_arguments"])) @@ -348,7 +348,7 @@ async def project_runner( continue repo_path: Optional[Path] = Path(__file__) - stdin_project = project_name.upper() == "STDIN" + stdin_project = (project_name.upper() == "STDIN") if not stdin_project: repo_path = await git_checkout_or_rebase(work_path, project_config, rebase) if not repo_path: diff --git a/src/blackd/middlewares.py b/src/blackd/middlewares.py index 97994ecc1df..c995f225b3d 100644 --- a/src/blackd/middlewares.py +++ b/src/blackd/middlewares.py @@ -10,7 +10,7 @@ def cors(allow_headers: Iterable[str]) -> Middleware: @middleware async def impl(request: Request, handler: Handler) -> StreamResponse: - is_options = request.method == "OPTIONS" + is_options = (request.method == "OPTIONS") is_preflight = is_options and "Access-Control-Request-Method" in request.headers if is_preflight: resp = StreamResponse() diff --git a/tests/test_format.py b/tests/test_format.py index 00cd07f36f7..9277ff2cde2 100644 --- a/tests/test_format.py +++ b/tests/test_format.py @@ -48,6 +48,7 @@ "function2", "function_trailing_comma", "import_spacing", + "parenthesized_context_managers", "remove_parens", "slices", "string_prefixes", From 32e554476f6228a1d3a63c8c523870befcb2db62 Mon Sep 17 00:00:00 2001 From: Shivansh-007 Date: Fri, 14 Jan 2022 14:21:44 +0530 Subject: [PATCH 3/6] Add changelog --- CHANGES.md | 1 + 1 file changed, 1 insertion(+) diff --git a/CHANGES.md b/CHANGES.md index 4b9ceae81dc..652c87dc3d3 100644 --- a/CHANGES.md +++ b/CHANGES.md @@ -30,6 +30,7 @@ - Fix handling of standalone `match()` or `case()` when there is a trailing newline or a comment inside of the parentheses. (#2760) - Black now normalizes string prefix order (#2297) +- Use parentheses with equality check in walrus/assigment statements (#2770) ### Packaging From 81a0040431a6401d5c9c42464c98432c10ba0008 Mon Sep 17 00:00:00 2001 From: Shivansh-007 Date: Sat, 12 Mar 2022 06:21:16 +0530 Subject: [PATCH 4/6] Run formatting test on black source with preview mode --- tests/test_black.py | 1 + tests/test_format.py | 5 +++-- tests/util.py | 1 + 3 files changed, 5 insertions(+), 2 deletions(-) diff --git a/tests/test_black.py b/tests/test_black.py index b1bf1772550..50f1e112e75 100644 --- a/tests/test_black.py +++ b/tests/test_black.py @@ -162,6 +162,7 @@ def test_piping(self) -> None: black.main, [ "-", + "--preview", "--fast", f"--line-length={black.DEFAULT_LINE_LENGTH}", f"--config={EMPTY_CONFIG}", diff --git a/tests/test_format.py b/tests/test_format.py index db177b40f8d..13682088ca9 100644 --- a/tests/test_format.py +++ b/tests/test_format.py @@ -7,6 +7,7 @@ import black from tests.util import ( DEFAULT_MODE, + PREVIEW_MODE, PY36_VERSIONS, THIS_DIR, assert_format, @@ -145,13 +146,13 @@ def test_simple_format(filename: str) -> None: @pytest.mark.parametrize("filename", PREVIEW_CASES) def test_preview_format(filename: str) -> None: - check_file(filename, black.Mode(preview=True)) + check_file(filename, PREVIEW_MODE) @pytest.mark.parametrize("filename", SOURCES) def test_source_is_formatted(filename: str) -> None: path = THIS_DIR.parent / filename - check_file(str(path), DEFAULT_MODE, data=False) + check_file(str(path), PREVIEW_MODE, data=False) # =============== # diff --git a/tests/util.py b/tests/util.py index 8755111f7c5..0bb8b2a9c7d 100644 --- a/tests/util.py +++ b/tests/util.py @@ -25,6 +25,7 @@ } DEFAULT_MODE = black.Mode() +PREVIEW_MODE = black.Mode(preview=True) ff = partial(black.format_file_in_place, mode=DEFAULT_MODE, fast=True) fs = partial(black.format_str, mode=DEFAULT_MODE) From d09396e927765d1c5a5e52c7e0183cf0f02a664d Mon Sep 17 00:00:00 2001 From: Shivansh-007 Date: Sat, 12 Mar 2022 06:29:56 +0530 Subject: [PATCH 5/6] Fix tests for feature --- tests/data/paren_eq_check_in_assigments.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/data/paren_eq_check_in_assigments.py b/tests/data/paren_eq_check_in_assigments.py index 2cbb64ceafb..22b310e7c73 100644 --- a/tests/data/paren_eq_check_in_assigments.py +++ b/tests/data/paren_eq_check_in_assigments.py @@ -66,7 +66,7 @@ if a := (b == c): pass -a = [y := (f(x) == True), y ** 2, y ** 3] +a = [y := (f(x) == True), y**2, y**3] a = lambda line: (m := (re.match(pattern, line) == True)) From ce9e47d72712781f55025f32a514317ad31adb9d Mon Sep 17 00:00:00 2001 From: Shivansh-007 Date: Mon, 14 Mar 2022 08:30:25 +0530 Subject: [PATCH 6/6] Remove walrus operator expressions --- tests/data/paren_eq_check_in_assigments.py | 20 -------------------- 1 file changed, 20 deletions(-) diff --git a/tests/data/paren_eq_check_in_assigments.py b/tests/data/paren_eq_check_in_assigments.py index 22b310e7c73..d0500f9dc16 100644 --- a/tests/data/paren_eq_check_in_assigments.py +++ b/tests/data/paren_eq_check_in_assigments.py @@ -1,8 +1,5 @@ match_count += new_value == old_value -if on_windows := os.name == "nt": - ... - on_windows: bool = (os.name == "nt") implementation_version = ( @@ -19,13 +16,6 @@ check_sockets(on_windows=os.name == "nt") -if a := b == c: - pass - -a = [y := f(x) == True, y ** 2, y ** 3] - -a = lambda line: (m := re.match(pattern, line) == True) - a = b in c and b == d a = b == c == d @@ -42,9 +32,6 @@ match_count += (new_value == old_value) -if on_windows := (os.name == "nt"): - ... - on_windows: bool = (os.name == "nt") implementation_version = ( @@ -63,13 +50,6 @@ check_sockets(on_windows=os.name == "nt") -if a := (b == c): - pass - -a = [y := (f(x) == True), y**2, y**3] - -a = lambda line: (m := (re.match(pattern, line) == True)) - a = b in c and b == d a = (b == c == d)