mas_tower/tracing/
future.rs1use std::task::ready;
8
9use pin_project_lite::pin_project;
10use tracing::Span;
11
12pin_project! {
13 pub struct TraceFuture<F, OnResponse, OnError> {
14 #[pin]
15 inner: F,
16 span: Span,
17 on_response: OnResponse,
18 on_error: OnError,
19 }
20}
21
22impl<F, OnResponse, OnError> TraceFuture<F, OnResponse, OnError> {
23 pub fn new(inner: F, span: Span, on_response: OnResponse, on_error: OnError) -> Self {
24 Self {
25 inner,
26 span,
27 on_response,
28 on_error,
29 }
30 }
31}
32
33impl<F, R, E, OnResponse, OnError> Future for TraceFuture<F, OnResponse, OnError>
34where
35 F: Future<Output = Result<R, E>>,
36 OnResponse: super::enrich_span::EnrichSpan<R>,
37 OnError: super::enrich_span::EnrichSpan<E>,
38{
39 type Output = Result<R, E>;
40
41 fn poll(
42 self: std::pin::Pin<&mut Self>,
43 cx: &mut std::task::Context<'_>,
44 ) -> std::task::Poll<Self::Output> {
45 let this = self.project();
46
47 let _guard = this.span.enter();
50 let result = ready!(this.inner.poll(cx));
51
52 match &result {
53 Ok(response) => {
54 this.on_response.enrich_span(this.span, response);
55 }
56 Err(error) => {
57 this.on_error.enrich_span(this.span, error);
58 }
59 }
60
61 std::task::Poll::Ready(result)
62 }
63}