luau_parser/impl/
cst.rs

1//! All `impl` blocks for [`Cst`].
2
3use luau_lexer::prelude::{Lexer, Token, TokenType};
4use smol_str::SmolStr;
5
6use crate::types::{AstStatus, Block, Cst, ParseWithArgs, Print, PrintingError};
7
8impl Cst {
9    /// The actual parsing logic for the [`Cst`].
10    pub(crate) fn parse<T: Into<SmolStr>>(token: Token, lexer: &mut Lexer, uri: T) -> Self {
11        let mut errors = Vec::new();
12
13        if token == TokenType::EndOfFile {
14            return Self {
15                uri: uri.into(),
16                block: Block::default(),
17                errors,
18                status: AstStatus::Complete,
19            };
20        }
21
22        let block = Block::parse_with(token, lexer, &mut errors, None::<Token>);
23        let status = if errors.is_empty() {
24            AstStatus::Complete
25        } else {
26            AstStatus::HasErrors
27        };
28
29        Self {
30            uri: uri.into(),
31            block: block.unwrap_or_default(),
32            errors,
33            status,
34        }
35    }
36
37    /// Whether or not this [`Cst`] has errors.
38    #[inline]
39    pub fn has_errors(&self) -> bool {
40        //FIXME:
41        // Check this or `self.errors`? The result will be the same as long
42        // as the users don't edit the CST themselves.
43        self.status == AstStatus::HasErrors
44    }
45
46    /// Try printing the [`Cst`] back into source code. This'll only fail if
47    /// [`Cst.has_errors()`](Self::has_errors()) returns `true`.
48    pub fn try_print(&self) -> Result<String, PrintingError> {
49        if self.has_errors() {
50            Err(PrintingError::ErroneousCst)
51        } else {
52            Ok(self.block.print())
53        }
54    }
55}