#[cfg(not(feature = "simd-json"))]
pub use serde_json::{from_slice, from_str, to_string, to_vec, Error as JsonError};
#[cfg(feature = "simd-json")]
pub use simd_json::{from_slice, from_str, to_string, to_vec, Error as JsonError};
use std::{
error::Error,
fmt::{Display, Formatter, Result as FmtResult},
};
use twilight_model::gateway::event::GatewayEvent;
#[derive(Debug)]
pub struct GatewayEventParsingError {
pub(super) source: Option<Box<dyn Error + Send + Sync>>,
pub(super) kind: GatewayEventParsingErrorType,
}
impl Display for GatewayEventParsingError {
fn fmt(&self, f: &mut Formatter<'_>) -> FmtResult {
match &self.kind {
GatewayEventParsingErrorType::Deserializing => {
f.write_str("deserializing gateway event as json failed")
}
GatewayEventParsingErrorType::PayloadInvalid => {
f.write_str("payload is an invalid json structure")
}
}
}
}
impl Error for GatewayEventParsingError {
fn source(&self) -> Option<&(dyn Error + 'static)> {
self.source
.as_ref()
.map(|source| &**source as &(dyn Error + 'static))
}
}
#[derive(Debug)]
#[non_exhaustive]
pub enum GatewayEventParsingErrorType {
Deserializing,
PayloadInvalid,
}
#[cfg(not(feature = "simd-json"))]
#[allow(dead_code)]
pub fn parse_gateway_event(
op: u8,
sequence: Option<u64>,
event_type: Option<&str>,
json: &mut [u8],
) -> Result<GatewayEvent, GatewayEventParsingError> {
use serde::de::DeserializeSeed;
use serde_json::Deserializer;
use twilight_model::gateway::event::GatewayEventDeserializer;
let gateway_deserializer = GatewayEventDeserializer::new(op, sequence, event_type);
let mut json_deserializer = Deserializer::from_slice(json);
gateway_deserializer
.deserialize(&mut json_deserializer)
.map_err(|source| {
#[cfg(feature = "tracing")]
tracing::debug!("invalid JSON: {}", String::from_utf8_lossy(json));
GatewayEventParsingError {
kind: GatewayEventParsingErrorType::Deserializing,
source: Some(Box::new(source)),
}
})
}
#[cfg(feature = "simd-json")]
#[allow(dead_code)]
pub fn parse_gateway_event(
op: u8,
sequence: Option<u64>,
event_type: Option<&str>,
json: &mut [u8],
) -> Result<GatewayEvent, GatewayEventParsingError> {
use serde::de::DeserializeSeed;
use simd_json::Deserializer;
use twilight_model::gateway::event::gateway::GatewayEventDeserializer;
let gateway_deserializer = GatewayEventDeserializer::new(op, sequence, event_type);
let mut json_deserializer =
Deserializer::from_slice(json).map_err(|_| GatewayEventParsingError {
kind: GatewayEventParsingErrorType::PayloadInvalid,
source: None,
})?;
gateway_deserializer
.deserialize(&mut json_deserializer)
.map_err(|source| {
#[cfg(feature = "tracing")]
tracing::debug!("invalid JSON: {}", String::from_utf8_lossy(json));
GatewayEventParsingError {
kind: GatewayEventParsingErrorType::Deserializing,
source: Some(Box::new(source)),
}
})
}
#[cfg(test)]
mod tests {
use super::{GatewayEventParsingError, GatewayEventParsingErrorType};
use static_assertions::assert_impl_all;
use std::{error::Error, fmt::Debug};
assert_impl_all!(GatewayEventParsingErrorType: Debug, Send, Sync);
assert_impl_all!(GatewayEventParsingError: Error, Send, Sync);
}