mirror of
https://github.com/python/cpython.git
synced 2025-11-04 03:44:55 +00:00
bpo-45764: improve error message when missing '(' after 'def' (GH-29484)
to achieve this, change the grammar to expect the '(' token after 'def' NAME.
Automerge-Triggered-By: GH:pablogsal
This commit is contained in:
parent
f4c03484da
commit
2819e98d10
4 changed files with 34 additions and 14 deletions
|
|
@ -264,11 +264,11 @@ function_def[stmt_ty]:
|
||||||
|
|
||||||
function_def_raw[stmt_ty]:
|
function_def_raw[stmt_ty]:
|
||||||
| invalid_def_raw
|
| invalid_def_raw
|
||||||
| 'def' n=NAME '(' params=[params] ')' a=['->' z=expression { z }] &&':' tc=[func_type_comment] b=block {
|
| 'def' n=NAME &&'(' params=[params] ')' a=['->' z=expression { z }] &&':' tc=[func_type_comment] b=block {
|
||||||
_PyAST_FunctionDef(n->v.Name.id,
|
_PyAST_FunctionDef(n->v.Name.id,
|
||||||
(params) ? params : CHECK(arguments_ty, _PyPegen_empty_arguments(p)),
|
(params) ? params : CHECK(arguments_ty, _PyPegen_empty_arguments(p)),
|
||||||
b, NULL, a, NEW_TYPE_COMMENT(p, tc), EXTRA) }
|
b, NULL, a, NEW_TYPE_COMMENT(p, tc), EXTRA) }
|
||||||
| ASYNC 'def' n=NAME '(' params=[params] ')' a=['->' z=expression { z }] &&':' tc=[func_type_comment] b=block {
|
| ASYNC 'def' n=NAME &&'(' params=[params] ')' a=['->' z=expression { z }] &&':' tc=[func_type_comment] b=block {
|
||||||
CHECK_VERSION(
|
CHECK_VERSION(
|
||||||
stmt_ty,
|
stmt_ty,
|
||||||
5,
|
5,
|
||||||
|
|
|
||||||
|
|
@ -898,6 +898,17 @@ leading to spurious errors.
|
||||||
Traceback (most recent call last):
|
Traceback (most recent call last):
|
||||||
SyntaxError: cannot assign to attribute here. Maybe you meant '==' instead of '='?
|
SyntaxError: cannot assign to attribute here. Maybe you meant '==' instead of '='?
|
||||||
|
|
||||||
|
|
||||||
|
Missing parens after function definition
|
||||||
|
|
||||||
|
>>> def f:
|
||||||
|
Traceback (most recent call last):
|
||||||
|
SyntaxError: expected '('
|
||||||
|
|
||||||
|
>>> async def f:
|
||||||
|
Traceback (most recent call last):
|
||||||
|
SyntaxError: expected '('
|
||||||
|
|
||||||
Custom error messages for try blocks that are not followed by except/finally
|
Custom error messages for try blocks that are not followed by except/finally
|
||||||
|
|
||||||
>>> try:
|
>>> try:
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,9 @@
|
||||||
|
The parser now gives a better error message when leaving out the opening
|
||||||
|
parenthesis ``(`` after a ``def``-statement::
|
||||||
|
|
||||||
|
>>> def f:
|
||||||
|
File "<stdin>", line 1
|
||||||
|
def f:
|
||||||
|
^
|
||||||
|
SyntaxError: expected '('
|
||||||
|
|
||||||
|
|
@ -4157,8 +4157,8 @@ function_def_rule(Parser *p)
|
||||||
|
|
||||||
// function_def_raw:
|
// function_def_raw:
|
||||||
// | invalid_def_raw
|
// | invalid_def_raw
|
||||||
// | 'def' NAME '(' params? ')' ['->' expression] &&':' func_type_comment? block
|
// | 'def' NAME &&'(' params? ')' ['->' expression] &&':' func_type_comment? block
|
||||||
// | ASYNC 'def' NAME '(' params? ')' ['->' expression] &&':' func_type_comment? block
|
// | ASYNC 'def' NAME &&'(' params? ')' ['->' expression] &&':' func_type_comment? block
|
||||||
static stmt_ty
|
static stmt_ty
|
||||||
function_def_raw_rule(Parser *p)
|
function_def_raw_rule(Parser *p)
|
||||||
{
|
{
|
||||||
|
|
@ -4197,12 +4197,12 @@ function_def_raw_rule(Parser *p)
|
||||||
D(fprintf(stderr, "%*c%s function_def_raw[%d-%d]: %s failed!\n", p->level, ' ',
|
D(fprintf(stderr, "%*c%s function_def_raw[%d-%d]: %s failed!\n", p->level, ' ',
|
||||||
p->error_indicator ? "ERROR!" : "-", _mark, p->mark, "invalid_def_raw"));
|
p->error_indicator ? "ERROR!" : "-", _mark, p->mark, "invalid_def_raw"));
|
||||||
}
|
}
|
||||||
{ // 'def' NAME '(' params? ')' ['->' expression] &&':' func_type_comment? block
|
{ // 'def' NAME &&'(' params? ')' ['->' expression] &&':' func_type_comment? block
|
||||||
if (p->error_indicator) {
|
if (p->error_indicator) {
|
||||||
D(p->level--);
|
D(p->level--);
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
D(fprintf(stderr, "%*c> function_def_raw[%d-%d]: %s\n", p->level, ' ', _mark, p->mark, "'def' NAME '(' params? ')' ['->' expression] &&':' func_type_comment? block"));
|
D(fprintf(stderr, "%*c> function_def_raw[%d-%d]: %s\n", p->level, ' ', _mark, p->mark, "'def' NAME &&'(' params? ')' ['->' expression] &&':' func_type_comment? block"));
|
||||||
Token * _keyword;
|
Token * _keyword;
|
||||||
Token * _literal;
|
Token * _literal;
|
||||||
Token * _literal_1;
|
Token * _literal_1;
|
||||||
|
|
@ -4217,7 +4217,7 @@ function_def_raw_rule(Parser *p)
|
||||||
&&
|
&&
|
||||||
(n = _PyPegen_name_token(p)) // NAME
|
(n = _PyPegen_name_token(p)) // NAME
|
||||||
&&
|
&&
|
||||||
(_literal = _PyPegen_expect_token(p, 7)) // token='('
|
(_literal = _PyPegen_expect_forced_token(p, 7, "(")) // forced_token='('
|
||||||
&&
|
&&
|
||||||
(params = params_rule(p), !p->error_indicator) // params?
|
(params = params_rule(p), !p->error_indicator) // params?
|
||||||
&&
|
&&
|
||||||
|
|
@ -4232,7 +4232,7 @@ function_def_raw_rule(Parser *p)
|
||||||
(b = block_rule(p)) // block
|
(b = block_rule(p)) // block
|
||||||
)
|
)
|
||||||
{
|
{
|
||||||
D(fprintf(stderr, "%*c+ function_def_raw[%d-%d]: %s succeeded!\n", p->level, ' ', _mark, p->mark, "'def' NAME '(' params? ')' ['->' expression] &&':' func_type_comment? block"));
|
D(fprintf(stderr, "%*c+ function_def_raw[%d-%d]: %s succeeded!\n", p->level, ' ', _mark, p->mark, "'def' NAME &&'(' params? ')' ['->' expression] &&':' func_type_comment? block"));
|
||||||
Token *_token = _PyPegen_get_last_nonnwhitespace_token(p);
|
Token *_token = _PyPegen_get_last_nonnwhitespace_token(p);
|
||||||
if (_token == NULL) {
|
if (_token == NULL) {
|
||||||
D(p->level--);
|
D(p->level--);
|
||||||
|
|
@ -4252,14 +4252,14 @@ function_def_raw_rule(Parser *p)
|
||||||
}
|
}
|
||||||
p->mark = _mark;
|
p->mark = _mark;
|
||||||
D(fprintf(stderr, "%*c%s function_def_raw[%d-%d]: %s failed!\n", p->level, ' ',
|
D(fprintf(stderr, "%*c%s function_def_raw[%d-%d]: %s failed!\n", p->level, ' ',
|
||||||
p->error_indicator ? "ERROR!" : "-", _mark, p->mark, "'def' NAME '(' params? ')' ['->' expression] &&':' func_type_comment? block"));
|
p->error_indicator ? "ERROR!" : "-", _mark, p->mark, "'def' NAME &&'(' params? ')' ['->' expression] &&':' func_type_comment? block"));
|
||||||
}
|
}
|
||||||
{ // ASYNC 'def' NAME '(' params? ')' ['->' expression] &&':' func_type_comment? block
|
{ // ASYNC 'def' NAME &&'(' params? ')' ['->' expression] &&':' func_type_comment? block
|
||||||
if (p->error_indicator) {
|
if (p->error_indicator) {
|
||||||
D(p->level--);
|
D(p->level--);
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
D(fprintf(stderr, "%*c> function_def_raw[%d-%d]: %s\n", p->level, ' ', _mark, p->mark, "ASYNC 'def' NAME '(' params? ')' ['->' expression] &&':' func_type_comment? block"));
|
D(fprintf(stderr, "%*c> function_def_raw[%d-%d]: %s\n", p->level, ' ', _mark, p->mark, "ASYNC 'def' NAME &&'(' params? ')' ['->' expression] &&':' func_type_comment? block"));
|
||||||
Token * _keyword;
|
Token * _keyword;
|
||||||
Token * _literal;
|
Token * _literal;
|
||||||
Token * _literal_1;
|
Token * _literal_1;
|
||||||
|
|
@ -4277,7 +4277,7 @@ function_def_raw_rule(Parser *p)
|
||||||
&&
|
&&
|
||||||
(n = _PyPegen_name_token(p)) // NAME
|
(n = _PyPegen_name_token(p)) // NAME
|
||||||
&&
|
&&
|
||||||
(_literal = _PyPegen_expect_token(p, 7)) // token='('
|
(_literal = _PyPegen_expect_forced_token(p, 7, "(")) // forced_token='('
|
||||||
&&
|
&&
|
||||||
(params = params_rule(p), !p->error_indicator) // params?
|
(params = params_rule(p), !p->error_indicator) // params?
|
||||||
&&
|
&&
|
||||||
|
|
@ -4292,7 +4292,7 @@ function_def_raw_rule(Parser *p)
|
||||||
(b = block_rule(p)) // block
|
(b = block_rule(p)) // block
|
||||||
)
|
)
|
||||||
{
|
{
|
||||||
D(fprintf(stderr, "%*c+ function_def_raw[%d-%d]: %s succeeded!\n", p->level, ' ', _mark, p->mark, "ASYNC 'def' NAME '(' params? ')' ['->' expression] &&':' func_type_comment? block"));
|
D(fprintf(stderr, "%*c+ function_def_raw[%d-%d]: %s succeeded!\n", p->level, ' ', _mark, p->mark, "ASYNC 'def' NAME &&'(' params? ')' ['->' expression] &&':' func_type_comment? block"));
|
||||||
Token *_token = _PyPegen_get_last_nonnwhitespace_token(p);
|
Token *_token = _PyPegen_get_last_nonnwhitespace_token(p);
|
||||||
if (_token == NULL) {
|
if (_token == NULL) {
|
||||||
D(p->level--);
|
D(p->level--);
|
||||||
|
|
@ -4312,7 +4312,7 @@ function_def_raw_rule(Parser *p)
|
||||||
}
|
}
|
||||||
p->mark = _mark;
|
p->mark = _mark;
|
||||||
D(fprintf(stderr, "%*c%s function_def_raw[%d-%d]: %s failed!\n", p->level, ' ',
|
D(fprintf(stderr, "%*c%s function_def_raw[%d-%d]: %s failed!\n", p->level, ' ',
|
||||||
p->error_indicator ? "ERROR!" : "-", _mark, p->mark, "ASYNC 'def' NAME '(' params? ')' ['->' expression] &&':' func_type_comment? block"));
|
p->error_indicator ? "ERROR!" : "-", _mark, p->mark, "ASYNC 'def' NAME &&'(' params? ')' ['->' expression] &&':' func_type_comment? block"));
|
||||||
}
|
}
|
||||||
_res = NULL;
|
_res = NULL;
|
||||||
done:
|
done:
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue