parent
dafa12f10b
commit
dd4477b701
30
README.md
30
README.md
@ -131,13 +131,13 @@ brackets and put that in a separate indented line.
|
|||||||
```py3
|
```py3
|
||||||
# in:
|
# in:
|
||||||
|
|
||||||
l = [[n for n in list_bosses()], [n for n in list_employees()]]
|
TracebackException.from_exception(exc, limit, lookup_lines, capture_locals)
|
||||||
|
|
||||||
# out:
|
# out:
|
||||||
|
|
||||||
l = [
|
TracebackException.from_exception(
|
||||||
[n for n in list_bosses()], [n for n in list_employees()]
|
exc, limit, lookup_lines, capture_locals
|
||||||
]
|
)
|
||||||
```
|
```
|
||||||
|
|
||||||
If that still doesn't fit the bill, it will decompose the internal
|
If that still doesn't fit the bill, it will decompose the internal
|
||||||
@ -176,13 +176,13 @@ between two distinct sections of the code that otherwise share the same
|
|||||||
indentation level (like the arguments list and the docstring in the
|
indentation level (like the arguments list and the docstring in the
|
||||||
example above).
|
example above).
|
||||||
|
|
||||||
If a line of "from" imports cannot fit in the allotted length, it's always split
|
If a data structure literal (tuple, list, set, dict) or a line of "from"
|
||||||
into one per line. Imports tend to change often and this minimizes diffs, as well
|
imports cannot fit in the allotted length, it's always split into one
|
||||||
as enables readers of code to easily find which commit introduced a particular
|
per line. This minimizes diffs as well as enables readers of code to
|
||||||
import. This exception also makes *Black* compatible with
|
find which commit introduced a particular entry. This also makes
|
||||||
[isort](https://pypi.org/p/isort/). Use `multi_line_output=3`,
|
*Black* compatible with [isort](https://pypi.org/p/isort/). Use
|
||||||
`include_trailing_comma=True`, `force_grid_wrap=0`, and `line_length=88` in your
|
`multi_line_output=3`, `include_trailing_comma=True`,
|
||||||
isort config.
|
`force_grid_wrap=0`, and `line_length=88` in your isort config.
|
||||||
|
|
||||||
|
|
||||||
### Line length
|
### Line length
|
||||||
@ -630,7 +630,13 @@ More details can be found in [CONTRIBUTING](CONTRIBUTING.md).
|
|||||||
|
|
||||||
### 18.5a0 (unreleased)
|
### 18.5a0 (unreleased)
|
||||||
|
|
||||||
* call chains are now formatted according to the [fluent interfaces](https://en.wikipedia.org/wiki/Fluent_interface) style (#67)
|
* call chains are now formatted according to the
|
||||||
|
[fluent interfaces](https://en.wikipedia.org/wiki/Fluent_interface)
|
||||||
|
style (#67)
|
||||||
|
|
||||||
|
* data structure literals (tuples, lists, dictionaries, and sets) are
|
||||||
|
now also always exploded like imports when they don't fit in a single
|
||||||
|
line (#152)
|
||||||
|
|
||||||
* slices are now formatted according to PEP 8 (#178)
|
* slices are now formatted according to PEP 8 (#178)
|
||||||
|
|
||||||
|
61
black.py
61
black.py
@ -776,6 +776,7 @@ class Line:
|
|||||||
comments: List[Tuple[Index, Leaf]] = Factory(list)
|
comments: List[Tuple[Index, Leaf]] = Factory(list)
|
||||||
bracket_tracker: BracketTracker = Factory(BracketTracker)
|
bracket_tracker: BracketTracker = Factory(BracketTracker)
|
||||||
inside_brackets: bool = False
|
inside_brackets: bool = False
|
||||||
|
should_explode: bool = False
|
||||||
|
|
||||||
def append(self, leaf: Leaf, preformatted: bool = False) -> None:
|
def append(self, leaf: Leaf, preformatted: bool = False) -> None:
|
||||||
"""Add a new `leaf` to the end of the line.
|
"""Add a new `leaf` to the end of the line.
|
||||||
@ -1473,7 +1474,9 @@ def whitespace(leaf: Leaf, *, complex_subscript: bool) -> str: # noqa C901
|
|||||||
|
|
||||||
assert p is not None, f"INTERNAL ERROR: hand-made leaf without parent: {leaf!r}"
|
assert p is not None, f"INTERNAL ERROR: hand-made leaf without parent: {leaf!r}"
|
||||||
if t == token.COLON and p.type not in {
|
if t == token.COLON and p.type not in {
|
||||||
syms.subscript, syms.subscriptlist, syms.sliceop
|
syms.subscript,
|
||||||
|
syms.subscriptlist,
|
||||||
|
syms.sliceop,
|
||||||
}:
|
}:
|
||||||
return NO
|
return NO
|
||||||
|
|
||||||
@ -1495,7 +1498,10 @@ def whitespace(leaf: Leaf, *, complex_subscript: bool) -> str: # noqa C901
|
|||||||
if prevp.type == token.EQUAL:
|
if prevp.type == token.EQUAL:
|
||||||
if prevp.parent:
|
if prevp.parent:
|
||||||
if prevp.parent.type in {
|
if prevp.parent.type in {
|
||||||
syms.arglist, syms.argument, syms.parameters, syms.varargslist
|
syms.arglist,
|
||||||
|
syms.argument,
|
||||||
|
syms.parameters,
|
||||||
|
syms.varargslist,
|
||||||
}:
|
}:
|
||||||
return NO
|
return NO
|
||||||
|
|
||||||
@ -1649,7 +1655,8 @@ def whitespace(leaf: Leaf, *, complex_subscript: bool) -> str: # noqa C901
|
|||||||
prevp_parent = prevp.parent
|
prevp_parent = prevp.parent
|
||||||
assert prevp_parent is not None
|
assert prevp_parent is not None
|
||||||
if prevp.type == token.COLON and prevp_parent.type in {
|
if prevp.type == token.COLON and prevp_parent.type in {
|
||||||
syms.subscript, syms.sliceop
|
syms.subscript,
|
||||||
|
syms.sliceop,
|
||||||
}:
|
}:
|
||||||
return NO
|
return NO
|
||||||
|
|
||||||
@ -1902,15 +1909,15 @@ def split_line(
|
|||||||
return
|
return
|
||||||
|
|
||||||
line_str = str(line).strip("\n")
|
line_str = str(line).strip("\n")
|
||||||
if is_line_short_enough(line, line_length=line_length, line_str=line_str):
|
if not line.should_explode and is_line_short_enough(
|
||||||
|
line, line_length=line_length, line_str=line_str
|
||||||
|
):
|
||||||
yield line
|
yield line
|
||||||
return
|
return
|
||||||
|
|
||||||
split_funcs: List[SplitFunc]
|
split_funcs: List[SplitFunc]
|
||||||
if line.is_def:
|
if line.is_def:
|
||||||
split_funcs = [left_hand_split]
|
split_funcs = [left_hand_split]
|
||||||
elif line.is_import:
|
|
||||||
split_funcs = [explode_split]
|
|
||||||
else:
|
else:
|
||||||
|
|
||||||
def rhs(line: Line, py36: bool = False) -> Iterator[Line]:
|
def rhs(line: Line, py36: bool = False) -> Iterator[Line]:
|
||||||
@ -2073,6 +2080,7 @@ def right_hand_split(
|
|||||||
|
|
||||||
ensure_visible(opening_bracket)
|
ensure_visible(opening_bracket)
|
||||||
ensure_visible(closing_bracket)
|
ensure_visible(closing_bracket)
|
||||||
|
body.should_explode = should_explode(body, opening_bracket)
|
||||||
for result in (head, body, tail):
|
for result in (head, body, tail):
|
||||||
if result:
|
if result:
|
||||||
yield result
|
yield result
|
||||||
@ -2212,26 +2220,6 @@ def append_to_line(leaf: Leaf) -> Iterator[Line]:
|
|||||||
yield current_line
|
yield current_line
|
||||||
|
|
||||||
|
|
||||||
def explode_split(
|
|
||||||
line: Line, py36: bool = False, omit: Collection[LeafID] = ()
|
|
||||||
) -> Iterator[Line]:
|
|
||||||
"""Split by rightmost bracket and immediately split contents by a delimiter."""
|
|
||||||
new_lines = list(right_hand_split(line, py36, omit))
|
|
||||||
if len(new_lines) != 3:
|
|
||||||
yield from new_lines
|
|
||||||
return
|
|
||||||
|
|
||||||
yield new_lines[0]
|
|
||||||
|
|
||||||
try:
|
|
||||||
yield from delimiter_split(new_lines[1], py36)
|
|
||||||
|
|
||||||
except CannotSplit:
|
|
||||||
yield new_lines[1]
|
|
||||||
|
|
||||||
yield new_lines[2]
|
|
||||||
|
|
||||||
|
|
||||||
def is_import(leaf: Leaf) -> bool:
|
def is_import(leaf: Leaf) -> bool:
|
||||||
"""Return True if the given leaf starts an import statement."""
|
"""Return True if the given leaf starts an import statement."""
|
||||||
p = leaf.parent
|
p = leaf.parent
|
||||||
@ -2547,6 +2535,17 @@ def ensure_visible(leaf: Leaf) -> None:
|
|||||||
leaf.value = ")"
|
leaf.value = ")"
|
||||||
|
|
||||||
|
|
||||||
|
def should_explode(line: Line, opening_bracket: Leaf) -> bool:
|
||||||
|
"""Should `line` immediately be split with `delimiter_split()` after RHS?"""
|
||||||
|
return bool(
|
||||||
|
opening_bracket.parent
|
||||||
|
and opening_bracket.parent.type in {syms.atom, syms.import_from}
|
||||||
|
and opening_bracket.value in "[{("
|
||||||
|
and line.bracket_tracker.delimiters
|
||||||
|
and line.bracket_tracker.max_delimiter_priority() == COMMA_PRIORITY
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
def is_python36(node: Node) -> bool:
|
def is_python36(node: Node) -> bool:
|
||||||
"""Return True if the current file is using Python 3.6+ features.
|
"""Return True if the current file is using Python 3.6+ features.
|
||||||
|
|
||||||
@ -2675,7 +2674,15 @@ def get_future_imports(node: Node) -> Set[str]:
|
|||||||
|
|
||||||
PYTHON_EXTENSIONS = {".py", ".pyi"}
|
PYTHON_EXTENSIONS = {".py", ".pyi"}
|
||||||
BLACKLISTED_DIRECTORIES = {
|
BLACKLISTED_DIRECTORIES = {
|
||||||
"build", "buck-out", "dist", "_build", ".git", ".hg", ".mypy_cache", ".tox", ".venv"
|
"build",
|
||||||
|
"buck-out",
|
||||||
|
"dist",
|
||||||
|
"_build",
|
||||||
|
".git",
|
||||||
|
".hg",
|
||||||
|
".mypy_cache",
|
||||||
|
".tox",
|
||||||
|
".venv",
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -66,8 +66,6 @@ Split functions
|
|||||||
|
|
||||||
.. autofunction:: black.delimiter_split
|
.. autofunction:: black.delimiter_split
|
||||||
|
|
||||||
.. autofunction:: black.explode_split
|
|
||||||
|
|
||||||
.. autofunction:: black.left_hand_split
|
.. autofunction:: black.left_hand_split
|
||||||
|
|
||||||
.. autofunction:: black.right_hand_split
|
.. autofunction:: black.right_hand_split
|
||||||
|
@ -38,7 +38,9 @@
|
|||||||
1
|
1
|
||||||
) # with a comment
|
) # with a comment
|
||||||
this_is_a_ridiculously_long_name_and_nobody_in_their_right_mind_would_use_one_like_it = [
|
this_is_a_ridiculously_long_name_and_nobody_in_their_right_mind_would_use_one_like_it = [
|
||||||
1, 2, 3
|
1,
|
||||||
|
2,
|
||||||
|
3,
|
||||||
]
|
]
|
||||||
this_is_a_ridiculously_long_name_and_nobody_in_their_right_mind_would_use_one_like_it = (
|
this_is_a_ridiculously_long_name_and_nobody_in_their_right_mind_would_use_one_like_it = (
|
||||||
function()
|
function()
|
||||||
|
@ -35,9 +35,9 @@
|
|||||||
def inline_comments_in_brackets_ruin_everything():
|
def inline_comments_in_brackets_ruin_everything():
|
||||||
if typedargslist:
|
if typedargslist:
|
||||||
parameters.children = [
|
parameters.children = [
|
||||||
parameters.children[0], # (1
|
children[0], # (1
|
||||||
body,
|
body,
|
||||||
parameters.children[-1], # )1
|
children[-1], # )1
|
||||||
]
|
]
|
||||||
else:
|
else:
|
||||||
parameters.children = [
|
parameters.children = [
|
||||||
@ -163,9 +163,7 @@ def inline_comments_in_brackets_ruin_everything():
|
|||||||
# Comment before function.
|
# Comment before function.
|
||||||
def inline_comments_in_brackets_ruin_everything():
|
def inline_comments_in_brackets_ruin_everything():
|
||||||
if typedargslist:
|
if typedargslist:
|
||||||
parameters.children = [
|
parameters.children = [children[0], body, children[-1]] # (1 # )1
|
||||||
parameters.children[0], body, parameters.children[-1] # (1 # )1
|
|
||||||
]
|
|
||||||
else:
|
else:
|
||||||
parameters.children = [
|
parameters.children = [
|
||||||
parameters.children[0], # (2 what if this was actually long
|
parameters.children[0], # (2 what if this was actually long
|
||||||
|
@ -11,7 +11,7 @@
|
|||||||
True
|
True
|
||||||
False
|
False
|
||||||
1
|
1
|
||||||
@@ -29,62 +29,82 @@
|
@@ -29,62 +29,83 @@
|
||||||
~great
|
~great
|
||||||
+value
|
+value
|
||||||
-1
|
-1
|
||||||
@ -29,7 +29,8 @@
|
|||||||
manylambdas = lambda x=lambda y=lambda z=1: z: y(): x()
|
manylambdas = lambda x=lambda y=lambda z=1: z: y(): x()
|
||||||
-foo = (lambda port_id, ignore_missing: {"port1": port1_resource, "port2": port2_resource}[port_id])
|
-foo = (lambda port_id, ignore_missing: {"port1": port1_resource, "port2": port2_resource}[port_id])
|
||||||
+foo = lambda port_id, ignore_missing: {
|
+foo = lambda port_id, ignore_missing: {
|
||||||
+ "port1": port1_resource, "port2": port2_resource
|
+ "port1": port1_resource,
|
||||||
|
+ "port2": port2_resource,
|
||||||
+}[port_id]
|
+}[port_id]
|
||||||
1 if True else 2
|
1 if True else 2
|
||||||
str or None if True else str or bytes or None
|
str or None if True else str or bytes or None
|
||||||
@ -115,7 +116,7 @@
|
|||||||
call(**self.screen_kwargs)
|
call(**self.screen_kwargs)
|
||||||
call(b, **self.screen_kwargs)
|
call(b, **self.screen_kwargs)
|
||||||
lukasz.langa.pl
|
lukasz.langa.pl
|
||||||
@@ -93,11 +113,11 @@
|
@@ -93,11 +114,11 @@
|
||||||
1.0 .real
|
1.0 .real
|
||||||
....__class__
|
....__class__
|
||||||
list[str]
|
list[str]
|
||||||
@ -128,7 +129,7 @@
|
|||||||
]
|
]
|
||||||
slice[0]
|
slice[0]
|
||||||
slice[0:1]
|
slice[0:1]
|
||||||
@@ -124,107 +144,159 @@
|
@@ -124,107 +145,159 @@
|
||||||
numpy[-(c + 1) :, d]
|
numpy[-(c + 1) :, d]
|
||||||
numpy[:, l[-2]]
|
numpy[:, l[-2]]
|
||||||
numpy[:, ::-1]
|
numpy[:, ::-1]
|
||||||
|
@ -273,7 +273,8 @@ async def f():
|
|||||||
lambda a, b, c=True, *vararg, d=(v1 << 2), e="str", **kwargs: a + b
|
lambda a, b, c=True, *vararg, d=(v1 << 2), e="str", **kwargs: a + b
|
||||||
manylambdas = lambda x=lambda y=lambda z=1: z: y(): x()
|
manylambdas = lambda x=lambda y=lambda z=1: z: y(): x()
|
||||||
foo = lambda port_id, ignore_missing: {
|
foo = lambda port_id, ignore_missing: {
|
||||||
"port1": port1_resource, "port2": port2_resource
|
"port1": port1_resource,
|
||||||
|
"port2": port2_resource,
|
||||||
}[port_id]
|
}[port_id]
|
||||||
1 if True else 2
|
1 if True else 2
|
||||||
str or None if True else str or bytes or None
|
str or None if True else str or bytes or None
|
||||||
|
Loading…
Reference in New Issue
Block a user