Continue passing tests

This commit is contained in:
Jeff 2024-08-14 19:43:12 -04:00
parent 441df54a44
commit f4ee3ffcf8
2 changed files with 274 additions and 13 deletions

View File

@ -16,6 +16,13 @@ pub enum Expression {
}
impl Expression {
pub fn range(range: Range, position: Span) -> Self {
Expression::WithoutBlock(Node::new(
Box::new(ExpressionWithoutBlock::Range(range)),
position,
))
}
pub fn call(call_expression: CallExpression, position: Span) -> Self {
Expression::WithoutBlock(Node::new(
Box::new(ExpressionWithoutBlock::Call(call_expression)),
@ -160,6 +167,7 @@ pub enum ExpressionWithoutBlock {
Grouped(Expression),
FieldAccess(FieldAccess),
ListIndex(ListIndex),
Range(Range),
}
impl Display for ExpressionWithoutBlock {
@ -174,10 +182,23 @@ impl Display for ExpressionWithoutBlock {
ExpressionWithoutBlock::Grouped(expression) => write!(f, "({})", expression),
ExpressionWithoutBlock::FieldAccess(field_access) => write!(f, "{}", field_access),
ExpressionWithoutBlock::ListIndex(list_index) => write!(f, "{}", list_index),
ExpressionWithoutBlock::Range(range) => write!(f, "{}", range),
}
}
}
#[derive(Debug, Clone, Eq, PartialEq, PartialOrd, Ord, Serialize, Deserialize)]
pub struct Range {
pub start: Expression,
pub end: Expression,
}
impl Display for Range {
fn fmt(&self, f: &mut Formatter) -> fmt::Result {
write!(f, "{}..{}", self.start, self.end)
}
}
#[derive(Debug, Clone, Eq, PartialEq, PartialOrd, Ord, Serialize, Deserialize)]
pub struct ListIndex {
pub list: Expression,

View File

@ -1023,96 +1023,336 @@ mod tests {
fn tuple_struct_access() {
let source = "(Foo(42, 'bar')).0";
assert_eq!(parse(source), todo!());
assert_eq!(
parse(source),
Ok(AbstractSyntaxTree::with_statements([
Statement::Expression(Expression::field_access(
FieldAccess {
container: Expression::r#struct(
StructExpression::Tuple {
name: Node::new(Identifier::new("Foo"), (0, 0)),
items: vec![
Expression::literal(LiteralExpression::Integer(42), (0, 0)),
Expression::literal(
LiteralExpression::String("bar".to_string()),
(0, 0)
),
],
},
(0, 0)
),
field: Node::new(Identifier::new("0"), (0, 0)),
},
(0, 0)
))
]))
);
}
#[test]
fn fields_struct_instantiation() {
let source = "Foo { a = 42, b = 4.0 }";
assert_eq!(parse(source), todo!());
assert_eq!(
parse(source),
Ok(AbstractSyntaxTree::with_statements([
Statement::Expression(Expression::r#struct(
StructExpression::Fields {
name: Node::new(Identifier::new("Foo"), (0, 0)),
fields: vec![
(
Node::new(Identifier::new("a"), (0, 0)),
Expression::literal(LiteralExpression::Integer(42), (0, 0)),
),
(
Node::new(Identifier::new("b"), (0, 0)),
Expression::literal(LiteralExpression::Float(4.0), (0, 0))
)
]
},
(0, 0)
))
]))
);
}
#[test]
fn fields_struct() {
let source = "struct Foo { a: int, b: float }";
assert_eq!(parse(source), todo!());
assert_eq!(
parse(source),
Ok(AbstractSyntaxTree::with_statements([
Statement::struct_definition(
StructDefinition::Fields {
name: Node::new(Identifier::new("Foo"), (0, 0)),
fields: vec![
(
Node::new(Identifier::new("a"), (0, 0)),
Node::new(Type::Integer, (0, 0))
),
(
Node::new(Identifier::new("b"), (0, 0)),
Node::new(Type::Float, (0, 0))
)
]
},
(0, 0)
)
]))
);
}
#[test]
fn tuple_struct_instantiation() {
let source = "struct Foo(int, float) Foo(1, 2.0)";
assert_eq!(parse(source), todo!());
assert_eq!(
parse(source),
Ok(AbstractSyntaxTree::with_statements([
Statement::struct_definition(
StructDefinition::Tuple {
name: Node::new(Identifier::new("Foo"), (0, 0)),
items: vec![
Node::new(Type::Integer, (0, 0)),
Node::new(Type::Float, (0, 0)),
]
},
(0, 0)
),
Statement::Expression(Expression::r#struct(
StructExpression::Tuple {
name: Node::new(Identifier::new("Foo"), (0, 0)),
items: vec![
Expression::literal(LiteralExpression::Integer(1), (0, 0)),
Expression::literal(LiteralExpression::Float(2.0), (0, 0))
]
},
(0, 0)
))
]))
);
}
#[test]
fn tuple_struct() {
let source = "struct Foo(int, float)";
assert_eq!(parse(source), todo!());
assert_eq!(
parse(source),
Ok(AbstractSyntaxTree::with_statements([
Statement::StructDefinition(Node::new(
StructDefinition::Tuple {
name: Node::new(Identifier::new("Foo"), (0, 0)),
items: vec![
Node::new(Type::Integer, (0, 0)),
Node::new(Type::Float, (0, 0)),
],
},
(0, 0)
))
]))
);
}
#[test]
fn unit_struct() {
let source = "struct Foo";
assert_eq!(parse(source), todo!());
assert_eq!(
parse(source),
Ok(AbstractSyntaxTree::with_statements([
Statement::StructDefinition(Node::new(
StructDefinition::Unit {
name: Node::new(Identifier::new("Foo"), (0, 0)),
},
(0, 0)
))
]))
);
}
#[test]
fn list_index_nested() {
let source = "[1, [2], 3][1][0]";
assert_eq!(parse(source), todo!());
assert_eq!(
parse(source),
Ok(AbstractSyntaxTree::with_statements([
Statement::Expression(Expression::list_index(
ListIndex {
list: Expression::list_index(
ListIndex {
list: Expression::list(
ListExpression::Ordered(vec![
Expression::literal(LiteralExpression::Integer(1), (0, 0)),
Expression::list(
ListExpression::Ordered(vec![Expression::literal(
LiteralExpression::Integer(2),
(0, 0)
)]),
(0, 0)
),
Expression::literal(LiteralExpression::Integer(3), (0, 0)),
]),
(0, 0)
),
index: Expression::literal(LiteralExpression::Integer(1), (0, 0)),
},
(0, 0)
),
index: Expression::literal(LiteralExpression::Integer(0), (0, 0)),
},
(0, 0)
))
]))
);
}
#[test]
fn map_property_nested() {
let source = "{ x = { y = 42 } }.x.y";
assert_eq!(parse(source), todo!());
}
#[test]
fn range() {
let source = "0..42";
assert_eq!(parse(source), todo!());
assert_eq!(
parse(source),
Ok(AbstractSyntaxTree::with_statements([
Statement::Expression(Expression::range(
Range {
start: Expression::literal(LiteralExpression::Integer(0), (0, 0)),
end: Expression::literal(LiteralExpression::Integer(42), (0, 0)),
},
(0, 0)
))
]))
);
}
#[test]
fn negate_variable() {
let source = "a = 1; -a";
assert_eq!(parse(source), todo!());
assert_eq!(
parse(source),
Ok(AbstractSyntaxTree::with_statements([
Statement::Expression(Expression::operator(
OperatorExpression::Assignment {
assignee: Expression::identifier(Identifier::new("a"), (0, 0)),
value: Expression::literal(LiteralExpression::Integer(1), (0, 0)),
},
(0, 0)
)),
Statement::Expression(Expression::operator(
OperatorExpression::Negation(Expression::identifier(
Identifier::new("a"),
(0, 0)
)),
(0, 0)
))
]))
);
}
#[test]
fn negate_expression() {
let source = "-(1 + 1)";
assert_eq!(parse(source), todo!());
assert_eq!(
parse(source),
Ok(AbstractSyntaxTree::with_statements([
Statement::Expression(Expression::operator(
OperatorExpression::Negation(Expression::grouped(
Expression::operator(
OperatorExpression::Math {
left: Expression::literal(LiteralExpression::Integer(1), (0, 0)),
operator: Node::new(MathOperator::Add, (0, 0)),
right: Expression::literal(LiteralExpression::Integer(1), (0, 0)),
},
(0, 0)
),
(0, 0)
)),
(0, 0)
))
]))
);
}
#[test]
fn not_expression() {
let source = "!(1 > 42)";
assert_eq!(parse(source), todo!());
assert_eq!(
parse(source),
Ok(AbstractSyntaxTree::with_statements([
Statement::Expression(Expression::operator(
OperatorExpression::Not(Expression::grouped(
Expression::operator(
OperatorExpression::Comparison {
left: Expression::literal(LiteralExpression::Integer(1), (0, 0)),
operator: Node::new(ComparisonOperator::GreaterThan, (0, 0)),
right: Expression::literal(LiteralExpression::Integer(42), (0, 0)),
},
(0, 0)
),
(0, 0)
)),
(0, 0)
))
]))
);
}
#[test]
fn not_variable() {
let source = "a = false; !a";
assert_eq!(parse(source), todo!());
assert_eq!(
parse(source),
Ok(AbstractSyntaxTree::with_statements([
Statement::Expression(Expression::operator(
OperatorExpression::Assignment {
assignee: Expression::identifier(Identifier::new("a"), (0, 0)),
value: Expression::literal(LiteralExpression::Boolean(false), (0, 0)),
},
(0, 0)
)),
Statement::Expression(Expression::operator(
OperatorExpression::Not(Expression::identifier(Identifier::new("a"), (0, 0))),
(0, 0)
)),
]))
);
}
#[test]
fn r#if() {
let source = "if x { y }";
assert_eq!(parse(source), todo!());
assert_eq!(
parse(source),
Ok(AbstractSyntaxTree::with_statements([
Statement::Expression(Expression::r#if(
If::If {
condition: Expression::identifier(Identifier::new("x"), (3, 4)),
if_block: Node::new(
Block::Sync(vec![Statement::Expression(Expression::identifier(
Identifier::new("y"),
(7, 8)
))]),
(5, 10)
)
},
(0, 10)
))
]))
);
}
#[test]