mirror of
https://github.com/RustPython/Parser.git
synced 2025-07-12 15:45:22 +00:00
Parse type parameters in class definitions
This commit is contained in:
parent
c8092b20a2
commit
d923aa92bb
9 changed files with 24303 additions and 22583 deletions
|
@ -636,6 +636,79 @@ class Foo(A, B):
|
||||||
insta::assert_debug_snapshot!(ast::Suite::parse(source, "<test>").unwrap());
|
insta::assert_debug_snapshot!(ast::Suite::parse(source, "<test>").unwrap());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
#[cfg(feature = "all-nodes-with-ranges")]
|
||||||
|
fn test_parse_class_with_empty_generic() {
|
||||||
|
let source = "\
|
||||||
|
class Foo[](A, B):
|
||||||
|
pass
|
||||||
|
";
|
||||||
|
insta::assert_debug_snapshot!(ast::Suite::parse(source, "<test>").unwrap());
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
#[cfg(feature = "all-nodes-with-ranges")]
|
||||||
|
fn test_parse_class_with_generic_type() {
|
||||||
|
let source = "\
|
||||||
|
class Foo[T](A, B):
|
||||||
|
pass
|
||||||
|
";
|
||||||
|
insta::assert_debug_snapshot!(ast::Suite::parse(source, "<test>").unwrap());
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
#[cfg(feature = "all-nodes-with-ranges")]
|
||||||
|
fn test_parse_class_with_generic_type_with_bound() {
|
||||||
|
let source = "\
|
||||||
|
class Foo[T: str](A, B):
|
||||||
|
pass
|
||||||
|
";
|
||||||
|
insta::assert_debug_snapshot!(ast::Suite::parse(source, "<test>").unwrap());
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
#[cfg(feature = "all-nodes-with-ranges")]
|
||||||
|
fn test_parse_class_with_multiple_generic_types() {
|
||||||
|
let source = "\
|
||||||
|
class Foo[T, U](A, B):
|
||||||
|
pass
|
||||||
|
";
|
||||||
|
insta::assert_debug_snapshot!(ast::Suite::parse(source, "<test>").unwrap());
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
#[cfg(feature = "all-nodes-with-ranges")]
|
||||||
|
fn test_parse_class_with_generic_type_var_tuple() {
|
||||||
|
let source = "\
|
||||||
|
class Foo[*U](A, B):
|
||||||
|
pass
|
||||||
|
";
|
||||||
|
insta::assert_debug_snapshot!(ast::Suite::parse(source, "<test>").unwrap());
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
#[cfg(feature = "all-nodes-with-ranges")]
|
||||||
|
fn test_parse_class_with_generic_param_spec() {
|
||||||
|
let source = "\
|
||||||
|
class Foo[**P](A, B):
|
||||||
|
pass
|
||||||
|
";
|
||||||
|
insta::assert_debug_snapshot!(ast::Suite::parse(source, "<test>").unwrap());
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
#[cfg(feature = "all-nodes-with-ranges")]
|
||||||
|
fn test_parse_class_with_all_possible_generic_types() {
|
||||||
|
let source = "\
|
||||||
|
class Foo[X, Y, *U, **P](A, B):
|
||||||
|
pass
|
||||||
|
";
|
||||||
|
insta::assert_debug_snapshot!(ast::Suite::parse(source, "<test>").unwrap());
|
||||||
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
#[cfg(feature = "all-nodes-with-ranges")]
|
#[cfg(feature = "all-nodes-with-ranges")]
|
||||||
fn test_parse_dict_comprehension() {
|
fn test_parse_dict_comprehension() {
|
||||||
|
|
|
@ -1126,13 +1126,12 @@ KwargParameter<ArgType>: Option<Box<ast::Arg>> = {
|
||||||
};
|
};
|
||||||
|
|
||||||
ClassDef: ast::Stmt = {
|
ClassDef: ast::Stmt = {
|
||||||
<decorator_list:Decorator*> <location:@L> "class" <name:Identifier> <a:("(" ArgumentList ")")?> ":" <body:Suite> => {
|
<decorator_list:Decorator*> <location:@L> "class" <name:Identifier> <type_params:TypeParamList?> <a:("(" ArgumentList ")")?> ":" <body:Suite> => {
|
||||||
let (bases, keywords) = match a {
|
let (bases, keywords) = match a {
|
||||||
Some((_, arg, _)) => (arg.args, arg.keywords),
|
Some((_, arg, _)) => (arg.args, arg.keywords),
|
||||||
None => (vec![], vec![]),
|
None => (vec![], vec![]),
|
||||||
};
|
};
|
||||||
let end_location = body.last().unwrap().end();
|
let end_location = body.last().unwrap().end();
|
||||||
let type_params = Vec::new();
|
|
||||||
ast::Stmt::ClassDef(
|
ast::Stmt::ClassDef(
|
||||||
ast::StmtClassDef {
|
ast::StmtClassDef {
|
||||||
name,
|
name,
|
||||||
|
@ -1140,13 +1139,38 @@ ClassDef: ast::Stmt = {
|
||||||
keywords,
|
keywords,
|
||||||
body,
|
body,
|
||||||
decorator_list,
|
decorator_list,
|
||||||
type_params,
|
type_params: type_params.unwrap_or_default(),
|
||||||
range: (location..end_location).into()
|
range: (location..end_location).into()
|
||||||
},
|
},
|
||||||
)
|
)
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
TypeParamList: Vec<ast::TypeParam> = {
|
||||||
|
<location:@L> "[" <vars:OneOrMore<TypeParam>> ","? "]" <end_location:@R> => {
|
||||||
|
vars
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
TypeParam: ast::TypeParam = {
|
||||||
|
<location:@L> <name:Identifier> <bound:(":" <Test<"all">>)?> <end_location:@R> => {
|
||||||
|
ast::TypeParam::TypeVar(
|
||||||
|
ast::TypeParamTypeVar { name, bound: bound.map(Box::new), range: (location..end_location).into() }
|
||||||
|
)
|
||||||
|
},
|
||||||
|
<location:@L> "*" <name:Identifier> <end_location:@R> => {
|
||||||
|
ast::TypeParam::TypeVarTuple(
|
||||||
|
ast::TypeParamTypeVarTuple { name, range: (location..end_location).into() }
|
||||||
|
)
|
||||||
|
},
|
||||||
|
<location:@L> "**" <name:Identifier> <end_location:@R> => {
|
||||||
|
ast::TypeParam::ParamSpec(
|
||||||
|
ast::TypeParamParamSpec { name, range: (location..end_location).into() }
|
||||||
|
)
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
// Decorators:
|
// Decorators:
|
||||||
Decorator: ast::Expr = {
|
Decorator: ast::Expr = {
|
||||||
<location:@L> "@" <p:NamedExpressionTest> "\n" => {
|
<location:@L> "@" <p:NamedExpressionTest> "\n" => {
|
||||||
|
|
46413
parser/src/python.rs
generated
46413
parser/src/python.rs
generated
File diff suppressed because it is too large
Load diff
|
@ -0,0 +1,79 @@
|
||||||
|
---
|
||||||
|
source: parser/src/parser.rs
|
||||||
|
expression: "ast::Suite::parse(source, \"<test>\").unwrap()"
|
||||||
|
---
|
||||||
|
[
|
||||||
|
ClassDef(
|
||||||
|
StmtClassDef {
|
||||||
|
range: 0..38,
|
||||||
|
name: Identifier(
|
||||||
|
"Foo",
|
||||||
|
),
|
||||||
|
bases: [
|
||||||
|
Name(
|
||||||
|
ExprName {
|
||||||
|
range: 25..26,
|
||||||
|
id: Identifier(
|
||||||
|
"A",
|
||||||
|
),
|
||||||
|
ctx: Load,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
Name(
|
||||||
|
ExprName {
|
||||||
|
range: 28..29,
|
||||||
|
id: Identifier(
|
||||||
|
"B",
|
||||||
|
),
|
||||||
|
ctx: Load,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
],
|
||||||
|
keywords: [],
|
||||||
|
body: [
|
||||||
|
Pass(
|
||||||
|
StmtPass {
|
||||||
|
range: 34..38,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
],
|
||||||
|
decorator_list: [],
|
||||||
|
type_params: [
|
||||||
|
TypeVar(
|
||||||
|
TypeParamTypeVar {
|
||||||
|
range: 10..11,
|
||||||
|
name: Identifier(
|
||||||
|
"X",
|
||||||
|
),
|
||||||
|
bound: None,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
TypeVar(
|
||||||
|
TypeParamTypeVar {
|
||||||
|
range: 13..14,
|
||||||
|
name: Identifier(
|
||||||
|
"Y",
|
||||||
|
),
|
||||||
|
bound: None,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
TypeVarTuple(
|
||||||
|
TypeParamTypeVarTuple {
|
||||||
|
range: 16..18,
|
||||||
|
name: Identifier(
|
||||||
|
"U",
|
||||||
|
),
|
||||||
|
},
|
||||||
|
),
|
||||||
|
ParamSpec(
|
||||||
|
TypeParamParamSpec {
|
||||||
|
range: 20..23,
|
||||||
|
name: Identifier(
|
||||||
|
"P",
|
||||||
|
),
|
||||||
|
},
|
||||||
|
),
|
||||||
|
],
|
||||||
|
},
|
||||||
|
),
|
||||||
|
]
|
53
parser/src/snapshots/rustpython_parser__parser__tests__parse_class_with_generic_param_spec.snap
generated
Normal file
53
parser/src/snapshots/rustpython_parser__parser__tests__parse_class_with_generic_param_spec.snap
generated
Normal file
|
@ -0,0 +1,53 @@
|
||||||
|
---
|
||||||
|
source: parser/src/parser.rs
|
||||||
|
expression: "ast::Suite::parse(source, \"<test>\").unwrap()"
|
||||||
|
---
|
||||||
|
[
|
||||||
|
ClassDef(
|
||||||
|
StmtClassDef {
|
||||||
|
range: 0..28,
|
||||||
|
name: Identifier(
|
||||||
|
"Foo",
|
||||||
|
),
|
||||||
|
bases: [
|
||||||
|
Name(
|
||||||
|
ExprName {
|
||||||
|
range: 15..16,
|
||||||
|
id: Identifier(
|
||||||
|
"A",
|
||||||
|
),
|
||||||
|
ctx: Load,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
Name(
|
||||||
|
ExprName {
|
||||||
|
range: 18..19,
|
||||||
|
id: Identifier(
|
||||||
|
"B",
|
||||||
|
),
|
||||||
|
ctx: Load,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
],
|
||||||
|
keywords: [],
|
||||||
|
body: [
|
||||||
|
Pass(
|
||||||
|
StmtPass {
|
||||||
|
range: 24..28,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
],
|
||||||
|
decorator_list: [],
|
||||||
|
type_params: [
|
||||||
|
ParamSpec(
|
||||||
|
TypeParamParamSpec {
|
||||||
|
range: 10..13,
|
||||||
|
name: Identifier(
|
||||||
|
"P",
|
||||||
|
),
|
||||||
|
},
|
||||||
|
),
|
||||||
|
],
|
||||||
|
},
|
||||||
|
),
|
||||||
|
]
|
54
parser/src/snapshots/rustpython_parser__parser__tests__parse_class_with_generic_type.snap
generated
Normal file
54
parser/src/snapshots/rustpython_parser__parser__tests__parse_class_with_generic_type.snap
generated
Normal file
|
@ -0,0 +1,54 @@
|
||||||
|
---
|
||||||
|
source: parser/src/parser.rs
|
||||||
|
expression: "ast::Suite::parse(source, \"<test>\").unwrap()"
|
||||||
|
---
|
||||||
|
[
|
||||||
|
ClassDef(
|
||||||
|
StmtClassDef {
|
||||||
|
range: 0..26,
|
||||||
|
name: Identifier(
|
||||||
|
"Foo",
|
||||||
|
),
|
||||||
|
bases: [
|
||||||
|
Name(
|
||||||
|
ExprName {
|
||||||
|
range: 13..14,
|
||||||
|
id: Identifier(
|
||||||
|
"A",
|
||||||
|
),
|
||||||
|
ctx: Load,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
Name(
|
||||||
|
ExprName {
|
||||||
|
range: 16..17,
|
||||||
|
id: Identifier(
|
||||||
|
"B",
|
||||||
|
),
|
||||||
|
ctx: Load,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
],
|
||||||
|
keywords: [],
|
||||||
|
body: [
|
||||||
|
Pass(
|
||||||
|
StmtPass {
|
||||||
|
range: 22..26,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
],
|
||||||
|
decorator_list: [],
|
||||||
|
type_params: [
|
||||||
|
TypeVar(
|
||||||
|
TypeParamTypeVar {
|
||||||
|
range: 10..11,
|
||||||
|
name: Identifier(
|
||||||
|
"T",
|
||||||
|
),
|
||||||
|
bound: None,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
],
|
||||||
|
},
|
||||||
|
),
|
||||||
|
]
|
53
parser/src/snapshots/rustpython_parser__parser__tests__parse_class_with_generic_type_var_tuple.snap
generated
Normal file
53
parser/src/snapshots/rustpython_parser__parser__tests__parse_class_with_generic_type_var_tuple.snap
generated
Normal file
|
@ -0,0 +1,53 @@
|
||||||
|
---
|
||||||
|
source: parser/src/parser.rs
|
||||||
|
expression: "ast::Suite::parse(source, \"<test>\").unwrap()"
|
||||||
|
---
|
||||||
|
[
|
||||||
|
ClassDef(
|
||||||
|
StmtClassDef {
|
||||||
|
range: 0..27,
|
||||||
|
name: Identifier(
|
||||||
|
"Foo",
|
||||||
|
),
|
||||||
|
bases: [
|
||||||
|
Name(
|
||||||
|
ExprName {
|
||||||
|
range: 14..15,
|
||||||
|
id: Identifier(
|
||||||
|
"A",
|
||||||
|
),
|
||||||
|
ctx: Load,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
Name(
|
||||||
|
ExprName {
|
||||||
|
range: 17..18,
|
||||||
|
id: Identifier(
|
||||||
|
"B",
|
||||||
|
),
|
||||||
|
ctx: Load,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
],
|
||||||
|
keywords: [],
|
||||||
|
body: [
|
||||||
|
Pass(
|
||||||
|
StmtPass {
|
||||||
|
range: 23..27,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
],
|
||||||
|
decorator_list: [],
|
||||||
|
type_params: [
|
||||||
|
TypeVarTuple(
|
||||||
|
TypeParamTypeVarTuple {
|
||||||
|
range: 10..12,
|
||||||
|
name: Identifier(
|
||||||
|
"U",
|
||||||
|
),
|
||||||
|
},
|
||||||
|
),
|
||||||
|
],
|
||||||
|
},
|
||||||
|
),
|
||||||
|
]
|
64
parser/src/snapshots/rustpython_parser__parser__tests__parse_class_with_generic_type_with_bound.snap
generated
Normal file
64
parser/src/snapshots/rustpython_parser__parser__tests__parse_class_with_generic_type_with_bound.snap
generated
Normal file
|
@ -0,0 +1,64 @@
|
||||||
|
---
|
||||||
|
source: parser/src/parser.rs
|
||||||
|
expression: "ast::Suite::parse(source, \"<test>\").unwrap()"
|
||||||
|
---
|
||||||
|
[
|
||||||
|
ClassDef(
|
||||||
|
StmtClassDef {
|
||||||
|
range: 0..31,
|
||||||
|
name: Identifier(
|
||||||
|
"Foo",
|
||||||
|
),
|
||||||
|
bases: [
|
||||||
|
Name(
|
||||||
|
ExprName {
|
||||||
|
range: 18..19,
|
||||||
|
id: Identifier(
|
||||||
|
"A",
|
||||||
|
),
|
||||||
|
ctx: Load,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
Name(
|
||||||
|
ExprName {
|
||||||
|
range: 21..22,
|
||||||
|
id: Identifier(
|
||||||
|
"B",
|
||||||
|
),
|
||||||
|
ctx: Load,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
],
|
||||||
|
keywords: [],
|
||||||
|
body: [
|
||||||
|
Pass(
|
||||||
|
StmtPass {
|
||||||
|
range: 27..31,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
],
|
||||||
|
decorator_list: [],
|
||||||
|
type_params: [
|
||||||
|
TypeVar(
|
||||||
|
TypeParamTypeVar {
|
||||||
|
range: 10..16,
|
||||||
|
name: Identifier(
|
||||||
|
"T",
|
||||||
|
),
|
||||||
|
bound: Some(
|
||||||
|
Name(
|
||||||
|
ExprName {
|
||||||
|
range: 13..16,
|
||||||
|
id: Identifier(
|
||||||
|
"str",
|
||||||
|
),
|
||||||
|
ctx: Load,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
),
|
||||||
|
},
|
||||||
|
),
|
||||||
|
],
|
||||||
|
},
|
||||||
|
),
|
||||||
|
]
|
63
parser/src/snapshots/rustpython_parser__parser__tests__parse_class_with_multiple_generic_types.snap
generated
Normal file
63
parser/src/snapshots/rustpython_parser__parser__tests__parse_class_with_multiple_generic_types.snap
generated
Normal file
|
@ -0,0 +1,63 @@
|
||||||
|
---
|
||||||
|
source: parser/src/parser.rs
|
||||||
|
expression: "ast::Suite::parse(source, \"<test>\").unwrap()"
|
||||||
|
---
|
||||||
|
[
|
||||||
|
ClassDef(
|
||||||
|
StmtClassDef {
|
||||||
|
range: 0..29,
|
||||||
|
name: Identifier(
|
||||||
|
"Foo",
|
||||||
|
),
|
||||||
|
bases: [
|
||||||
|
Name(
|
||||||
|
ExprName {
|
||||||
|
range: 16..17,
|
||||||
|
id: Identifier(
|
||||||
|
"A",
|
||||||
|
),
|
||||||
|
ctx: Load,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
Name(
|
||||||
|
ExprName {
|
||||||
|
range: 19..20,
|
||||||
|
id: Identifier(
|
||||||
|
"B",
|
||||||
|
),
|
||||||
|
ctx: Load,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
],
|
||||||
|
keywords: [],
|
||||||
|
body: [
|
||||||
|
Pass(
|
||||||
|
StmtPass {
|
||||||
|
range: 25..29,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
],
|
||||||
|
decorator_list: [],
|
||||||
|
type_params: [
|
||||||
|
TypeVar(
|
||||||
|
TypeParamTypeVar {
|
||||||
|
range: 10..11,
|
||||||
|
name: Identifier(
|
||||||
|
"T",
|
||||||
|
),
|
||||||
|
bound: None,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
TypeVar(
|
||||||
|
TypeParamTypeVar {
|
||||||
|
range: 13..14,
|
||||||
|
name: Identifier(
|
||||||
|
"U",
|
||||||
|
),
|
||||||
|
bound: None,
|
||||||
|
},
|
||||||
|
),
|
||||||
|
],
|
||||||
|
},
|
||||||
|
),
|
||||||
|
]
|
Loading…
Add table
Add a link
Reference in a new issue