-
-
Notifications
You must be signed in to change notification settings - Fork 12
/
typed_identifier.rs
138 lines (114 loc) · 3.19 KB
/
typed_identifier.rs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
use crate::nodes::{Identifier, Token, Type};
#[derive(Clone, Debug, PartialEq, Eq)]
pub struct TypedIdentifier {
name: Identifier,
r#type: Option<Type>,
token: Option<Token>,
}
impl TypedIdentifier {
pub fn new(name: impl Into<String>) -> Self {
Self {
name: Identifier::new(name.into()),
r#type: None,
token: None,
}
}
pub fn with_type(mut self, type_value: impl Into<Type>) -> Self {
self.r#type = Some(type_value.into());
self
}
pub fn with_colon_token(mut self, token: Token) -> Self {
self.token = Some(token);
self
}
#[inline]
pub fn set_colon_token(&mut self, token: Token) {
self.token = Some(token);
}
#[inline]
pub fn get_colon_token(&self) -> Option<&Token> {
self.token.as_ref()
}
#[inline]
pub fn get_identifier(&self) -> &Identifier {
&self.name
}
#[inline]
pub fn get_type(&self) -> Option<&Type> {
self.r#type.as_ref()
}
#[inline]
pub fn has_type(&self) -> bool {
self.r#type.is_some()
}
#[inline]
pub fn mutate_type(&mut self) -> Option<&mut Type> {
self.r#type.as_mut()
}
pub fn remove_type(mut self) -> Option<Type> {
self.token.take();
self.r#type.take()
}
pub fn clear_comments(&mut self) {
self.name.clear_comments();
if let Some(token) = &mut self.token {
token.clear_comments();
}
}
pub fn clear_whitespaces(&mut self) {
self.name.clear_whitespaces();
if let Some(token) = &mut self.token {
token.clear_whitespaces();
}
}
pub(crate) fn replace_referenced_tokens(&mut self, code: &str) {
self.name.replace_referenced_tokens(code);
if let Some(token) = &mut self.token {
token.replace_referenced_tokens(code);
}
}
pub(crate) fn shift_token_line(&mut self, amount: usize) {
self.name.shift_token_line(amount);
if let Some(token) = &mut self.token {
token.shift_token_line(amount);
}
}
}
impl<IntoIdentifier: Into<Identifier>> From<IntoIdentifier> for TypedIdentifier {
fn from(name: IntoIdentifier) -> Self {
Self {
name: name.into(),
r#type: None,
token: None,
}
}
}
impl std::ops::Deref for TypedIdentifier {
type Target = Identifier;
fn deref(&self) -> &Self::Target {
&self.name
}
}
impl std::ops::DerefMut for TypedIdentifier {
fn deref_mut(&mut self) -> &mut Self::Target {
&mut self.name
}
}
#[cfg(test)]
mod test {
use crate::nodes::Position;
use super::*;
#[test]
fn set_name_replaces_the_token_content() {
let token = Token::new_with_line(7, 10, 1);
let mut typed_identifier = TypedIdentifier::from(Identifier::new("var").with_token(token));
typed_identifier.set_name("newVar");
assert_eq!(
typed_identifier.get_identifier().get_token().unwrap(),
&Token::from_position(Position::LineNumber {
line_number: 1,
content: "newVar".into(),
})
);
}
}