use nu_protocol::LabeledError;
use thiserror::Error;
#[derive(Clone, Copy, Debug, PartialEq, Eq)]
pub(crate) enum ErrorKind {
Validation,
State,
FieldCollision,
Http,
Transport,
Timeout,
Response,
Cancelled,
}
impl ErrorKind {
pub(crate) fn as_str(self) -> &'static str {
match self {
Self::Validation => "validation",
Self::State => "state",
Self::FieldCollision => "field_collision",
Self::Http => "http",
Self::Transport => "transport",
Self::Timeout => "timeout",
Self::Response => "response",
Self::Cancelled => "cancelled",
}
}
}
#[derive(Debug, Error)]
#[error("{message}")]
pub(crate) struct JevError {
pub(crate) kind: ErrorKind,
pub(crate) message: String,
pub(crate) status: Option<u16>,
}
impl JevError {
pub(crate) fn new(kind: ErrorKind, message: impl Into<String>) -> Self {
Self {
kind,
message: message.into(),
status: None,
}
}
pub(crate) fn http(status: u16) -> Self {
Self {
kind: ErrorKind::Http,
message: format!("Jev returned HTTP {status}"),
status: Some(status),
}
}
pub(crate) fn into_labeled(self) -> LabeledError {
LabeledError::new(self.message).with_code(format!("jev::{}", self.kind.as_str()))
}
}
#[cfg(test)]
mod tests {
use super::{ErrorKind, JevError};
#[test]
fn maps_redacted_error_categories() {
let http = JevError::http(503);
assert_eq!(http.kind, ErrorKind::Http);
assert_eq!(http.status, Some(503));
assert_eq!(http.into_labeled().code.as_deref(), Some("jev::http"));
let timeout = JevError::new(ErrorKind::Timeout, "deadline expired");
assert_eq!(timeout.status, None);
assert_eq!(timeout.into_labeled().code.as_deref(), Some("jev::timeout"));
}
}