vectordotdev/vector · error
Failed type coercion, {self:?} is not a metric reference
Error message
Failed type coercion, {self:?} is not a metric reference What it means
EventRef::as_metric() extracts the &'a Metric from an EventRef, panicking unless the reference is the Metric variant. The panic is an invariant assertion: the API is designed for call sites that have already established the event is a metric, so any other variant reaching this code is a logic bug in the caller.
Source
Thrown at lib/vector-core/src/event/ref.rs:52
/// # Panics
///
/// This will panic if this is not a `LogEvent` reference.
pub fn into_log(self) -> LogEvent {
match self {
Self::Log(log) => log.clone(),
_ => panic!("Failed type coercion, {self:?} is not a log reference"),
}
}
/// Extract the `Metric` reference in this.
///
/// # Panics
///
/// This will panic if this is not a `Metric` reference.
pub fn as_metric(self) -> &'a Metric {
match self {
Self::Metric(metric) => metric,
_ => panic!("Failed type coercion, {self:?} is not a metric reference"),
}
}
/// Convert this reference into a new `Metric` by cloning.
///
/// # Panics
///
/// This will panic if this is not a `Metric` reference.
pub fn into_metric(self) -> Metric {
match self {
Self::Metric(metric) => metric.clone(),
_ => panic!("Failed type coercion, {self:?} is not a metric reference"),
}
}
}
impl<'a> From<&'a Event> for EventRef<'a> {
fn from(event: &'a Event) -> Self {View on GitHub (pinned to 3708c39b12)
Solutions
- Narrow first: only call as_metric() when matches!(event_ref, EventRef::Metric(_))
- Branch on the source Event with match event { Event::Metric(m) => ..., _ => ... } so the compiler guarantees the type
- Fix the pipeline wiring so metric-only code only receives metrics (inputs/outputs declarations)
Example fix
// before
let metric = event_ref.as_metric(); // panics if not Metric
// after
if let EventRef::Metric(_) = event_ref {
let metric = event_ref.as_metric();
// ...
} Defensive patterns
Strategy: type-guard
Validate before calling
if let EventRef::Metric(_) = event_ref {
let metric = event_ref.as_metric(); // safe
} Type guard
fn is_metric_ref(r: &EventRef<'_>) -> bool {
matches!(r, EventRef::Metric(_))
} Prevention
- Match on the owning Event enum (Event::Metric arm) instead of coercing a shared reference
- Keep metric-specific logic behind output-type declarations in pipeline config
- Add tests covering mixed event arrays for any code that coerces references
When it happens
Trigger: Calling event_ref.as_metric() when the EventRef wraps a LogEvent or TraceEvent, e.g. metric-accumulator code fed from a logs source, or a match that falls through to a blanket coercion branch.
Common situations: Custom metric transforms or sinks connected to log inputs; code that inspects Event::as_log()/as_metric() based on a stale or wrong discriminant check; unit tests using mixed event fixtures where a log slips into the metric path.
Related errors
- Failed type coercion, {self:?} is not a metric
- Failed type coercion, {self:?} is not a log event
- Failed type coercion, {self:?} is not a log reference
- Failed type coercion, {self:?} is not a trace event
- Failed type coercion, {self:?} is not a Sink
AI-assisted analysis of vectordotdev/vector@3708c39b12 (2026-08-20).
Data as JSON: /api/errors/b9ba9b942102c0fb.
Report an issue: GitHub.