1 #[path = "../../tracing-futures/tests/support.rs"]
2 // we don't use some of the test support functions, but `tracing-futures` does.
7 use std
::{future::Future, pin::Pin, sync::Arc}
;
8 use tracing
::subscriber
::with_default
;
9 use tracing_attributes
::instrument
;
12 async
fn test_async_fn(polls
: usize) -> Result
<(), ()> {
13 let future
= PollN
::new_ok(polls
);
14 tracing
::trace
!(awaiting
= true);
18 // Reproduces a compile error when returning an `impl Trait` from an
19 // instrumented async fn (see https://github.com/tokio-rs/tracing/issues/1615)
21 async
fn test_ret_impl_trait(n
: i32) -> Result
<impl Iterator
<Item
= i32>, ()> {
23 Ok((0..10).filter(move |x
| *x
< n
))
26 // Reproduces a compile error when returning an `impl Trait` from an
27 // instrumented async fn (see https://github.com/tokio-rs/tracing/issues/1615)
29 async
fn test_ret_impl_trait_err(n
: i32) -> Result
<impl Iterator
<Item
= i32>, &'
static str> {
30 Ok((0..10).filter(move |x
| *x
< n
))
34 async
fn test_async_fn_empty() {}
36 // Reproduces https://github.com/tokio-rs/tracing/issues/1613
38 // LOAD-BEARING `#[rustfmt::skip]`! This is necessary to reproduce the bug;
39 // with the rustfmt-generated formatting, the lint will not be triggered!
41 #[deny(clippy::suspicious_else_formatting)]
42 async
fn repro_1613(var
: bool
) {
45 if var { "true" }
else { "false" }
49 // Reproduces https://github.com/tokio-rs/tracing/issues/1613
50 // and https://github.com/rust-lang/rust-clippy/issues/7760
52 #[deny(clippy::suspicious_else_formatting)]
53 async
fn repro_1613_2() {
59 fn async_fn_only_enters_for_polls() {
60 let (subscriber
, handle
) = subscriber
::mock()
61 .new_span(span
::mock().named("test_async_fn"))
62 .enter(span
::mock().named("test_async_fn"))
63 .event(event
::mock().with_fields(field
::mock("awaiting").with_value(&true)))
64 .exit(span
::mock().named("test_async_fn"))
65 .enter(span
::mock().named("test_async_fn"))
66 .exit(span
::mock().named("test_async_fn"))
67 .drop_span(span
::mock().named("test_async_fn"))
70 with_default(subscriber
, || {
71 block_on_future(async { test_async_fn(2).await }
).unwrap();
73 handle
.assert_finished();
77 fn async_fn_nested() {
79 async
fn test_async_fns_nested() {
80 test_async_fns_nested_other().await
84 async
fn test_async_fns_nested_other() {
85 tracing
::trace
!(nested
= true);
88 let span
= span
::mock().named("test_async_fns_nested");
89 let span2
= span
::mock().named("test_async_fns_nested_other");
90 let (subscriber
, handle
) = subscriber
::mock()
91 .new_span(span
.clone())
93 .new_span(span2
.clone())
95 .event(event
::mock().with_fields(field
::mock("nested").with_value(&true)))
103 with_default(subscriber
, || {
104 block_on_future(async { test_async_fns_nested().await }
);
107 handle
.assert_finished();
111 fn async_fn_with_async_trait() {
112 use async_trait
::async_trait
;
114 // test the correctness of the metadata obtained by #[instrument]
115 // (function name, functions parameters) when async-trait is used
118 async
fn foo(&mut self, v
: usize);
121 // test nesting of async fns with aync-trait
127 // test skip(self) with async-await
134 struct TestImpl(usize);
137 impl TestA
for TestImpl
{
139 async
fn foo(&mut self, v
: usize) {
147 impl TestB
for TestImpl
{
149 async
fn bar(&self) {
150 tracing
::trace
!(val
= self.0);
155 impl TestC
for TestImpl
{
156 #[instrument(skip(self))]
157 async
fn baz(&self) {
158 tracing
::trace
!(val
= self.0);
162 let span
= span
::mock().named("foo");
163 let span2
= span
::mock().named("bar");
164 let span3
= span
::mock().named("baz");
165 let (subscriber
, handle
) = subscriber
::mock()
168 .with_field(field
::mock("self"))
169 .with_field(field
::mock("v")),
172 .new_span(span3
.clone())
173 .enter(span3
.clone())
174 .event(event
::mock().with_fields(field
::mock("val").with_value(&2u64)))
177 .new_span(span2
.clone().with_field(field
::mock("self")))
178 .enter(span2
.clone())
179 .event(event
::mock().with_fields(field
::mock("val").with_value(&5u64)))
187 with_default(subscriber
, || {
188 let mut test
= TestImpl(2);
189 block_on_future(async { test.foo(5).await }
);
192 handle
.assert_finished();
196 fn async_fn_with_async_trait_and_fields_expressions() {
197 use async_trait
::async_trait
;
201 async
fn call(&mut self, v
: usize);
204 #[derive(Clone, Debug)]
208 fn foo(&self) -> usize {
214 impl Test
for TestImpl
{
215 // check that self is correctly handled, even when using async_trait
216 #[instrument(fields(val=self.foo(), val2=Self::clone(self).foo(), test=%_v+5))]
217 async
fn call(&mut self, _v
: usize) {}
220 let span
= span
::mock().named("call");
221 let (subscriber
, handle
) = subscriber
::mock()
223 span
.clone().with_field(
226 .and(field
::mock("test").with_value(&tracing
::field
::debug(10)))
227 .and(field
::mock("val").with_value(&42u64))
228 .and(field
::mock("val2").with_value(&42u64)),
237 with_default(subscriber
, || {
238 block_on_future(async { TestImpl.call(5).await }
);
241 handle
.assert_finished();
245 fn async_fn_with_async_trait_and_fields_expressions_with_generic_parameter() {
246 use async_trait
::async_trait
;
251 async
fn call_with_self(&self);
252 async
fn call_with_mut_self(&mut self);
255 #[derive(Clone, Debug)]
258 // we also test sync functions that return futures, as they should be handled just like
259 // async-trait (>= 0.1.44) functions
261 #[instrument(fields(Self=std::any::type_name::<Self>()))]
262 fn sync_fun(&self) -> Pin
<Box
<dyn Future
<Output
= ()> + Send
+ '_
>> {
263 let val
= self.clone();
264 Box
::pin(async
move {
271 impl Test
for TestImpl
{
272 // instrumenting this is currently not possible, see https://github.com/tokio-rs/tracing/issues/864#issuecomment-667508801
273 //#[instrument(fields(Self=std::any::type_name::<Self>()))]
276 #[instrument(fields(Self=std::any::type_name::<Self>()))]
277 async
fn call_with_self(&self) {
278 self.sync_fun().await
;
281 #[instrument(fields(Self=std::any::type_name::<Self>()))]
282 async
fn call_with_mut_self(&mut self) {}
285 //let span = span::mock().named("call");
286 let span2
= span
::mock().named("call_with_self");
287 let span3
= span
::mock().named("call_with_mut_self");
288 let span4
= span
::mock().named("sync_fun");
289 let (subscriber
, handle
) = subscriber
::mock()
290 /*.new_span(span.clone()
292 field::mock("Self").with_value(&"TestImpler")))
299 .with_field(field
::mock("Self").with_value(&std
::any
::type_name
::<TestImpl
>())),
301 .enter(span2
.clone())
305 .with_field(field
::mock("Self").with_value(&std
::any
::type_name
::<TestImpl
>())),
307 .enter(span4
.clone())
314 .with_field(field
::mock("Self").with_value(&std
::any
::type_name
::<TestImpl
>())),
316 .enter(span3
.clone())
322 with_default(subscriber
, || {
323 block_on_future(async
{
324 TestImpl
::call().await
;
325 TestImpl
.call_with_self().await
;
326 TestImpl
.call_with_mut_self().await
330 handle
.assert_finished();
334 fn out_of_scope_fields() {
335 // Reproduces tokio-rs/tracing#1296
342 #[instrument(skip(self, _req), fields(app_id))]
343 fn call(&mut self, _req
: ()) -> Pin
<Box
<dyn Future
<Output
= Arc
<()>> + Send
+ Sync
>> {
345 let metrics
= self.metrics
.clone();
347 Box
::pin(async
move {
349 metrics
// cannot find value `metrics` in this scope
354 let span
= span
::mock().named("call");
355 let (subscriber
, handle
) = subscriber
::mock()
356 .new_span(span
.clone())
363 with_default(subscriber
, || {
364 block_on_future(async
{
365 let mut my_thing
= Thing
{
366 metrics
: Arc
::new(()),
368 my_thing
.call(()).await
;
372 handle
.assert_finished();