Add ListItem type for Expr::List (#12529)

# Description
This PR adds a `ListItem` enum to our set of AST types. It encodes the
two possible expressions inside of list expression: a singular item or a
spread. This is similar to the existing `RecordItem` enum. Adding
`ListItem` allows us to remove the existing `Expr::Spread` case which
was previously used for list spreads. As a consequence, this guarantees
(via the type system) that spreads can only ever occur inside lists,
records, or as command args.

This PR also does a little bit of cleanup in relevant parser code.
This commit is contained in:
Ian Manske
2024-04-18 11:21:05 +00:00
committed by GitHub
parent 57b0c722c6
commit 6ccd547d81
8 changed files with 179 additions and 133 deletions

View File

@ -86,13 +86,6 @@ impl Expression {
}
}
pub fn as_list(&self) -> Option<Vec<Expression>> {
match &self.expr {
Expr::List(list) => Some(list.clone()),
_ => None,
}
}
pub fn as_keyword(&self) -> Option<&Expression> {
match &self.expr {
Expr::Keyword(_, _, expr) => Some(expr),
@ -213,8 +206,8 @@ impl Expression {
Expr::Int(_) => false,
Expr::Keyword(_, _, expr) => expr.has_in_variable(working_set),
Expr::List(list) => {
for l in list {
if l.has_in_variable(working_set) {
for item in list {
if item.expr().has_in_variable(working_set) {
return true;
}
}
@ -304,7 +297,6 @@ impl Expression {
Expr::ValueWithUnit(expr, _) => expr.has_in_variable(working_set),
Expr::Var(var_id) => *var_id == IN_VARIABLE_ID,
Expr::VarDecl(_) => false,
Expr::Spread(expr) => expr.has_in_variable(working_set),
}
}
@ -394,8 +386,9 @@ impl Expression {
Expr::Int(_) => {}
Expr::Keyword(_, _, expr) => expr.replace_span(working_set, replaced, new_span),
Expr::List(list) => {
for l in list {
l.replace_span(working_set, replaced, new_span)
for item in list {
item.expr_mut()
.replace_span(working_set, replaced, new_span);
}
}
Expr::Operator(_) => {}
@ -456,7 +449,6 @@ impl Expression {
Expr::ValueWithUnit(expr, _) => expr.replace_span(working_set, replaced, new_span),
Expr::Var(_) => {}
Expr::VarDecl(_) => {}
Expr::Spread(expr) => expr.replace_span(working_set, replaced, new_span),
}
}
}