use std::io::ErrorKind;
use zond_engine::ScanError;
use crate::exit::Code;
use crate::target::TargetError;
#[derive(Debug, thiserror::Error)]
#[non_exhaustive]
pub(crate) enum Error {
#[error("{0}")]
Target(#[from] TargetError),
#[error("the scan did not run to completion: {0}")]
Scan(#[from] ScanError),
#[error("{0}")]
Io(#[from] std::io::Error),
#[error("{0}")]
Settings(#[from] crate::settings::SettingsError),
#[error("{0}")]
Presentation(#[from] crate::render::Unavailable),
}
impl Error {
#[must_use]
pub(crate) fn code(&self) -> Code {
match self {
Error::Target(_) | Error::Settings(_) | Error::Presentation(_) => Code::Usage,
Error::Scan(_) => Code::Failure,
Error::Io(e) => {
if e.kind() == ErrorKind::BrokenPipe {
Code::Success
} else {
Code::Failure
}
}
}
}
pub(crate) fn report(&self) {
if self.is_silent() {
return;
}
eprintln!("error: {self}");
}
#[must_use]
pub(crate) fn is_silent(&self) -> bool {
matches!(self, Error::Io(e) if e.kind() == ErrorKind::BrokenPipe)
}
}