Diffstat (limited to 'src/error.rs')
-rw-r--r--src/error.rs93
1 files changed, 93 insertions, 0 deletions
diff --git a/src/error.rs b/src/error.rs
new file mode 100644
index 0000000..d975312
--- /dev/null
+++ b/src/error.rs
@@ -0,0 +1,93 @@
+use crate::protocol::{Protocol, ProtocolDescription};
+
+pub trait WalkerError<'value, 'ctx: 'value> {
+ fn wrong_visit<P: Protocol<'value, 'ctx>>() -> Self;
+ fn needs_hint() -> Self;
+}
+
+pub trait VisitorError<'value, 'ctx: 'value> {
+ fn wrong_hint<P: Protocol<'value, 'ctx>>() -> Self;
+}
+
+#[derive(thiserror::Error, Debug)]
+pub enum UniError<WalkerErr, VisitorErr> {
+ #[error(transparent)]
+ Walker(WalkerErr),
+
+ #[error(transparent)]
+ Visitor(VisitorErr),
+}
+
+#[derive(thiserror::Error, Debug)]
+#[error("{message}")]
+pub struct BasicError {
+ message: &'static str,
+}
+
+impl BasicError {
+ pub fn new(message: &'static str) -> Self {
+ Self { message }
+ }
+
+ pub fn message(&self) -> &'static str {
+ self.message
+ }
+}
+
+impl<'value, 'ctx: 'value> WalkerError<'value, 'ctx> for BasicError {
+ fn wrong_visit<P: Protocol<'value, 'ctx>>() -> Self {
+ Self::new("wrong protocol for visit")
+ }
+
+ fn needs_hint() -> Self {
+ Self::new("walker needs hint from visitor")
+ }
+}
+
+impl<'value, 'ctx: 'value> VisitorError<'value, 'ctx> for BasicError {
+ fn wrong_hint<P: Protocol<'value, 'ctx>>() -> Self {
+ Self::new("wrong protocol for hint")
+ }
+}
+
+/// Error wrapper that adds a missing variant.
+#[derive(thiserror::Error, Debug)]
+pub enum Missing<E> {
+ /// The value was never visted.
+ #[error("value is missing after walking")]
+ Missing,
+
+ /// Another error.
+ #[error(transparent)]
+ Error(#[from] E),
+}
+
+impl<'value, 'ctx: 'value, E: VisitorError<'value, 'ctx>> VisitorError<'value, 'ctx>
+ for Missing<E>
+{
+ fn wrong_hint<P: Protocol<'value, 'ctx>>() -> Self {
+ E::wrong_hint::<P>().into()
+ }
+}
+
+#[derive(thiserror::Error, Debug)]
+pub enum WrongProtocol<E> {
+ /// The wrong protocol was given in a query.
+ #[error("wrong protocol, expected: `{expected}`, got: `{got}`")]
+ WrongProtocol {
+ expected: ProtocolDescription,
+ got: ProtocolDescription,
+ },
+
+ /// Another error.
+ #[error(transparent)]
+ Error(#[from] E),
+}
+
+impl<'value, 'ctx: 'value, E: VisitorError<'value, 'ctx>> VisitorError<'value, 'ctx>
+ for WrongProtocol<E>
+{
+ fn wrong_hint<P: Protocol<'value, 'ctx>>() -> Self {
+ E::wrong_hint::<P>().into()
+ }
+}