Most of these changes are places where lifetimes were named, but can be
elided. Then a few cases where a lifetime was elided, but actually
resolves to a named lifetime. So lots of lifetimes.
This is the `v0.1.x` branch sister PR to #3164 (for the `master`
branch), since `clippy --fix` on another branch is a much better way to
apply these changes than backporting.
There are 2 triggers which will cause a subscriber to receive a call to
`Subscriber::register_callsite` for a specific callsite.
1. The first time the event or span at that callsite is executed.
2. When a new subscriber is added or removed (for example, calls to
`set_default` or `with_default`)
It is trigger (2) that will cause a new subscriber to receive
`Subscriber::register_callsite` for all the callsites which had already
been registered before it became active.
When a callsite is registered for trigger (1), the callsite starts in
state `UNREGISTERED`.
The first thread to encounter the callsite will transition it to
`REGISTERING` and determine the overall interest for the callsite by
registering with all known dispatchers (which will call into
`Subscriber::register_callsite`).
Once that is complete, the callsite is added to the list of all known
callsites and its state is transitioned to `REGISTERED`.
is (re)built for all known dispatchers. The callsite starts in state
`UNREGISTERED`. The This calls down into
`Subscriber::register_callsite` for each subscriber. Once that is
complete, the callsite is added to the global list of known callsites.
While the callsite interest is being rebuilt, other threads that
encounter the callsite will be given `Interest::sometimes()` until the
registration is complete. However, if a new subscriber is added during
this window, all the interest for all callsites will be rebuilt, but
because the new callsite (in state `REGISTERING`) won't be included
because it isn't yet in the global list of callsites.
This can cause a case where that new subscriber being added won't
receive `Subscriber::register_callsite` before it receives the subsequent
call to `Subscriber::event` or `Subscriber::new_span`.
The documentation on [Registering Callsites] is not very explicit on
this point, but it does suggest that `Subscriber::register_callsite`
will be called before the call to either `Subscriber::event` or
`Subscriber::new_span`, and the current behavior can break this implicit
contract.
[Registering Callsites]: https://docs.rs/tracing-core/0.1.32/tracing_core/callsite/index.html#registering-callsites
This change swaps the order of rebuilding the callsite interest and
adding the callsite to the global list so that the callsite gets pushed
first, avoiding this window in which a subscriber won't get a call to
`register_callsite`.
As such, a callsite may have its interest read before it is set. In this
case, the existing implementation will return `Interest::sometimes()`
for the `DefaultCallsite` implementation. Other implementations (outside
of the `tracing` project) may perform this differently, but in this
case, there is no documented guarantee regarding the ordering.
A regression test is included which provokes the race condition 100% of
the time before the changes in this fix.
Fixes: #2743
Co-authored-by: David Barsky <me@davidbarsky.com>
## Motivation
Expose the index of the field in order to support cases such as sending field information
by index instead of by the string name in Tokio Console. Details:
https://github.com/tokio-rs/console/issues/462#issuecomment-1830842319
## Solution
Adds a new API which exposes the index of a field, which is how it is stored internally
(together with a reference to the `FieldSet` containing the ordered field names.
Signed-off-by: hi-rustin <rustin.liu@gmail.com>
Co-authored-by: Hayden Stainsby <hds@caffeineconcepts.com>
Users may want to pass data to `Subscribe`s which is not valid UTF-8. Currently, it would have to be encoded into `&str` to be passed as a field value.
This branch adds a `record_bytes` method to `Visit`. It has an implementation falling back to `record_debug` so it is not be a breaking change.
`JsonVisitor` got an overridden implementation as it should not use `Debug` output and encode it as a string, but rather store the bytes as an array.
`PrettyVisitor` go an overridden implementation to make the output more pretty.
Co-authored-by: Eliza Weisman <eliza@buoyant.io>
This results in a substantial performance improvement,
and is compatible with our MSRV.
Signed-off-by: Alex Saveau <saveau.alexandre@gmail.com>
Co-authored-by: Eliza Weisman <eliza@buoyant.io>
## Motivation
`tracing-core` adds a dependency on `valuable` anytime the `std` (or `default`) feature is enabled even when `valuable` is not meant to be used. This was pointed out by [this comment](https://github.com/tokio-rs/tracing/pull/1608#discussion_r1626673415).
## Solution
Only add the feature dependency when something enables `valuable`.
This does not apply to `master` as `valuable` support there is always on.
With the release of Rust 1.74, there are some new or modified clippy
lints that need adaption in the code.
The main change was the removal of the `private_in_public`.
https://rust-lang.github.io/rfcs/2145-type-privacy.html
Then two more changes were required, in one case to adhere a lint and
the other to allow it. When talking about what an "application" needs to
do when setting up `tracing-error`, it makes sense to include `fn
main()` in the doctest, even though the lint recommends against it.
; Conflicts:
; examples/examples/map-traced-error.rs
These docs were updated (in response to #1669), but the "or equal to"
phrase should have been moved to the other case.
Fixes: #1993
## Motivation
When these docs were updated in response to #1669, they were updated
incompletely (a level that is equal to a filter is _enabled_, not
_disabled_) and therefore remained incorrect.
## Solution
The docs were updated, moving the "or equal to" phrase to the other
case.
## Motivation
Fixes: #1566
## Solution
This change removes the maximum of 32 fields limitation using const
generics.
Having this arbitrary restriction in place to prevent stack overflows
feels a little misplaced to me since stack size varies between
environments.
This branch fixes a handful of new warnings which have shown up after
updating to Rust 1.72.0.
This includes:
* `clippy::redundant_closure_call` in macros --- allowed because the
macro sometimes calls a function that isn't a closure, and the closure
is just used in the case where it's not a function.
* Unnecessary uses of `#` in raw string literals that don't contain `"`
characters.
* Dead code warnings with specific feature flag combinations in
`tracing-subscriber`.
In addition, I've fixed a broken RustDoc link that was making the
Netlify build sad.
The test relies on TEST_CALLSITE_1 and TEST_CALLSITE_2 to have
different addresses. However, as they are zero-sized types, this
is not guaranteed.
This fixes the test failure with LLVM 17 and certain optimization
options reported at https://github.com/rust-lang/rust/issues/114699.
Currently, in many places, macros do not use fully qualified names for
items exported from the prelude. This means that naming collisions
(`struct Some`) or the removal of the std library prelude will cause
compilation errors.
- Identify and use fully qualified names in macros were we previously
assumed the Rust std prelude. We use `::core` rather than `::std`.
- Add
[`no_implicit_prelude`](https://doc.rust-lang.org/reference/names/preludes.html#the-no_implicit_prelude-attribute)
to `tracing/tests/macros.rs`. I'm unsure if this is giving us good
coverage - can we improve on this approach? I'm not confident I've
caught everything.
# 0.1.31 (May 11, 2023)
This release of `tracing-core` fixes a bug that caused threads which
call `dispatcher::get_default` _before_ a global default subscriber is
set to never see the global default once it is set. In addition, it
includes improvements for instrumentation performance in some cases,
especially when using a global default dispatcher.
### Fixed
- Fixed incorrect thread-local caching of `Dispatch::none` if
`dispatcher::get_default` is called before
`dispatcher::set_global_default` (#2593)
### Changed
- Cloning a `Dispatch` that points at a global default subscriber no
longer requires an `Arc` reference count increment, improving
performance substantially (#2593)
- `dispatcher::get_default` no longer attempts to access a thread local
if the scoped dispatcher is not in use, improving performance when the
default dispatcher is global (#2593)
- Added `#[inline]` annotations called by the `event!` and `span!`
macros to reduce the size of macro-generated code and improve
recording performance (#2555)
Thanks to new contributor @ldm0 for contributing to this release!
## Motivation
Currently, when a call to `dispatcher::get_default` occurs, `tracing`
will check the thread-local default dispatcher first. If a thread-local
scoped default is set, it is returned. Otherwise, the thread will then
check the global default. If a global default is present, it is then
cached in the thread local, so that subsequent calls do not need to
check the global default.
Unfortunately, this behavior results in issues if the scoped default is
accessed (e.g. using `get_default` or creating a new span) *prior* to a
global default being set. When `get_default` runs for the first time and
there is no global default, a `none` dispatcher is cached as the
thread-local default. This means that the thread will now behave as
though its default dispatcher is `None` until the scoped default is
overridden, even if a global default is then set later. This is quite
bad, and results in issues such as #2587, #2436, and #2411.
## Solution
This branch makes several changes to remove the use of the thread-local
caching of the global default dispatcher, and to lessen the performance
impact of doing so.
On the `master` (v0.2.x) branch, we track the number of scoped
dispatchers currently active, and use it to determine whether or not to
check thread-local storage at all. This optimization was introduced in
PR #1017. This branch backports a similar change to `v0.1.x`.
In addition, #1017 also changes the dispatcher module to represent a
`Dispatch` internally using an enum of either an `Arc` in the case where
the dispatcher is scoped, or a `&'static dyn Subscriber + Send + Sync`
reference when the dispatcher is the global default. This makes cloning
and constructing the global default cheaper, and also allows us to
change the `None` dispatcher into a static singleton. That means that
the use of a `None` dispatcher no longer requires an allocation and arc
reference bump, an issue which was previously resolved by locally
caching a `None` dispatcher. A side benefit of this change is that
*cloning* a `Dispatch` is substantially cheaper when the dispatcher is a
global default, as it's just an `&'static` reference and no `Arc` bump
is necessary. This will also make cloning a `Span` cheaper when the
global default dispatcher is in use.
Finally, because the overhead of getting the global default is
substantially reduced, we are able to change the scoped default
dispatcher's behavior to remove the caching entirely. This means that
the category of bugs involving the local cache becoming stale is
resolved entirely.
Fixes#2587Fixes#2436Fixes#2411Closes#2592
## Performance Impact
This change results in a change in performance characteristics. Running
the benchmarks, we observe a significant improvement in performance in
most of the benchmarks that use the global default dispatcher, and a
noticeable decrease in performance for some benchmarks using the scoped
default. In my opinion, this performance change is acceptable, as a
global default dispatcher is the common case for most users, and is
generally expected to perform better than the scoped default. In
addition, resolving the variety of bugs that are caused by the local
caching of the default when using the scoped default dispatcher is worth
a performance cost when the scoped default is in use.
<details>
<summary>Benchmark results:</summary>
```
Running benches/baseline.rs (target/release/deps/baseline-9b70733ce49582d2)
comparison/relaxed_load time: [456.48 ps 456.55 ps 456.63 ps]
change: [+3.0281% +3.3135% +3.5664%] (p = 0.00 < 0.05)
Performance has regressed.
Found 10 outliers among 100 measurements (10.00%)
5 (5.00%) high mild
5 (5.00%) high severe
comparison/acquire_load time: [438.98 ps 439.32 ps 439.76 ps]
change: [-0.3725% -0.2092% -0.0614%] (p = 0.01 < 0.05)
Change within noise threshold.
Found 12 outliers among 100 measurements (12.00%)
2 (2.00%) high mild
10 (10.00%) high severe
comparison/log time: [227.05 ps 227.14 ps 227.27 ps]
change: [+3.1351% +3.2984% +3.4537%] (p = 0.00 < 0.05)
Performance has regressed.
Found 14 outliers among 100 measurements (14.00%)
5 (5.00%) high mild
9 (9.00%) high severe
```
```
Running benches/dispatch_get_clone.rs (target/release/deps/dispatch_get_clone-d4d6ca1f9895e432)
Dispatch::get_clone/none
time: [8.3974 ns 8.4004 ns 8.4039 ns]
change: [-22.870% -22.796% -22.728%] (p = 0.00 < 0.05)
Performance has improved.
Found 10 outliers among 100 measurements (10.00%)
1 (1.00%) low severe
1 (1.00%) low mild
4 (4.00%) high mild
4 (4.00%) high severe
Dispatch::get_clone/scoped
time: [15.877 ns 15.959 ns 16.045 ns]
change: [+52.358% +52.943% +53.500%] (p = 0.00 < 0.05)
Performance has regressed.
Found 16 outliers among 100 measurements (16.00%)
2 (2.00%) high mild
14 (14.00%) high severe
Dispatch::get_clone/global
time: [8.3962 ns 8.4000 ns 8.4054 ns]
change: [-19.126% -18.961% -18.817%] (p = 0.00 < 0.05)
Performance has improved.
Found 15 outliers among 100 measurements (15.00%)
2 (2.00%) low severe
6 (6.00%) high mild
7 (7.00%) high severe
```
```
Running benches/dispatch_get_ref.rs (target/release/deps/dispatch_get_ref-6ce05749a0b1bf87)
Dispatch::get_ref/none time: [1.7551 ns 1.7564 ns 1.7579 ns]
change: [-51.858% -51.749% -51.644%] (p = 0.00 < 0.05)
Performance has improved.
Found 10 outliers among 100 measurements (10.00%)
3 (3.00%) low mild
2 (2.00%) high mild
5 (5.00%) high severe
Dispatch::get_ref/scoped
time: [3.6341 ns 3.6365 ns 3.6397 ns]
change: [-2.6892% -2.5955% -2.4968%] (p = 0.00 < 0.05)
Performance has improved.
Found 12 outliers among 100 measurements (12.00%)
5 (5.00%) high mild
7 (7.00%) high severe
Dispatch::get_ref/global
time: [1.7668 ns 1.7686 ns 1.7713 ns]
change: [-52.697% -52.647% -52.603%] (p = 0.00 < 0.05)
Performance has improved.
Found 7 outliers among 100 measurements (7.00%)
2 (2.00%) high mild
5 (5.00%) high severe
```
```
Running benches/empty_span.rs (target/release/deps/empty_span-745c777d77b8b7ca)
empty_span/none time: [227.02 ps 227.10 ps 227.20 ps]
change: [-0.1729% -0.0705% +0.0495%] (p = 0.24 > 0.05)
No change in performance detected.
Found 10 outliers among 100 measurements (10.00%)
5 (5.00%) high mild
5 (5.00%) high severe
empty_span/scoped time: [218.51 ps 218.69 ps 218.90 ps]
change: [-0.7582% -0.6056% -0.4630%] (p = 0.00 < 0.05)
Change within noise threshold.
Found 8 outliers among 100 measurements (8.00%)
5 (5.00%) high mild
3 (3.00%) high severe
empty_span/global time: [217.85 ps 218.15 ps 218.56 ps]
change: [-2.6528% -2.4341% -2.1602%] (p = 0.00 < 0.05)
Performance has improved.
Found 8 outliers among 100 measurements (8.00%)
4 (4.00%) high mild
4 (4.00%) high severe
empty_span/baseline_struct
time: [655.54 ps 656.09 ps 656.76 ps]
change: [-1.6595% -1.4125% -1.1776%] (p = 0.00 < 0.05)
Performance has improved.
Found 7 outliers among 100 measurements (7.00%)
5 (5.00%) high mild
2 (2.00%) high severe
```
```
Running benches/enter_span.rs (target/release/deps/enter_span-7fc1c2a69c076475)
enter_span/none time: [0.0000 ps 0.0000 ps 0.0000 ps]
change: [-43.600% +6.5764% +109.38%] (p = 0.86 > 0.05)
No change in performance detected.
Found 14 outliers among 100 measurements (14.00%)
6 (6.00%) high mild
8 (8.00%) high severe
enter_span/scoped time: [2.6513 ns 2.6567 ns 2.6641 ns]
change: [+0.3121% +1.9504% +3.4648%] (p = 0.01 < 0.05)
Change within noise threshold.
Found 9 outliers among 100 measurements (9.00%)
2 (2.00%) high mild
7 (7.00%) high severe
enter_span/global time: [3.2108 ns 3.2160 ns 3.2220 ns]
change: [+25.963% +26.742% +27.434%] (p = 0.00 < 0.05)
Performance has regressed.
Found 2 outliers among 100 measurements (2.00%)
2 (2.00%) high mild
```
```
Running benches/event.rs (target/release/deps/event-6742eef6ebe07aa4)
event/none time: [227.04 ps 227.18 ps 227.41 ps]
change: [-1.6751% -1.5743% -1.4711%] (p = 0.00 < 0.05)
Performance has improved.
Found 13 outliers among 100 measurements (13.00%)
6 (6.00%) high mild
7 (7.00%) high severe
event/scoped time: [8.3849 ns 8.4335 ns 8.4888 ns]
change: [-3.4754% -3.0252% -2.6092%] (p = 0.00 < 0.05)
Performance has improved.
Found 5 outliers among 100 measurements (5.00%)
3 (3.00%) high mild
2 (2.00%) high severe
event/scoped_recording time: [36.916 ns 37.022 ns 37.194 ns]
change: [+8.1054% +18.714% +30.381%] (p = 0.00 < 0.05)
Performance has regressed.
Found 10 outliers among 100 measurements (10.00%)
1 (1.00%) low mild
2 (2.00%) high mild
7 (7.00%) high severe
event/global time: [6.9694 ns 7.1677 ns 7.3469 ns]
change: [-23.407% -21.940% -20.398%] (p = 0.00 < 0.05)
Performance has improved.
```
```
Running benches/span_fields.rs (target/release/deps/span_fields-96dfd0a8a577dec6)
span_fields/none time: [3.5936 ns 3.6008 ns 3.6106 ns]
change: [+17.160% +17.776% +18.413%] (p = 0.00 < 0.05)
Performance has regressed.
Found 14 outliers among 100 measurements (14.00%)
8 (8.00%) high mild
6 (6.00%) high severe
span_fields/scoped time: [33.751 ns 33.765 ns 33.779 ns]
change: [+22.689% +22.873% +23.037%] (p = 0.00 < 0.05)
Performance has regressed.
Found 7 outliers among 100 measurements (7.00%)
1 (1.00%) low mild
4 (4.00%) high mild
2 (2.00%) high severe
span_fields/scoped_recording
time: [270.22 ns 270.55 ns 270.91 ns]
change: [+10.615% +10.827% +11.028%] (p = 0.00 < 0.05)
Performance has regressed.
Found 6 outliers among 100 measurements (6.00%)
6 (6.00%) high mild
span_fields/global time: [28.337 ns 28.428 ns 28.527 ns]
change: [+3.0582% +3.3355% +3.6278%] (p = 0.00 < 0.05)
Performance has regressed.
Found 13 outliers among 100 measurements (13.00%)
13 (13.00%) high mild
```
```
Running benches/span_no_fields.rs (target/release/deps/span_no_fields-f8c7d7a84f720442)
span_no_fields/none time: [1.5467 ns 1.5507 ns 1.5553 ns]
change: [+12.966% +13.206% +13.434%] (p = 0.00 < 0.05)
Performance has regressed.
Found 8 outliers among 100 measurements (8.00%)
7 (7.00%) high mild
1 (1.00%) high severe
span_no_fields/scoped time: [17.796 ns 17.810 ns 17.826 ns]
change: [+1.0381% +1.1673% +1.2914%] (p = 0.00 < 0.05)
Performance has regressed.
Found 12 outliers among 100 measurements (12.00%)
6 (6.00%) high mild
6 (6.00%) high severe
span_no_fields/scoped_recording
time: [30.397 ns 30.459 ns 30.524 ns]
change: [-0.8489% -0.6268% -0.3915%] (p = 0.00 < 0.05)
Change within noise threshold.
span_no_fields/global time: [12.747 ns 12.791 ns 12.844 ns]
change: [-27.930% -27.672% -27.386%] (p = 0.00 < 0.05)
Performance has improved.
```
```
Running benches/span_repeated.rs (target/release/deps/span_repeated-03bfaaf4ecd13d36)
span_repeated/none time: [699.28 ns 699.84 ns 700.53 ns]
change: [+2.4125% +2.6359% +2.8862%] (p = 0.00 < 0.05)
Performance has regressed.
Found 9 outliers among 100 measurements (9.00%)
7 (7.00%) high mild
2 (2.00%) high severe
span_repeated/scoped time: [2.5029 µs 2.5057 µs 2.5090 µs]
change: [+4.5095% +4.6605% +4.8122%] (p = 0.00 < 0.05)
Performance has regressed.
Found 16 outliers among 100 measurements (16.00%)
8 (8.00%) low mild
6 (6.00%) high mild
2 (2.00%) high severe
span_repeated/scoped_recording
time: [5.0509 µs 5.0535 µs 5.0566 µs]
change: [+0.7346% +1.0724% +1.3718%] (p = 0.00 < 0.05)
Change within noise threshold.
Found 13 outliers among 100 measurements (13.00%)
6 (6.00%) high mild
7 (7.00%) high severe
span_repeated/global time: [2.1264 µs 2.1272 µs 2.1282 µs]
change: [-11.213% -11.119% -11.031%] (p = 0.00 < 0.05)
Performance has improved.
Found 10 outliers among 100 measurements (10.00%)
5 (5.00%) high mild
5 (5.00%) high severe
```
</details>
This branch adds documentation and tests noting that the `#[instrument]`
macro accepts `tracing::Level` directly. Using `tracing::Level` directly
allows for IDE autocomplete and earlier detection of typos.
The documentation for tracing-attributes was also rewritten to remove
the usage of the second-person perspective, making it more consistent
with the rest of tracing's documentation.
Co-authored-by: David Barsky <me@davidbarsky.com>
; Conflicts:
; tracing-attributes/Cargo.toml
; tracing-attributes/src/lib.rs
## Motivation
Clippy check fails in recent CI runs in v0.1.x branch PRs, for example
this run:
https://github.com/tokio-rs/tracing/actions/runs/4641107803/jobs/8215263838
Relevant error logs:
```
error: lint `const_err` has been removed: converted into hard error, see issue #71800 <https://github.com/rust-lang/rust/issues/71800> for more information
--> tracing-core/src/lib.rs:132:5
|
132 | const_err,
| ^^^^^^^^^
|
= note: `-D renamed-and-removed-lints` implied by `-D warnings`
error: deref which would be done by auto-deref
--> tracing-core/src/dispatcher.rs:371:26
|
371 | return f(&*entered.current());
| ^^^^^^^^^^^^^^^^^^^ help: try this: `&entered.current()`
|
= help: for further information visit https://rust-lang.github.io/rust-clippy/master/index.html#explicit_auto_deref
= note: `-D clippy::explicit-auto-deref` implied by `-D warnings`
error: deref which would be done by auto-deref
--> tracing-core/src/dispatcher.rs:393:20
|
393 | Some(f(&*entered.current()))
| ^^^^^^^^^^^^^^^^^^^ help: try this: `&entered.current()`
|
= help: for further information visit https://rust-lang.github.io/rust-clippy/master/index.html#explicit_auto_deref
```
## Solution
Fix the warnings based on the suggestions for Clippy.
# 0.1.30 (October 6, 2022)
This release of `tracing-core` adds a new `on_register_dispatch` method
to the `Subscriber` trait to allow the `Subscriber` to perform
initialization after being registered as a `Dispatch`, and a
`WeakDispatch` type to allow a `Subscriber` to store its own `Dispatch`
without creating reference count cycles.
### Added
- `Subscriber::on_register_dispatch` method ([#2269])
- `WeakDispatch` type and `Dispatch::downgrade()` function ([#2293])
Thanks to @jswrenn for contributing to this release!
[#2269]: https://github.com/tokio-rs/tracing/pull/2269
[#2293]: https://github.com/tokio-rs/tracing/pull/2293
Allows `Subscriber`s and `Layer`s to stash their own `Dispatch` without
causing a memory leak.
## Motivation
Resolves a shortcoming of #2269: that it's impossible for `Subscriber`s
or `Layer`s to stash a copy of their own `Dispatch` without creating a
reference cycle that would prevent them from being dropped.
## Solution
Introduces `WeakDispatch` (analogous to `std::sync::Weak`) that holds a
weak pointer to a `Subscriber`. `WeakDispatch` can be created via
`Dispatch::downgrade`, and can be transformed into a `Dispatch` via
`WeakDispatch::upgrade`.
Co-authored-by: Eliza Weisman <eliza@buoyant.io>
The `on_register_dispatch` method is invoked when a `Subscriber` is
registered as a `Dispatch`. This method should be overridden to
perform actions upon the installation of a subscriber/layer;
for instance, to send a copy of the subscriber's `Dispatch` to a
worker thread.
# 0.1.29 (July 29, 2022)
This release of `tracing-core` adds `PartialEq` and `Eq` implementations
for metadata types, and improves error messages when setting the global
default subscriber fails.
### Added
- `PartialEq` and `Eq` implementations for `Metadata` ([#2229])
- `PartialEq` and `Eq` implementations for `FieldSet` ([#2229])
### Fixed
- Fixed unhelpful `fmt::Debug` output for
`dispatcher::SetGlobalDefaultError` ([#2250])
- Fixed compilation with `-Z minimal-versions` ([#2246])
Thanks to @jswrenn and @CAD97 for contributing to this release!
[#2229]: https://github.com/tokio-rs/tracing/pull/2229
[#2246]: https://github.com/tokio-rs/tracing/pull/2246
[#2250]: https://github.com/tokio-rs/tracing/pull/2250
## Motivation
When a global default dispatcher has already been set, the
`dispatch::set_global_default` function fails with a
`SetGlobalDefaultError`. The `fmt::Display` impl for this type includes
a message explaining that the error indicates that a global default has
already been set, but the `fmt::Debug` impl is derived, and just looks
like this:
```
SetGlobalDefaultError { _no_construct: () }
```
which isn't particularly helpful.
Unfortunately, when `unwrap()`ping or `expect()`ing a `Result`, the
`fmt::Debug` implementation for the error type is used, rather than
`fmt::Display`. This means that the error message will not explain to
the user why setting the global default dispatcher failed, which is a
bummer.
## Solution
This branch replaces the derived `Debug` impl with a manually
implemented one that prints the same message as the `Display` impl, but
formatted like a tuple struct with a single string field. This avoids
emitting `Debug` output that's *just* a textual human-readable message,
rather than looking like Rust code, but ensures the message is visible
to the user when writing code like
```rust
tracing::dispatch::set_global_default(foo).unwrap();
```
The mesasge now looks like:
```
SetGlobalDefaultError("a global default trace dispatcher has already been set")
```
which should be a bit easier to debug.
## Motivation
Fix minimal-versions failure.
## Solution
Upgrade all the dependencies to their most recent semver-compatible
version, adjusting back down as necessary for MSRV.
Essentially a cherry-pick of #2231, but redone by hand.
## Tests
- `cargo minimal-versions msrv verify -- cargo check --all-features`
- `cargo minimal-versions msrv verify -- cargo check --no-default-features`
## Methodology
- `cargo update && cargo upgrade --to-lockfile`
- Identify [a bug](https://github.com/killercup/cargo-edit/issues/750) and manually resolve it
- loop; upgrade transitive deps
- `cargo minimal-versions check --all-features`
- Identify failing dep
- `cargo minimal-versions tree -i dep --all-features`
- Find the closest dependency leading to pulling in `dep`
- `cargo add fixdep --optional` to force a more recent more-minimal-versions-correct version
- loop; downgrade to msrv
- `cargo minimal-versions msrv verify -- cargo check --all-features`
- Identify failing dep
- `cargo minimal-versions tree -i dep --all-features`
- Find the version that supports MSRV from lib.rs
- `cargo upgrade dep@msrv`
A `FieldSet` is equal to another `FieldSet` if they share the same
callsite and fields (provided in the same order). This ensures
that a `Field` applicable to one `FieldSet` is applicable to any
equal `FieldSet`. A `Metadata` is equal to another `Metadata` if
all of their contained metadata is exactly equal.
This change manually re-implements `PartialEq` and `Eq` for
`Metadata` and `FieldSet` to define their equality strictly in
terms of callsite equality. In debug builds, the equality of
these types' other fields is also checked.
Documentation is added to both `Metadata` and `FieldSet`
explaining this behavior.
The expectation that, in a well-behaving application, `Metadata`
and `FieldSet`s with equal callsites will be otherwise equal is
documented on `Callsite::metadata`. This is not a breaking change,
as previous releases did not define equality for `Metadata` or
`FieldSet`. The `Callsite` trait remains safe, as this expectation
is not (yet) a safety-critical property.
# 0.1.28 (June 23, 2022)
This release of `tracing-core` adds new `Value` implementations,
including one for `String`, to allow recording `&String` as a value
without having to call `as_str()` or similar, and for 128-bit integers
(`i128` and `u128`). In addition, it adds new methods and trait
implementations for `Subscriber`s.
### Added
- `Value` implementation for `String` ([#2164])
- `Value` implementation for `u128` and `i28` ([#2166])
- `downcast_ref` and `is` methods for `dyn Subscriber + Sync`,
`dyn Subscriber + Send`, and `dyn Subscriber + Send + Sync` ([#2160])
- `Subscriber::event_enabled` method to enable filtering based on
`Event` field
values ([#2008])
- `Subscriber` implementation for `Box<S: Subscriber + ?Sized>` and
`Arc<S: Subscriber + ?Sized>` ([#2161])
Thanks to @jswrenn and @CAD97 for contributing to this release!
[#2164]: https://github.com/tokio-rs/tracing/pull/2164
[#2166]: https://github.com/tokio-rs/tracing/pull/2166
[#2160]: https://github.com/tokio-rs/tracing/pull/2160
[#2008]: https://github.com/tokio-rs/tracing/pull/2008
[#2161]: https://github.com/tokio-rs/tracing/pull/2161
Currently, `no_std` targets use a vendored version of `lazy_static` that
uses the `spin` crate's `Once` type, while the `std` target uses the
`once_cell` crate's `Lazy` type. This is unfortunate, as the
`lazy_static` macro has a different interface from the `Lazy` cell type.
This increases the amount of code that differs based on whether or not
`std` is enabled.
This branch removes the vendored `lazy_static` macro and replaces it
with a reimplementation of `once_cell::sync::Lazy` that uses
`spin::Once` rather than `once_cell::sync::OnceCell` as the inner "once
type". Now, all code can be written against a `Lazy` struct with the
same interface, regardless of whether or not `std` is enabled.
Signed-off-by: Eliza Weisman <eliza@buoyant.io>
## Motivation
Allow filter layers to filter on the contents of events (see #2007).
## Solution
This branch adds a new `Subscriber::event_enabled` method, taking an
`Event` and returning `bool`. This is called before the
`Subscriber::event` method, and if it returns `false`,
`Subscriber::event` is not called.
For simple subscriber (e.g. not using `Layer`s), the `event_enabled`
method is not particulary necessary, as the subscriber can just skip the
`event` call. However, this branch also adds a new
`Layer::event_enabled` method, with the signature:
```rust
fn event_enabled(&self, event: &Event<'_>, ctx: Context<'_, S>) -> bool;
```
This is called before `Layer::on_event`, and if `event_enabled`
returns `false`, `on_event` is not called (nor is `Subscriber::event`).
This allows filter `Layer`s to filter out an `Event` based on its
fields.
Closes#2007
## Motivation
I've received a request at work to record 128-bit integers and realized
that we should probably support recording them.
## Solution
Added two methods to the `Visit` trait, `record_i128` and `record_u128`.
However, I didn't add the size conversions present for 64-bit integers,
as 128-bit integers are, at this time, more specialized.
These broader impls supersede the previous impls where the inner type was a
`dyn Subscriber`. With these generic impls, you no longer must (but
still can, if you wish) cast the inner type of a boxed or arc'd
subscriber to `dyn Subscriber` to use it as a `Subscriber`.
## Motivation
Currently, it is rather difficult to record `String`s as field values,
even though `&str` is a primitive `Value` type. For example, this code
does not currently compile:
```rust
let my_string = String::from("hello world!");
tracing::debug!(my_string);
```
Instead, it is necessary to explicitly call `String::as_str` or a
similar conversion method:
```rust
let my_string = String::from("hello world!");
tracing::debug!(my_string = my_string.as_str());
```
This is unfortunate, as it makes a fairly straightforward, commomplace
task (recording a `String` as a field) unnecessarily verbose.
## Solution
This branch adds an `impl Value for String` in `tracing-core`. The impl
simply calls `String::as_str` and then calls `record_str`. Because
`Value` takes an `&self`, and there are preexisting `impl<T: Value>
Value` for `&T` and `&mut T`, the string is not consumed, and `&String`
or `&mut String`s can also be used as `Value`s.
I've also added tests validating that this actually works.
Adds inherent `downcast_ref` and `is` inherent methods to:
- `dyn Subscriber + Send`
- `dyn Subscriber + Sync`
- `dyn Subscriber + Send + Sync`
- `Layered`
These additional implementations reduce the circumstances in which one
must cast to `dyn Subscriber` (which, previously, was the only type for
which `downcast_ref` and `is` were available).
## Motivation
This PR adds two new accessor functions that are useful for creating a
structured serde implementation for tracing.
This is a sort of "distilled" version of
https://github.com/tokio-rs/tracing/pull/2113, based on the `v0.1.x`
branch.
As it is unlikely that "structured serde" will be 1:1 compatible with
the existing JSON-based `tracing-serde` (or at least - I'm not sure how
to do it in a reasonable amount of effort), these functions will allow
me to make a separate crate to hold me over until breaking formatting
changes are possible in `tracing-serde`.
CC @hawkw, as we've discussed this pretty extensively
Replace `lazy_static` with `once_cell`. Fixes#2146.
## Motivation
`lazy_static!`, while a declarative macro, is a macro nonetheless. It
can add quite a bit of additional compilation time cost.
`once_cell::sync::Lazy` does the same thing with generics, and can be
used more flexibly (i.e. non-static lazily initialized values), and has
been proposed to be added to `std` (see linked issue).
I'm trying to reduce the compile time and dependency tree complexity of
a dependent project: [bevy](https://bevyengine.org), which is using
tracing. `lazy_static` and `once_cell` are both in our dependency tree
and both end up doing the same thing.
## Solution
Migrate to `once_cell`.
This adds a small note on the use of `DefaultCallsite` to the
`tracing-core` docs. I wanted to take care of this before publishing a
new `tracing-core` release.
Currently, there isn't a lot of documentation explaining what callsites
and registration are for, and how they work. There's some documentation
explaining this stuff, but it's all on the `register_callsite` *method*,
rather than in the `callsite` module itself. We should fix that.
This branch adds new documentation to `tracing-core`'s `callsite`
module. Hopefully this should shine some light on how this part of
tracing works.
Thanks to @JamesHallowell for fixing some typos!
Signed-off-by: Eliza Weisman <eliza@buoyant.io>