tell users to use -t py310 (#2668)

This commit is contained in:
Jelle Zijlstra 2021-12-04 15:30:23 -08:00 committed by GitHub
parent f52cb0fe37
commit dc8cdda8fd
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
3 changed files with 33 additions and 1 deletions

View File

@ -4,6 +4,7 @@
### _Black_ ### _Black_
- Point users to using `--target-version py310` if we detect 3.10-only syntax (#2668)
- Cell magics are now only processed if they are known Python cell magics. Earlier, all - Cell magics are now only processed if they are known Python cell magics. Earlier, all
cell magics were tokenized, leading to possible indentation errors e.g. with cell magics were tokenized, leading to possible indentation errors e.g. with
`%%writefile`. (#2630) `%%writefile`. (#2630)

View File

@ -43,6 +43,11 @@
ast3 = ast27 = ast ast3 = ast27 = ast
PY310_HINT: Final[
str
] = "Consider using --target-version py310 to parse Python 3.10 code."
class InvalidInput(ValueError): class InvalidInput(ValueError):
"""Raised when input source code fails all parse attempts.""" """Raised when input source code fails all parse attempts."""
@ -96,7 +101,8 @@ def lib2to3_parse(src_txt: str, target_versions: Iterable[TargetVersion] = ()) -
if not src_txt.endswith("\n"): if not src_txt.endswith("\n"):
src_txt += "\n" src_txt += "\n"
for grammar in get_grammars(set(target_versions)): grammars = get_grammars(set(target_versions))
for grammar in grammars:
drv = driver.Driver(grammar) drv = driver.Driver(grammar)
try: try:
result = drv.parse_string(src_txt, True) result = drv.parse_string(src_txt, True)
@ -117,6 +123,12 @@ def lib2to3_parse(src_txt: str, target_versions: Iterable[TargetVersion] = ()) -
exc = InvalidInput(f"Cannot parse: {lineno}:{column}: {te.args[0]}") exc = InvalidInput(f"Cannot parse: {lineno}:{column}: {te.args[0]}")
else: else:
if pygram.python_grammar_soft_keywords not in grammars and matches_grammar(
src_txt, pygram.python_grammar_soft_keywords
):
original_msg = exc.args[0]
msg = f"{original_msg}\n{PY310_HINT}"
raise InvalidInput(msg) from None
raise exc from None raise exc from None
if isinstance(result, Leaf): if isinstance(result, Leaf):
@ -124,6 +136,16 @@ def lib2to3_parse(src_txt: str, target_versions: Iterable[TargetVersion] = ()) -
return result return result
def matches_grammar(src_txt: str, grammar: Grammar) -> bool:
drv = driver.Driver(grammar)
try:
drv.parse_string(src_txt, True)
except ParseError:
return False
else:
return True
def lib2to3_unparse(node: Node) -> str: def lib2to3_unparse(node: Node) -> str:
"""Given a lib2to3 node, return its string representation.""" """Given a lib2to3 node, return its string representation."""
code = str(node) code = str(node)

View File

@ -210,6 +210,15 @@ def test_patma_invalid() -> None:
exc_info.match("Cannot parse: 10:11") exc_info.match("Cannot parse: 10:11")
def test_patma_hint() -> None:
source, expected = read_data("pattern_matching_simple")
mode = black.Mode(target_versions={black.TargetVersion.PY39})
with pytest.raises(black.parsing.InvalidInput) as exc_info:
assert_format(source, expected, mode, minimum_version=(3, 10))
exc_info.match(black.parsing.PY310_HINT)
def test_docstring_no_string_normalization() -> None: def test_docstring_no_string_normalization() -> None:
"""Like test_docstring but with string normalization off.""" """Like test_docstring but with string normalization off."""
source, expected = read_data("docstring_no_string_normalization") source, expected = read_data("docstring_no_string_normalization")