use std::fmt;
use crate::{
ancestry::{ActualAncestry, ExpectedAncestry},
field,
metadata::ExpectedMetadata,
span,
};
#[derive(Default, Eq, PartialEq)]
pub struct ExpectedEvent {
pub(super) fields: Option<field::ExpectedFields>,
pub(super) ancestry: Option<ExpectedAncestry>,
pub(super) in_spans: Option<Vec<span::ExpectedSpan>>,
pub(super) metadata: ExpectedMetadata,
}
impl ExpectedEvent {
pub fn named<I>(self, name: I) -> Self
where
I: Into<String>,
{
Self {
metadata: ExpectedMetadata {
name: Some(name.into()),
..self.metadata
},
..self
}
}
pub fn with_fields<I>(self, fields: I) -> Self
where
I: Into<field::ExpectedFields>,
{
Self {
fields: Some(fields.into()),
..self
}
}
pub fn at_level(self, level: tracing::Level) -> Self {
Self {
metadata: ExpectedMetadata {
level: Some(level),
..self.metadata
},
..self
}
}
pub fn with_target<I>(self, target: I) -> Self
where
I: Into<String>,
{
Self {
metadata: ExpectedMetadata {
target: Some(target.into()),
..self.metadata
},
..self
}
}
pub fn with_ancestry(self, ancenstry: ExpectedAncestry) -> ExpectedEvent {
Self {
ancestry: Some(ancenstry),
..self
}
}
#[cfg(feature = "tracing-subscriber")]
pub fn in_scope(self, spans: impl IntoIterator<Item = span::ExpectedSpan>) -> Self {
Self {
in_spans: Some(spans.into_iter().collect()),
..self
}
}
#[cfg(feature = "tracing-subscriber")]
pub(crate) fn scope_mut(&mut self) -> Option<&mut [span::ExpectedSpan]> {
self.in_spans.as_mut().map(|s| &mut s[..])
}
pub(crate) fn check(
&mut self,
event: &tracing::Event<'_>,
get_ancestry: impl FnOnce() -> ActualAncestry,
subscriber_name: &str,
) {
let meta = event.metadata();
let name = meta.name();
self.metadata
.check(meta, format_args!("event \"{}\"", name), subscriber_name);
assert!(
meta.is_event(),
"[{}] expected {}, but got {:?}",
subscriber_name,
self,
event
);
if let Some(ref mut expected_fields) = self.fields {
let mut checker = expected_fields.checker(name, subscriber_name);
event.record(&mut checker);
checker.finish();
}
if let Some(ref expected_ancestry) = self.ancestry {
let actual_ancestry = get_ancestry();
expected_ancestry.check(&actual_ancestry, event.metadata().name(), subscriber_name);
}
}
}
impl fmt::Display for ExpectedEvent {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
write!(f, "an event{}", self.metadata)
}
}
impl fmt::Debug for ExpectedEvent {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
let mut s = f.debug_struct("MockEvent");
if let Some(ref name) = self.metadata.name {
s.field("name", name);
}
if let Some(ref target) = self.metadata.target {
s.field("target", target);
}
if let Some(ref level) = self.metadata.level {
s.field("level", &format_args!("{:?}", level));
}
if let Some(ref fields) = self.fields {
s.field("fields", fields);
}
if let Some(ref parent) = self.ancestry {
s.field("parent", &format_args!("{:?}", parent));
}
if let Some(in_spans) = &self.in_spans {
s.field("in_spans", in_spans);
}
s.finish()
}
}