ezno_parser/types/
declare_variable.rs

1use tokenizer_lib::{sized_tokens::TokenStart, Token};
2
3use crate::{
4	declarations::VariableDeclarationItem, derive_ASTNode, errors::parse_lexing_error, ASTNode,
5	Decorator, ParseOptions, ParseResult, Span, TSXKeyword, TSXToken, TokenReader, VariableKeyword,
6};
7
8/// A `declare var/let/const` thingy.
9#[apply(derive_ASTNode)]
10#[derive(Debug, Clone, PartialEq, get_field_by_type::GetFieldByType)]
11#[get_field_by_type_target(Span)]
12pub struct DeclareVariableDeclaration {
13	pub keyword: VariableKeyword,
14	/// TODO expressions advised against, but still parse
15	pub declarations: Vec<VariableDeclarationItem<Option<crate::Expression>>>,
16	pub position: Span,
17	pub decorators: Vec<Decorator>,
18}
19
20impl ASTNode for DeclareVariableDeclaration {
21	fn get_position(&self) -> Span {
22		self.position
23	}
24
25	fn from_reader(
26		reader: &mut impl TokenReader<TSXToken, crate::TokenStart>,
27		state: &mut crate::ParsingState,
28		options: &ParseOptions,
29	) -> ParseResult<Self> {
30		let start = state.expect_keyword(reader, TSXKeyword::Declare)?;
31		Self::from_reader_sub_declare(reader, state, options, Some(start), Vec::new())
32	}
33
34	fn to_string_from_buffer<T: source_map::ToString>(
35		&self,
36		buf: &mut T,
37		options: &crate::ToStringOptions,
38		local: crate::LocalToStringInformation,
39	) {
40		if options.include_type_annotations {
41			buf.push_str("declare ");
42			buf.push_str(self.keyword.as_str());
43			crate::declarations::variable::declarations_to_string(
44				&self.declarations,
45				buf,
46				options,
47				local,
48				false,
49			);
50		}
51	}
52}
53
54impl DeclareVariableDeclaration {
55	pub fn from_reader_sub_declare(
56		reader: &mut impl TokenReader<TSXToken, crate::TokenStart>,
57		state: &mut crate::ParsingState,
58		options: &ParseOptions,
59		start: Option<TokenStart>,
60		decorators: Vec<Decorator>,
61	) -> ParseResult<Self> {
62		let token = reader.next().ok_or_else(parse_lexing_error)?;
63		let start = start.unwrap_or(token.1);
64		let keyword = VariableKeyword::from_reader(token)?;
65		let mut declarations = Vec::new();
66		loop {
67			let value = VariableDeclarationItem::from_reader(reader, state, options)?;
68			declarations.push(value);
69			if let Some(Token(TSXToken::Comma, _)) = reader.peek() {
70				reader.next();
71			} else {
72				break;
73			}
74		}
75
76		let position = start.union(declarations.last().unwrap().get_position());
77
78		Ok(DeclareVariableDeclaration { keyword, declarations, position, decorators })
79	}
80}