Update error variants
This commit is contained in:
parent
f20f69afa4
commit
c6675e87ba
@ -34,7 +34,8 @@ impl AbstractTree for FunctionCall {
|
|||||||
"assert_equal" => Tool::AssertEqual,
|
"assert_equal" => Tool::AssertEqual,
|
||||||
"output" => Tool::Output,
|
"output" => Tool::Output,
|
||||||
"read" => Tool::Read,
|
"read" => Tool::Read,
|
||||||
_ => panic!(""),
|
"help" => Tool::Help,
|
||||||
|
_ => panic!("Tool name not recognized."),
|
||||||
};
|
};
|
||||||
|
|
||||||
FunctionName::Tool(tool)
|
FunctionName::Tool(tool)
|
||||||
|
@ -2,7 +2,7 @@ use std::fs::read_to_string;
|
|||||||
|
|
||||||
use serde::{Deserialize, Serialize};
|
use serde::{Deserialize, Serialize};
|
||||||
|
|
||||||
use crate::{Error, Result, Value};
|
use crate::{Error, Result, Table, Value};
|
||||||
|
|
||||||
#[derive(Debug, Clone, Serialize, Deserialize, Eq, PartialEq, PartialOrd, Ord)]
|
#[derive(Debug, Clone, Serialize, Deserialize, Eq, PartialEq, PartialOrd, Ord)]
|
||||||
pub enum Tool {
|
pub enum Tool {
|
||||||
@ -10,6 +10,7 @@ pub enum Tool {
|
|||||||
AssertEqual,
|
AssertEqual,
|
||||||
Output,
|
Output,
|
||||||
Read,
|
Read,
|
||||||
|
Help,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Tool {
|
impl Tool {
|
||||||
@ -27,10 +28,7 @@ impl Tool {
|
|||||||
if values[0].as_boolean()? {
|
if values[0].as_boolean()? {
|
||||||
Value::Empty
|
Value::Empty
|
||||||
} else {
|
} else {
|
||||||
return Err(Error::AssertEqualFailed {
|
return Err(Error::AssertFailed);
|
||||||
expected: Value::Boolean(true),
|
|
||||||
actual: values[0].clone(),
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Tool::AssertEqual => {
|
Tool::AssertEqual => {
|
||||||
@ -77,6 +75,41 @@ impl Tool {
|
|||||||
|
|
||||||
Value::String(file_contents)
|
Value::String(file_contents)
|
||||||
}
|
}
|
||||||
|
Tool::Help => {
|
||||||
|
if values.len() > 1 {
|
||||||
|
return Err(Error::ExpectedToolArgumentAmount {
|
||||||
|
tool_name: "help",
|
||||||
|
expected: 1,
|
||||||
|
actual: values.len(),
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
let mut help_table =
|
||||||
|
Table::new(vec!["name".to_string(), "description".to_string()]);
|
||||||
|
|
||||||
|
help_table.insert(vec![
|
||||||
|
Value::String("help".to_string()),
|
||||||
|
Value::String("List available tools.".to_string()),
|
||||||
|
])?;
|
||||||
|
help_table.insert(vec![
|
||||||
|
Value::String("assert".to_string()),
|
||||||
|
Value::String("Panic if an expression is false.".to_string()),
|
||||||
|
])?;
|
||||||
|
help_table.insert(vec![
|
||||||
|
Value::String("assert_equal".to_string()),
|
||||||
|
Value::String("Panic if two values are not equal.".to_string()),
|
||||||
|
])?;
|
||||||
|
help_table.insert(vec![
|
||||||
|
Value::String("output".to_string()),
|
||||||
|
Value::String("Emit a value to stdout.".to_string()),
|
||||||
|
])?;
|
||||||
|
help_table.insert(vec![
|
||||||
|
Value::String("read".to_string()),
|
||||||
|
Value::String("Get a file's content.".to_string()),
|
||||||
|
])?;
|
||||||
|
|
||||||
|
Value::Table(help_table)
|
||||||
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
Ok(value)
|
Ok(value)
|
||||||
|
273
src/error.rs
273
src/error.rs
@ -3,14 +3,13 @@
|
|||||||
//! To deal with errors from dependencies, either create a new error variant
|
//! To deal with errors from dependencies, either create a new error variant
|
||||||
//! or use the MacroFailure variant if the error can only occur inside a macro.
|
//! or use the MacroFailure variant if the error can only occur inside a macro.
|
||||||
|
|
||||||
use crate::{value::value_type::ValueType, value::Value, Identifier};
|
use crate::{value::Value, Identifier};
|
||||||
|
|
||||||
use std::{fmt, io, time::SystemTimeError};
|
use std::{fmt, io, time::SystemTimeError};
|
||||||
|
|
||||||
pub type Result<T> = std::result::Result<T, Error>;
|
pub type Result<T> = std::result::Result<T, Error>;
|
||||||
|
|
||||||
#[derive(Clone, PartialEq)]
|
#[derive(Clone, PartialEq)]
|
||||||
#[non_exhaustive]
|
|
||||||
pub enum Error {
|
pub enum Error {
|
||||||
UnexpectedSyntaxNode {
|
UnexpectedSyntaxNode {
|
||||||
expected: &'static str,
|
expected: &'static str,
|
||||||
@ -19,8 +18,6 @@ pub enum Error {
|
|||||||
relevant_source: String,
|
relevant_source: String,
|
||||||
},
|
},
|
||||||
|
|
||||||
ExpectedFieldName,
|
|
||||||
|
|
||||||
ExpectedChildNode {
|
ExpectedChildNode {
|
||||||
empty_node_sexp: String,
|
empty_node_sexp: String,
|
||||||
},
|
},
|
||||||
@ -116,113 +113,14 @@ pub enum Error {
|
|||||||
actual: Value,
|
actual: Value,
|
||||||
},
|
},
|
||||||
|
|
||||||
/// Tried to append a child to a node such that the precedence of the child
|
|
||||||
/// is not higher. This error should never occur. If it does, please file a
|
|
||||||
/// bug report.
|
|
||||||
PrecedenceViolation,
|
|
||||||
|
|
||||||
/// A `VariableIdentifier` operation did not find its value in the context.
|
/// A `VariableIdentifier` operation did not find its value in the context.
|
||||||
VariableIdentifierNotFound(String),
|
VariableIdentifierNotFound(String),
|
||||||
|
|
||||||
/// A `FunctionIdentifier` operation did not find its value in the context.
|
/// A `FunctionIdentifier` operation did not find its value in the context.
|
||||||
FunctionIdentifierNotFound(Identifier),
|
FunctionIdentifierNotFound(Identifier),
|
||||||
|
|
||||||
/// A value has the wrong type.
|
|
||||||
/// Only use this if there is no other error that describes the expected and
|
|
||||||
/// provided types in more detail.
|
|
||||||
TypeError {
|
|
||||||
/// The expected types.
|
|
||||||
expected: &'static [ValueType],
|
|
||||||
/// The actual value.
|
|
||||||
actual: Value,
|
|
||||||
},
|
|
||||||
|
|
||||||
/// An operator is used with a wrong combination of types.
|
|
||||||
WrongTypeCombination {
|
|
||||||
/// The operator that whose evaluation caused the error.
|
|
||||||
expected: ValueType,
|
|
||||||
/// The types that were used in the operator causing it to fail.
|
|
||||||
actual: ValueType,
|
|
||||||
},
|
|
||||||
|
|
||||||
/// An opening brace without a matching closing brace was found.
|
|
||||||
UnmatchedLBrace,
|
|
||||||
|
|
||||||
/// A closing brace without a matching opening brace was found.
|
|
||||||
UnmatchedRBrace,
|
|
||||||
|
|
||||||
/// Left of an opening brace or right of a closing brace is a token that does not expect the brace next to it.
|
|
||||||
/// For example, writing `4(5)` would yield this error, as the `4` does not have any operands.
|
|
||||||
MissingOperatorOutsideOfBrace,
|
|
||||||
|
|
||||||
/// An addition operation performed by Rust failed.
|
|
||||||
AdditionError {
|
|
||||||
/// The first argument of the addition.
|
|
||||||
augend: Value,
|
|
||||||
/// The second argument of the addition.
|
|
||||||
addend: Value,
|
|
||||||
},
|
|
||||||
|
|
||||||
/// A subtraction operation performed by Rust failed.
|
|
||||||
SubtractionError {
|
|
||||||
/// The first argument of the subtraction.
|
|
||||||
minuend: Value,
|
|
||||||
/// The second argument of the subtraction.
|
|
||||||
subtrahend: Value,
|
|
||||||
},
|
|
||||||
|
|
||||||
/// A negation operation performed by Rust failed.
|
|
||||||
NegationError {
|
|
||||||
/// The argument of the negation.
|
|
||||||
argument: Value,
|
|
||||||
},
|
|
||||||
|
|
||||||
/// A multiplication operation performed by Rust failed.
|
|
||||||
MultiplicationError {
|
|
||||||
/// The first argument of the multiplication.
|
|
||||||
multiplicand: Value,
|
|
||||||
/// The second argument of the multiplication.
|
|
||||||
multiplier: Value,
|
|
||||||
},
|
|
||||||
|
|
||||||
/// A division operation performed by Rust failed.
|
|
||||||
DivisionError {
|
|
||||||
/// The first argument of the division.
|
|
||||||
dividend: Value,
|
|
||||||
/// The second argument of the division.
|
|
||||||
divisor: Value,
|
|
||||||
},
|
|
||||||
|
|
||||||
/// A modulation operation performed by Rust failed.
|
|
||||||
ModulationError {
|
|
||||||
/// The first argument of the modulation.
|
|
||||||
dividend: Value,
|
|
||||||
/// The second argument of the modulation.
|
|
||||||
divisor: Value,
|
|
||||||
},
|
|
||||||
|
|
||||||
/// A regular expression could not be parsed
|
|
||||||
InvalidRegex {
|
|
||||||
/// The invalid regular expression
|
|
||||||
regex: String,
|
|
||||||
/// Failure message from the regex engine
|
|
||||||
message: String,
|
|
||||||
},
|
|
||||||
|
|
||||||
/// A modification was attempted on a `Context` that does not allow modifications.
|
|
||||||
ContextNotMutable,
|
|
||||||
|
|
||||||
/// An escape sequence within a string literal is illegal.
|
|
||||||
IllegalEscapeSequence(String),
|
|
||||||
|
|
||||||
/// This context does not allow enabling builtin functions.
|
|
||||||
BuiltinFunctionsCannotBeEnabled,
|
|
||||||
|
|
||||||
/// This context does not allow disabling builtin functions.
|
|
||||||
BuiltinFunctionsCannotBeDisabled,
|
|
||||||
|
|
||||||
/// The function failed due to an external error.
|
/// The function failed due to an external error.
|
||||||
MacroFailure(String),
|
ToolFailure(String),
|
||||||
|
|
||||||
/// A custom error explained by its message.
|
/// A custom error explained by its message.
|
||||||
CustomMessage(String),
|
CustomMessage(String),
|
||||||
@ -230,129 +128,55 @@ pub enum Error {
|
|||||||
|
|
||||||
impl From<csv::Error> for Error {
|
impl From<csv::Error> for Error {
|
||||||
fn from(value: csv::Error) -> Self {
|
fn from(value: csv::Error) -> Self {
|
||||||
Error::MacroFailure(value.to_string())
|
Error::ToolFailure(value.to_string())
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl From<json::Error> for Error {
|
impl From<json::Error> for Error {
|
||||||
fn from(value: json::Error) -> Self {
|
fn from(value: json::Error) -> Self {
|
||||||
Error::MacroFailure(value.to_string())
|
Error::ToolFailure(value.to_string())
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl From<io::Error> for Error {
|
impl From<io::Error> for Error {
|
||||||
fn from(value: std::io::Error) -> Self {
|
fn from(value: std::io::Error) -> Self {
|
||||||
Error::MacroFailure(value.to_string())
|
Error::ToolFailure(value.to_string())
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl From<git2::Error> for Error {
|
impl From<git2::Error> for Error {
|
||||||
fn from(value: git2::Error) -> Self {
|
fn from(value: git2::Error) -> Self {
|
||||||
Error::MacroFailure(value.to_string())
|
Error::ToolFailure(value.to_string())
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl From<reqwest::Error> for Error {
|
impl From<reqwest::Error> for Error {
|
||||||
fn from(value: reqwest::Error) -> Self {
|
fn from(value: reqwest::Error) -> Self {
|
||||||
Error::MacroFailure(value.to_string())
|
Error::ToolFailure(value.to_string())
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl From<serde_json::Error> for Error {
|
impl From<serde_json::Error> for Error {
|
||||||
fn from(value: serde_json::Error) -> Self {
|
fn from(value: serde_json::Error) -> Self {
|
||||||
Error::MacroFailure(value.to_string())
|
Error::ToolFailure(value.to_string())
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl From<SystemTimeError> for Error {
|
impl From<SystemTimeError> for Error {
|
||||||
fn from(value: SystemTimeError) -> Self {
|
fn from(value: SystemTimeError) -> Self {
|
||||||
Error::MacroFailure(value.to_string())
|
Error::ToolFailure(value.to_string())
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl From<trash::Error> for Error {
|
impl From<trash::Error> for Error {
|
||||||
fn from(value: trash::Error) -> Self {
|
fn from(value: trash::Error) -> Self {
|
||||||
Error::MacroFailure(value.to_string())
|
Error::ToolFailure(value.to_string())
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl From<toml::de::Error> for Error {
|
impl From<toml::de::Error> for Error {
|
||||||
fn from(value: toml::de::Error) -> Self {
|
fn from(value: toml::de::Error) -> Self {
|
||||||
Error::MacroFailure(value.to_string())
|
Error::ToolFailure(value.to_string())
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl Error {
|
|
||||||
pub fn type_error(actual: Value, expected: &'static [ValueType]) -> Self {
|
|
||||||
Error::TypeError { actual, expected }
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn expected_string(actual: Value) -> Self {
|
|
||||||
Error::ExpectedString { actual }
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn expected_int(actual: Value) -> Self {
|
|
||||||
Error::ExpectedInt { actual }
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn expected_float(actual: Value) -> Self {
|
|
||||||
Error::ExpectedFloat { actual }
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn expected_number(actual: Value) -> Self {
|
|
||||||
Error::ExpectedNumber { actual }
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn expected_number_or_string(actual: Value) -> Self {
|
|
||||||
Error::ExpectedNumberOrString { actual }
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn expected_boolean(actual: Value) -> Self {
|
|
||||||
Error::ExpectedBoolean { actual }
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn expected_list(actual: Value) -> Self {
|
|
||||||
Error::ExpectedList { actual }
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn expected_fixed_len_list(expected_len: usize, actual: Value) -> Self {
|
|
||||||
Error::ExpectedFixedLenList {
|
|
||||||
expected_len,
|
|
||||||
actual,
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn expected_empty(actual: Value) -> Self {
|
|
||||||
Error::ExpectedEmpty { actual }
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn expected_map(actual: Value) -> Self {
|
|
||||||
Error::ExpectedMap { actual }
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn expected_table(actual: Value) -> Self {
|
|
||||||
Error::ExpectedTable { actual }
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn expected_function(actual: Value) -> Self {
|
|
||||||
Error::ExpectedFunction { actual }
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn expected_collection(actual: Value) -> Self {
|
|
||||||
Error::ExpectedCollection { actual }
|
|
||||||
}
|
|
||||||
|
|
||||||
/// Constructs `EvalexprError::InvalidRegex(regex)`
|
|
||||||
pub fn invalid_regex(regex: String, message: String) -> Self {
|
|
||||||
Error::InvalidRegex { regex, message }
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/// Returns `Ok(())` if the given value is a string or a numeric.
|
|
||||||
pub fn expect_number_or_string(actual: &Value) -> Result<()> {
|
|
||||||
match actual {
|
|
||||||
Value::String(_) | Value::Float(_) | Value::Integer(_) => Ok(()),
|
|
||||||
_ => Err(Error::expected_number_or_string(actual.clone())),
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -438,10 +262,6 @@ impl fmt::Display for Error {
|
|||||||
actual
|
actual
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
PrecedenceViolation => write!(
|
|
||||||
f,
|
|
||||||
"Tried to append a node to another node with higher precedence."
|
|
||||||
),
|
|
||||||
VariableIdentifierNotFound(identifier) => write!(
|
VariableIdentifierNotFound(identifier) => write!(
|
||||||
f,
|
f,
|
||||||
"Variable identifier is not bound to anything by context: {}.",
|
"Variable identifier is not bound to anything by context: {}.",
|
||||||
@ -452,75 +272,16 @@ impl fmt::Display for Error {
|
|||||||
"Function identifier is not bound to anything by context: {}.",
|
"Function identifier is not bound to anything by context: {}.",
|
||||||
identifier.inner()
|
identifier.inner()
|
||||||
),
|
),
|
||||||
TypeError { expected, actual } => {
|
|
||||||
write!(
|
|
||||||
f,
|
|
||||||
"Type Error. The value {actual} is not one of the following: {expected:?}.",
|
|
||||||
)
|
|
||||||
}
|
|
||||||
UnmatchedLBrace => write!(f, "Found an unmatched opening parenthesis '('."),
|
|
||||||
UnmatchedRBrace => write!(f, "Found an unmatched closing parenthesis ')'."),
|
|
||||||
MissingOperatorOutsideOfBrace { .. } => write!(
|
|
||||||
f,
|
|
||||||
"Found an opening parenthesis that is preceded by something that does not take \
|
|
||||||
any arguments on the right, or found a closing parenthesis that is succeeded by \
|
|
||||||
something that does not take any arguments on the left."
|
|
||||||
),
|
|
||||||
AdditionError { augend, addend } => write!(f, "Error adding {} + {}", augend, addend),
|
|
||||||
SubtractionError {
|
|
||||||
minuend,
|
|
||||||
subtrahend,
|
|
||||||
} => write!(f, "Error subtracting {} - {}", minuend, subtrahend),
|
|
||||||
NegationError { argument } => write!(f, "Error negating -{}", argument),
|
|
||||||
MultiplicationError {
|
|
||||||
multiplicand,
|
|
||||||
multiplier,
|
|
||||||
} => write!(f, "Error multiplying {} * {}", multiplicand, multiplier),
|
|
||||||
DivisionError { dividend, divisor } => {
|
|
||||||
write!(f, "Error dividing {} / {}", dividend, divisor)
|
|
||||||
}
|
|
||||||
ModulationError { dividend, divisor } => {
|
|
||||||
write!(f, "Error modulating {} % {}", dividend, divisor)
|
|
||||||
}
|
|
||||||
InvalidRegex { regex, message } => write!(
|
|
||||||
f,
|
|
||||||
"Regular expression {:?} is invalid: {:?}",
|
|
||||||
regex, message
|
|
||||||
),
|
|
||||||
ContextNotMutable => write!(f, "Cannot manipulate context"),
|
|
||||||
BuiltinFunctionsCannotBeEnabled => {
|
|
||||||
write!(f, "This context does not allow enabling builtin functions")
|
|
||||||
}
|
|
||||||
BuiltinFunctionsCannotBeDisabled => {
|
|
||||||
write!(f, "This context does not allow disabling builtin functions")
|
|
||||||
}
|
|
||||||
IllegalEscapeSequence(string) => write!(f, "Illegal escape sequence: {}", string),
|
|
||||||
MacroFailure(message) => write!(f, "Function failure: {}", message),
|
|
||||||
CustomMessage(message) => write!(f, "Error: {}", message),
|
|
||||||
WrongColumnAmount { expected, actual } => write!(
|
|
||||||
f,
|
|
||||||
"Wrong number of columns for this table. Expected {expected}, found {actual}."
|
|
||||||
),
|
|
||||||
UnexpectedSyntaxNode {
|
UnexpectedSyntaxNode {
|
||||||
expected,
|
expected,
|
||||||
actual,
|
actual,
|
||||||
location,
|
location,
|
||||||
relevant_source
|
relevant_source,
|
||||||
} => write!(
|
} => todo!(),
|
||||||
f,
|
ExpectedChildNode { empty_node_sexp } => todo!(),
|
||||||
"Unexpected syntax at {location}. Expected {expected}, but found {actual}. {relevant_source}"
|
WrongColumnAmount { expected, actual } => todo!(),
|
||||||
),
|
ToolFailure(_) => todo!(),
|
||||||
ExpectedFieldName => write!(
|
CustomMessage(_) => todo!(),
|
||||||
f,
|
|
||||||
"Expected a field name for this node, but none was found."
|
|
||||||
),
|
|
||||||
WrongTypeCombination { expected, actual } => write!(
|
|
||||||
f,
|
|
||||||
"Wrong type combination. Expected {expected}, found {actual}."
|
|
||||||
),
|
|
||||||
ExpectedChildNode { empty_node_sexp } => {
|
|
||||||
write!(f, "Expected this node to have a child, {empty_node_sexp}.")
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -92,7 +92,9 @@ impl Value {
|
|||||||
pub fn as_string(&self) -> Result<&String> {
|
pub fn as_string(&self) -> Result<&String> {
|
||||||
match self {
|
match self {
|
||||||
Value::String(string) => Ok(string),
|
Value::String(string) => Ok(string),
|
||||||
value => Err(Error::expected_string(value.clone())),
|
value => Err(Error::ExpectedString {
|
||||||
|
actual: value.clone(),
|
||||||
|
}),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -100,7 +102,9 @@ impl Value {
|
|||||||
pub fn as_int(&self) -> Result<i64> {
|
pub fn as_int(&self) -> Result<i64> {
|
||||||
match self {
|
match self {
|
||||||
Value::Integer(i) => Ok(*i),
|
Value::Integer(i) => Ok(*i),
|
||||||
value => Err(Error::expected_int(value.clone())),
|
value => Err(Error::ExpectedInt {
|
||||||
|
actual: value.clone(),
|
||||||
|
}),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -108,7 +112,9 @@ impl Value {
|
|||||||
pub fn as_float(&self) -> Result<f64> {
|
pub fn as_float(&self) -> Result<f64> {
|
||||||
match self {
|
match self {
|
||||||
Value::Float(f) => Ok(*f),
|
Value::Float(f) => Ok(*f),
|
||||||
value => Err(Error::expected_float(value.clone())),
|
value => Err(Error::ExpectedFloat {
|
||||||
|
actual: value.clone(),
|
||||||
|
}),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -118,7 +124,9 @@ impl Value {
|
|||||||
match self {
|
match self {
|
||||||
Value::Float(f) => Ok(*f),
|
Value::Float(f) => Ok(*f),
|
||||||
Value::Integer(i) => Ok(*i as f64),
|
Value::Integer(i) => Ok(*i as f64),
|
||||||
value => Err(Error::expected_number(value.clone())),
|
value => Err(Error::ExpectedNumber {
|
||||||
|
actual: value.clone(),
|
||||||
|
}),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -126,7 +134,9 @@ impl Value {
|
|||||||
pub fn as_boolean(&self) -> Result<bool> {
|
pub fn as_boolean(&self) -> Result<bool> {
|
||||||
match self {
|
match self {
|
||||||
Value::Boolean(boolean) => Ok(*boolean),
|
Value::Boolean(boolean) => Ok(*boolean),
|
||||||
value => Err(Error::expected_boolean(value.clone())),
|
value => Err(Error::ExpectedBoolean {
|
||||||
|
actual: value.clone(),
|
||||||
|
}),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -134,7 +144,9 @@ impl Value {
|
|||||||
pub fn as_list(&self) -> Result<&Vec<Value>> {
|
pub fn as_list(&self) -> Result<&Vec<Value>> {
|
||||||
match self {
|
match self {
|
||||||
Value::List(list) => Ok(list),
|
Value::List(list) => Ok(list),
|
||||||
value => Err(Error::expected_list(value.clone())),
|
value => Err(Error::ExpectedList {
|
||||||
|
actual: value.clone(),
|
||||||
|
}),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -142,21 +154,9 @@ impl Value {
|
|||||||
pub fn into_inner_list(self) -> Result<Vec<Value>> {
|
pub fn into_inner_list(self) -> Result<Vec<Value>> {
|
||||||
match self {
|
match self {
|
||||||
Value::List(list) => Ok(list),
|
Value::List(list) => Ok(list),
|
||||||
value => Err(Error::expected_list(value.clone())),
|
value => Err(Error::ExpectedList {
|
||||||
}
|
actual: value.clone(),
|
||||||
}
|
}),
|
||||||
|
|
||||||
/// Borrows the value stored in `self` as `Vec<Value>` or returns `Err` if `self` is not a `Value::Map` of the required length.
|
|
||||||
pub fn as_fixed_len_list(&self, len: usize) -> Result<&Vec<Value>> {
|
|
||||||
match self {
|
|
||||||
Value::List(tuple) => {
|
|
||||||
if tuple.len() == len {
|
|
||||||
Ok(tuple)
|
|
||||||
} else {
|
|
||||||
Err(Error::expected_fixed_len_list(len, self.clone()))
|
|
||||||
}
|
|
||||||
}
|
|
||||||
value => Err(Error::expected_list(value.clone())),
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -164,7 +164,9 @@ impl Value {
|
|||||||
pub fn as_map(&self) -> Result<&VariableMap> {
|
pub fn as_map(&self) -> Result<&VariableMap> {
|
||||||
match self {
|
match self {
|
||||||
Value::Map(map) => Ok(map),
|
Value::Map(map) => Ok(map),
|
||||||
value => Err(Error::expected_map(value.clone())),
|
value => Err(Error::ExpectedMap {
|
||||||
|
actual: value.clone(),
|
||||||
|
}),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -172,7 +174,9 @@ impl Value {
|
|||||||
pub fn as_table(&self) -> Result<&Table> {
|
pub fn as_table(&self) -> Result<&Table> {
|
||||||
match self {
|
match self {
|
||||||
Value::Table(table) => Ok(table),
|
Value::Table(table) => Ok(table),
|
||||||
value => Err(Error::expected_table(value.clone())),
|
value => Err(Error::ExpectedTable {
|
||||||
|
actual: value.clone(),
|
||||||
|
}),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -181,7 +185,9 @@ impl Value {
|
|||||||
pub fn as_function(&self) -> Result<&Function> {
|
pub fn as_function(&self) -> Result<&Function> {
|
||||||
match self {
|
match self {
|
||||||
Value::Function(function) => Ok(function),
|
Value::Function(function) => Ok(function),
|
||||||
value => Err(Error::expected_function(value.clone())),
|
value => Err(Error::ExpectedFunction {
|
||||||
|
actual: value.clone(),
|
||||||
|
}),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -189,7 +195,9 @@ impl Value {
|
|||||||
pub fn as_empty(&self) -> Result<()> {
|
pub fn as_empty(&self) -> Result<()> {
|
||||||
match self {
|
match self {
|
||||||
Value::Empty => Ok(()),
|
Value::Empty => Ok(()),
|
||||||
value => Err(Error::expected_empty(value.clone())),
|
value => Err(Error::ExpectedEmpty {
|
||||||
|
actual: value.clone(),
|
||||||
|
}),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -199,7 +207,9 @@ impl Value {
|
|||||||
Value::Table(table) => Ok(table.clone()),
|
Value::Table(table) => Ok(table.clone()),
|
||||||
Value::List(list) => Ok(Table::from(list)),
|
Value::List(list) => Ok(Table::from(list)),
|
||||||
Value::Map(map) => Ok(Table::from(map)),
|
Value::Map(map) => Ok(Table::from(map)),
|
||||||
value => Err(Error::expected_table(value.clone())),
|
value => Err(Error::ExpectedTable {
|
||||||
|
actual: value.clone(),
|
||||||
|
}),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -41,9 +41,9 @@ impl VariableMap {
|
|||||||
let index = if let Ok(index) = next_identifier.parse::<usize>() {
|
let index = if let Ok(index) = next_identifier.parse::<usize>() {
|
||||||
index
|
index
|
||||||
} else {
|
} else {
|
||||||
return Err(Error::expected_int(Value::String(
|
return Err(Error::ExpectedInt {
|
||||||
next_identifier.to_string(),
|
actual: Value::String(next_identifier.to_string()),
|
||||||
)));
|
});
|
||||||
};
|
};
|
||||||
|
|
||||||
Ok(list.get(index).cloned())
|
Ok(list.get(index).cloned())
|
||||||
@ -70,9 +70,9 @@ impl VariableMap {
|
|||||||
let index = if let Ok(index) = next_identifier.parse::<usize>() {
|
let index = if let Ok(index) = next_identifier.parse::<usize>() {
|
||||||
index
|
index
|
||||||
} else {
|
} else {
|
||||||
return Err(Error::expected_int(Value::String(
|
return Err(Error::ExpectedInt {
|
||||||
next_identifier.to_string(),
|
actual: Value::String(next_identifier.to_string()),
|
||||||
)));
|
});
|
||||||
};
|
};
|
||||||
|
|
||||||
let mut missing_elements = index.saturating_sub(list.len()) + 1;
|
let mut missing_elements = index.saturating_sub(list.len()) + 1;
|
||||||
|
Loading…
Reference in New Issue
Block a user