luau_parser/impl/expression/
table.rs

1//! All `impl` blocks for table access-related types:
2//!
3//! * [`TableAccessPrefix`]
4//! * [`TableAccessKey`]
5//! * [`TableAccess`]
6
7use luau_lexer::prelude::{Error, Lexer, Symbol, Token, TokenType};
8
9use crate::{
10    handle_error_token,
11    types::{
12        ExpressionWrap, FunctionCall, Parse, ParseWithArgs, Pointer, TableAccess, TableAccessKey,
13        TableAccessPrefix, TableKey, TryParse,
14    },
15};
16
17impl Parse for TableAccessPrefix {
18    fn parse(token: Token, lexer: &mut Lexer, errors: &mut Vec<Error>) -> Option<Self> {
19        match token.token_type {
20            TokenType::Error(error) => handle_error_token!(errors, error),
21            TokenType::Identifier(_) | TokenType::PartialKeyword(_) => {
22                FunctionCall::parse(token.clone(), lexer, errors).or(Some(Self::Name(token)))
23            }
24            TokenType::Symbol(Symbol::OpeningParenthesis) => ExpressionWrap::parse_with(
25                token,
26                lexer,
27                errors,
28                ("Expected <expr>", Symbol::ClosingParenthesis),
29            )
30            .map(Pointer::new)
31            .map(Self::ExpressionWrap),
32            _ => None,
33        }
34    }
35}
36impl TryParse for TableAccessPrefix {}
37
38impl Parse for TableAccessKey {
39    fn parse(maybe_dot: Token, lexer: &mut Lexer, errors: &mut Vec<Error>) -> Option<Self> {
40        Self::parse_with(maybe_dot, lexer, errors, true)
41    }
42}
43impl TryParse for TableAccessKey {}
44
45impl ParseWithArgs<bool> for TableAccessKey {
46    fn parse_with(
47        token: Token,
48        lexer: &mut Lexer,
49        errors: &mut Vec<Error>,
50        accept_expression: bool,
51    ) -> Option<Self> {
52        match token.token_type {
53            TokenType::Error(error) => handle_error_token!(errors, error),
54            TokenType::Symbol(Symbol::Dot) => {
55                next_token_recoverable!(
56                    lexer,
57                    name,
58                    TokenType::Identifier(_) | TokenType::PartialKeyword(_),
59                    TokenType::Identifier("*error*".into()),
60                    errors,
61                    "Expected <ident>"
62                );
63
64                Some(Self::Name {
65                    dot: Pointer::new(token),
66                    name: Pointer::new(name),
67                })
68            }
69            _ if accept_expression && token == TokenType::Symbol(Symbol::OpeningBrackets) => {
70                TableKey::parse_with(token, lexer, errors, false)
71                    .map(Pointer::new)
72                    .map(Self::Expression)
73            }
74            _ => None,
75        }
76    }
77}
78
79impl Parse for TableAccess {
80    fn parse(token: Token, lexer: &mut Lexer, errors: &mut Vec<Error>) -> Option<Self> {
81        Some(Self {
82            prefix: TableAccessPrefix::parse(token, lexer, errors)?,
83            accessed_keys: Vec::<TableAccessKey>::try_parse(lexer, errors)?,
84        })
85    }
86}
87impl TryParse for TableAccess {
88    fn try_parse(lexer: &mut Lexer, errors: &mut Vec<Error>) -> Option<Self> {
89        Some(Self {
90            prefix: TableAccessPrefix::try_parse(lexer, errors)?,
91            accessed_keys: Vec::<TableAccessKey>::try_parse(lexer, errors)?,
92        })
93    }
94}