mirror of
https://github.com/tokio-rs/tokio.git
synced 2026-08-07 00:00:09 +02:00
trace: Make Span API functions taking IDs a little more flexible (#1021)
This branch modifies the `tokio_trace::Span` API functions that take span IDs (the `Span::child_of` constructor, and the `Span::follows_from` method) so that more types bearing a span ID can be passed as an argument. Span IDs may now be passed directly without requiring them to be passed as `Some(id)`. This should make the API slightly more ergonomic. Also, it changes the `Span::field` method to take an `AsField` rather than a `Borrow<str>`. Signed-off-by: Eliza Weisman <[email protected]>
This commit is contained in:
+70
-18
@@ -126,12 +126,16 @@
|
||||
pub use tokio_trace_core::span::{Attributes, Id, Record};
|
||||
|
||||
use std::{
|
||||
borrow::Borrow,
|
||||
cmp, fmt,
|
||||
hash::{Hash, Hasher},
|
||||
};
|
||||
use {dispatcher::Dispatch, field, Metadata};
|
||||
|
||||
/// Trait implemented by types which have a span `Id`.
|
||||
pub trait AsId: ::sealed::Sealed {
|
||||
fn as_id(&self) -> Option<&Id>;
|
||||
}
|
||||
|
||||
/// A handle representing a span, with the capability to enter the span if it
|
||||
/// exists.
|
||||
///
|
||||
@@ -229,10 +233,10 @@ impl Span {
|
||||
values: &field::ValueSet,
|
||||
) -> Span
|
||||
where
|
||||
I: Into<Option<Id>>,
|
||||
I: AsId,
|
||||
{
|
||||
let new_span = match parent.into() {
|
||||
Some(parent) => Attributes::child_of(parent, meta, values),
|
||||
let new_span = match parent.as_id() {
|
||||
Some(parent) => Attributes::child_of(parent.clone(), meta, values),
|
||||
None => Attributes::new_root(meta, values),
|
||||
};
|
||||
Self::make(meta, new_span)
|
||||
@@ -280,22 +284,21 @@ impl Span {
|
||||
|
||||
/// Returns a [`Field`](::field::Field) for the field with the given `name`, if
|
||||
/// one exists,
|
||||
pub fn field<Q>(&self, name: &Q) -> Option<field::Field>
|
||||
pub fn field<Q: ?Sized>(&self, field: &Q) -> Option<field::Field>
|
||||
where
|
||||
Q: Borrow<str>,
|
||||
Q: field::AsField,
|
||||
{
|
||||
self.metadata().and_then(|meta| meta.fields().field(name))
|
||||
self.metadata().and_then(|meta| field.as_field(meta))
|
||||
}
|
||||
|
||||
/// Returns true if this `Span` has a field for the given
|
||||
/// [`Field`](::field::Field) or field name.
|
||||
#[inline]
|
||||
pub fn has_field<Q: ?Sized>(&self, field: &Q) -> bool
|
||||
where
|
||||
Q: field::AsField,
|
||||
{
|
||||
self.metadata()
|
||||
.and_then(|meta| field.as_field(meta))
|
||||
.is_some()
|
||||
self.field(field).is_some()
|
||||
}
|
||||
|
||||
/// Visits that the field described by `field` has the value `value`.
|
||||
@@ -347,9 +350,14 @@ impl Span {
|
||||
///
|
||||
/// If this span is disabled, or the resulting follows-from relationship
|
||||
/// would be invalid, this function will do nothing.
|
||||
pub fn follows_from(&self, from: &Id) -> &Self {
|
||||
pub fn follows_from<I>(&self, from: I) -> &Self
|
||||
where
|
||||
I: AsId,
|
||||
{
|
||||
if let Some(ref inner) = self.inner {
|
||||
inner.follows_from(from);
|
||||
if let Some(from) = from.as_id() {
|
||||
inner.follows_from(from);
|
||||
}
|
||||
}
|
||||
self
|
||||
}
|
||||
@@ -436,12 +444,6 @@ impl fmt::Debug for Span {
|
||||
}
|
||||
}
|
||||
|
||||
impl<'a> Into<Option<Id>> for &'a Span {
|
||||
fn into(self) -> Option<Id> {
|
||||
self.id()
|
||||
}
|
||||
}
|
||||
|
||||
// ===== impl Inner =====
|
||||
|
||||
impl Inner {
|
||||
@@ -553,3 +555,53 @@ impl<'a> fmt::Display for FmtAttrs<'a> {
|
||||
res
|
||||
}
|
||||
}
|
||||
|
||||
// ===== impl AsId =====
|
||||
|
||||
impl ::sealed::Sealed for Span {}
|
||||
|
||||
impl AsId for Span {
|
||||
fn as_id(&self) -> Option<&Id> {
|
||||
self.inner.as_ref().map(|inner| &inner.id)
|
||||
}
|
||||
}
|
||||
|
||||
impl<'a> ::sealed::Sealed for &'a Span {}
|
||||
|
||||
impl<'a> AsId for &'a Span {
|
||||
fn as_id(&self) -> Option<&Id> {
|
||||
self.inner.as_ref().map(|inner| &inner.id)
|
||||
}
|
||||
}
|
||||
|
||||
impl ::sealed::Sealed for Id {}
|
||||
|
||||
impl AsId for Id {
|
||||
fn as_id(&self) -> Option<&Id> {
|
||||
Some(self)
|
||||
}
|
||||
}
|
||||
|
||||
impl<'a> ::sealed::Sealed for &'a Id {}
|
||||
|
||||
impl<'a> AsId for &'a Id {
|
||||
fn as_id(&self) -> Option<&Id> {
|
||||
Some(self)
|
||||
}
|
||||
}
|
||||
|
||||
impl ::sealed::Sealed for Option<Id> {}
|
||||
|
||||
impl AsId for Option<Id> {
|
||||
fn as_id(&self) -> Option<&Id> {
|
||||
self.as_ref()
|
||||
}
|
||||
}
|
||||
|
||||
impl<'a> ::sealed::Sealed for &'a Option<Id> {}
|
||||
|
||||
impl<'a> AsId for &'a Option<Id> {
|
||||
fn as_id(&self) -> Option<&Id> {
|
||||
self.as_ref()
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user