Implement table values
This commit is contained in:
parent
7f049f86c5
commit
834b6743eb
@ -4,7 +4,7 @@ use serde::{Deserialize, Serialize};
|
||||
use tree_sitter::Node;
|
||||
|
||||
use crate::{
|
||||
AbstractTree, Error, Expression, Function, Identifier, Item, Result, Value, ValueType,
|
||||
AbstractTree, Error, Expression, Function, Identifier, Item, Result, Table, Value, ValueType,
|
||||
VariableMap,
|
||||
};
|
||||
|
||||
@ -54,7 +54,28 @@ impl AbstractTree for ValueNode {
|
||||
|
||||
ValueType::ListExact(child_nodes)
|
||||
}
|
||||
"table" => ValueType::Table,
|
||||
"table" => {
|
||||
let child_count = child.child_count();
|
||||
let mut column_names = Vec::new();
|
||||
|
||||
let expression_node = child.child(child_count - 1).unwrap();
|
||||
let expression = Expression::from_syntax_node(source, expression_node)?;
|
||||
|
||||
for index in 2..child.child_count() - 2 {
|
||||
let node = child.child(index).unwrap();
|
||||
|
||||
if node.is_named() {
|
||||
let identifier = Identifier::from_syntax_node(source, node)?;
|
||||
|
||||
column_names.push(identifier)
|
||||
}
|
||||
}
|
||||
|
||||
ValueType::Table {
|
||||
column_names,
|
||||
rows: Box::new(expression),
|
||||
}
|
||||
}
|
||||
"map" => {
|
||||
let mut child_nodes = BTreeMap::new();
|
||||
let mut current_key = "".to_string();
|
||||
@ -150,7 +171,32 @@ impl AbstractTree for ValueNode {
|
||||
|
||||
Value::Map(values)
|
||||
}
|
||||
ValueType::Table => todo!(),
|
||||
ValueType::Table {
|
||||
column_names,
|
||||
rows: row_expression,
|
||||
} => {
|
||||
let mut headers = Vec::with_capacity(column_names.len());
|
||||
let mut rows = Vec::new();
|
||||
|
||||
for identifier in column_names {
|
||||
let name = identifier.inner().clone();
|
||||
|
||||
headers.push(name)
|
||||
}
|
||||
|
||||
let _row_values = row_expression.run(source, context)?;
|
||||
let row_values = _row_values.as_list()?;
|
||||
|
||||
for value in row_values {
|
||||
let row = value.as_list()?.clone();
|
||||
|
||||
rows.push(row)
|
||||
}
|
||||
|
||||
let table = Table::from_raw_parts(headers, rows);
|
||||
|
||||
Value::Table(table)
|
||||
}
|
||||
ValueType::Function(function) => Value::Function(function.clone()),
|
||||
};
|
||||
|
||||
|
@ -175,11 +175,11 @@ mod tests {
|
||||
assert_eq!(
|
||||
evaluate(
|
||||
"
|
||||
table <messages, numbers> {
|
||||
table <messages, numbers> [
|
||||
['hiya', 42]
|
||||
['foo', 57]
|
||||
['bar', 99.99]
|
||||
}
|
||||
]
|
||||
"
|
||||
),
|
||||
Ok(Value::Table(table))
|
||||
|
@ -5,7 +5,7 @@ use std::{
|
||||
|
||||
use serde::{Deserialize, Serialize};
|
||||
|
||||
use crate::{value_node::ValueNode, Expression, Function, Value};
|
||||
use crate::{value_node::ValueNode, Expression, Function, Identifier, Value};
|
||||
|
||||
/// The type of a `Value`.
|
||||
#[derive(Clone, Serialize, Deserialize, PartialOrd, Ord)]
|
||||
@ -18,7 +18,10 @@ pub enum ValueType {
|
||||
ListExact(Vec<Expression>),
|
||||
Empty,
|
||||
Map(BTreeMap<String, Expression>),
|
||||
Table,
|
||||
Table {
|
||||
column_names: Vec<Identifier>,
|
||||
rows: Box<Expression>,
|
||||
},
|
||||
Function(Function),
|
||||
}
|
||||
|
||||
@ -36,7 +39,16 @@ impl PartialEq for ValueType {
|
||||
(ValueType::ListExact(left), ValueType::ListExact(right)) => left == right,
|
||||
(ValueType::Empty, ValueType::Empty) => true,
|
||||
(ValueType::Map(left), ValueType::Map(right)) => left == right,
|
||||
(ValueType::Table, ValueType::Table) => true,
|
||||
(
|
||||
ValueType::Table {
|
||||
column_names: left_columns,
|
||||
rows: left_rows,
|
||||
},
|
||||
ValueType::Table {
|
||||
column_names: right_columns,
|
||||
rows: right_rows,
|
||||
},
|
||||
) => left_columns == right_columns && left_rows == right_rows,
|
||||
(ValueType::Function(left), ValueType::Function(right)) => left == right,
|
||||
_ => false,
|
||||
}
|
||||
@ -65,7 +77,9 @@ impl Display for ValueType {
|
||||
}
|
||||
ValueType::Empty => write!(f, "empty"),
|
||||
ValueType::Map(_map) => write!(f, "map"),
|
||||
ValueType::Table => write!(f, "table"),
|
||||
ValueType::Table { column_names, rows } => {
|
||||
write!(f, "table")
|
||||
}
|
||||
ValueType::Function(function) => write!(f, "{function}"),
|
||||
}
|
||||
}
|
||||
@ -106,7 +120,10 @@ impl From<&Value> for ValueType {
|
||||
|
||||
ValueType::Map(value_nodes)
|
||||
}
|
||||
Value::Table(_) => ValueType::Table,
|
||||
Value::Table(table) => ValueType::Table {
|
||||
column_names: todo!(),
|
||||
rows: todo!(),
|
||||
},
|
||||
Value::Function(function) => ValueType::Function(function.clone()),
|
||||
}
|
||||
}
|
||||
|
@ -2,9 +2,9 @@
|
||||
Table Declaration
|
||||
==================
|
||||
|
||||
table <text, number> {
|
||||
table <text, number> [
|
||||
['answer', 42]
|
||||
}
|
||||
]
|
||||
|
||||
---
|
||||
|
||||
@ -17,6 +17,9 @@ table <text, number> {
|
||||
(identifier)
|
||||
(identifier)
|
||||
(expression
|
||||
(value
|
||||
(list
|
||||
(expression
|
||||
(value
|
||||
(list
|
||||
(expression
|
||||
@ -24,15 +27,14 @@ table <text, number> {
|
||||
(string)))
|
||||
(expression
|
||||
(value
|
||||
(integer))))))))))))
|
||||
|
||||
(integer)))))))))))))))
|
||||
==================
|
||||
Table Assignment
|
||||
==================
|
||||
|
||||
foobar = table <text, number> {
|
||||
foobar = table <text, number> [
|
||||
['answer', 42]
|
||||
}
|
||||
]
|
||||
|
||||
---
|
||||
|
||||
@ -49,6 +51,9 @@ foobar = table <text, number> {
|
||||
(identifier)
|
||||
(identifier)
|
||||
(expression
|
||||
(value
|
||||
(list
|
||||
(expression
|
||||
(value
|
||||
(list
|
||||
(expression
|
||||
@ -56,7 +61,7 @@ foobar = table <text, number> {
|
||||
(string)))
|
||||
(expression
|
||||
(value
|
||||
(integer))))))))))))))
|
||||
(integer)))))))))))))))))
|
||||
|
||||
==================
|
||||
Table Access
|
||||
|
@ -76,13 +76,11 @@ module.exports = grammar({
|
||||
'}',
|
||||
),
|
||||
|
||||
table: $ => seq(
|
||||
table: $ => prec.right(seq(
|
||||
'table',
|
||||
seq('<', repeat1(seq($.identifier, optional(','))), '>'),
|
||||
'{',
|
||||
repeat($.expression),
|
||||
'}',
|
||||
),
|
||||
$.expression,
|
||||
)),
|
||||
|
||||
map: $ => seq(
|
||||
'{',
|
||||
|
@ -307,6 +307,9 @@
|
||||
]
|
||||
},
|
||||
"table": {
|
||||
"type": "PREC_RIGHT",
|
||||
"value": 0,
|
||||
"content": {
|
||||
"type": "SEQ",
|
||||
"members": [
|
||||
{
|
||||
@ -351,21 +354,11 @@
|
||||
]
|
||||
},
|
||||
{
|
||||
"type": "STRING",
|
||||
"value": "{"
|
||||
},
|
||||
{
|
||||
"type": "REPEAT",
|
||||
"content": {
|
||||
"type": "SYMBOL",
|
||||
"name": "expression"
|
||||
}
|
||||
},
|
||||
{
|
||||
"type": "STRING",
|
||||
"value": "}"
|
||||
}
|
||||
]
|
||||
}
|
||||
},
|
||||
"map": {
|
||||
"type": "SEQ",
|
||||
|
File diff suppressed because it is too large
Load Diff
Loading…
Reference in New Issue
Block a user