-
Notifications
You must be signed in to change notification settings - Fork 882
Expose simultaneous access to Span and Inner on Instrumented so that implementation of foreign traits are possible #2804
Description
Feature Request
Motivation
In my own crate I have a trait that represents some asynchronous work (similar to Stream trait). I wanted to support instrumenting on it. I.e. on my crate, I would provide impl<T: MyTrait> MyTrait for Instrumented<T> {.
On the poll() method of my trait I would enter the span, invoke the original T::poll and then exit the span. However, in order to do that I need simultaneous access to &Span and to Pin<&mut T>.
Proposal
In order to implement Future for Instrumented<T>, the tracing crate uses a private function called span_and_inner_pin_mut. A public version of this function could be exposed.
impl<T: MyTrait> MyTrait for Instrumented<T> {
fn my_poll(self: Pin<&mut Self>, cx: &mut Context) -> Poll<()> {
let (span, this) = self.span_and_inner_pin_mut();
let _enter = span.enter();
this.my_poll(cx)
}
}
Alternatives
At the moment, it is possible to achieve the same goal by cloning the span from the reference that Instrumented provides, thus not borrowing the Instrumented. Since Instrumented is not borrowed, the public method inner_pin_mut may be used:
impl<T: MyTrait> MyTrait for Instrunmented<T> {
fn my_poll(self: Pin<&mut Self>, cx: &mut Context) -> Poll<()> {
let _enter = self.span().clone().entered();
self.inner_pin_mut().poll(cx)
}
}