use serde::{de, ser};
use std::fmt::{Debug, Display};
use thiserror::Error;
#[derive(Debug, Error)]
#[non_exhaustive]
pub enum WMIError {
#[error("HRESULT Call failed with: {hres:#X}")]
HResultError { hres: i32 },
#[error(transparent)]
ParseIntError(#[from] std::num::ParseIntError),
#[error(transparent)]
ParseFloatError(#[from] std::num::ParseFloatError),
#[cfg(feature = "chrono")]
#[error(transparent)]
ParseDatetimeError(#[from] chrono::format::ParseError),
#[cfg(feature = "chrono")]
#[error("Cannot parse a non unique local timestamp")]
ParseDatetimeLocalError,
#[cfg(feature = "time")]
#[error(transparent)]
ParseOffsetDatetimeError(#[from] time::Error),
#[error("Converting from variant type {0:#X} is not implemented yet")]
ConvertError(u16),
#[error("{0}")]
ConvertVariantError(String),
#[error("Invalid bool value: {0:#X}")]
ConvertBoolError(i16),
#[error(transparent)]
ConvertStringError(#[from] std::string::FromUtf16Error),
#[error("Expected {0:?} to be at least 21 chars")]
ConvertDatetimeError(String),
#[error("Expected {0:?} to be at 25 chars")]
ConvertDurationError(String),
#[error("Length {0} was too long to convert")]
ConvertLengthError(u64),
#[error("{0}")]
SerdeError(String),
#[error(transparent)]
DeserializeValueError(#[from] de::value::Error),
#[error("No results returned")]
ResultEmpty,
#[error("Null pointer was sent as part of query result")]
NullPointerResult,
#[error("Unimplemeted array item in query")]
UnimplementedArrayItem,
#[error("Invalid variant {0} during deserialization")]
InvalidDeserializationVariantError(String),
}
impl From<windows::core::Error> for WMIError {
fn from(value: windows::core::Error) -> Self {
Self::HResultError {
hres: value.code().0,
}
}
}
impl de::Error for WMIError {
#[cold]
fn custom<T: Display>(msg: T) -> WMIError {
Self::SerdeError(format!("{}", msg))
}
}
impl ser::Error for WMIError {
#[cold]
fn custom<T: Display>(msg: T) -> WMIError {
Self::SerdeError(format!("{}", msg))
}
}
pub type WMIResult<T> = Result<T, WMIError>;