Handle self/super/crate in PathSegment as NameRef

This commit is contained in:
Lukas Wirth 2021-01-15 18:57:32 +01:00
parent 0c58aa9dc0
commit cb863390f2
42 changed files with 258 additions and 254 deletions

View file

@ -18,6 +18,9 @@ pub struct NameRef {
}
impl NameRef {
pub fn ident_token(&self) -> Option<SyntaxToken> { support::token(&self.syntax, T![ident]) }
pub fn self_token(&self) -> Option<SyntaxToken> { support::token(&self.syntax, T![self]) }
pub fn super_token(&self) -> Option<SyntaxToken> { support::token(&self.syntax, T![super]) }
pub fn crate_token(&self) -> Option<SyntaxToken> { support::token(&self.syntax, T![crate]) }
}
#[derive(Debug, Clone, PartialEq, Eq, Hash)]
pub struct Lifetime {
@ -42,9 +45,6 @@ pub struct PathSegment {
pub(crate) syntax: SyntaxNode,
}
impl PathSegment {
pub fn crate_token(&self) -> Option<SyntaxToken> { support::token(&self.syntax, T![crate]) }
pub fn self_token(&self) -> Option<SyntaxToken> { support::token(&self.syntax, T![self]) }
pub fn super_token(&self) -> Option<SyntaxToken> { support::token(&self.syntax, T![super]) }
pub fn coloncolon_token(&self) -> Option<SyntaxToken> { support::token(&self.syntax, T![::]) }
pub fn name_ref(&self) -> Option<NameRef> { support::child(&self.syntax) }
pub fn generic_arg_list(&self) -> Option<GenericArgList> { support::child(&self.syntax) }

View file

@ -156,14 +156,28 @@ impl ast::PathSegment {
.expect("segments are always nested in paths")
}
pub fn crate_token(&self) -> Option<SyntaxToken> {
self.name_ref().and_then(|it| it.crate_token())
}
pub fn self_token(&self) -> Option<SyntaxToken> {
self.name_ref().and_then(|it| it.self_token())
}
pub fn super_token(&self) -> Option<SyntaxToken> {
self.name_ref().and_then(|it| it.super_token())
}
pub fn kind(&self) -> Option<PathSegmentKind> {
let res = if let Some(name_ref) = self.name_ref() {
PathSegmentKind::Name(name_ref)
match name_ref.syntax().first_token().map(|it| it.kind()) {
Some(T![self]) => PathSegmentKind::SelfKw,
Some(T![super]) => PathSegmentKind::SuperKw,
Some(T![crate]) => PathSegmentKind::CrateKw,
_ => PathSegmentKind::Name(name_ref),
}
} else {
match self.syntax().first_child_or_token()?.kind() {
T![self] => PathSegmentKind::SelfKw,
T![super] => PathSegmentKind::SuperKw,
T![crate] => PathSegmentKind::CrateKw,
T![<] => {
// <T> or <T as Trait>
// T is any TypeRef, Trait has to be a PathType