1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
//! Toolkit for monitoring tokio runtimes using the [`rustfoundry metrics api`].
//!
//! Rustfoundry provides a simple toolkit for registering tokio runtimes with a monitor and collecting runtime metrics
//! for registered runtimes.
//!
//! # Note
//! This is currently an [unstable API](https://docs.rs/rustfoundry/latest/rustfoundry/index.html#unstable-features).
//!
//! # Metrics
//! | Metric | Source | Labels (? indicates optional) |
//! |:-------------------------------------------------|:--------------------------------------------------------------------|:---------------------------------------|
//! | tokio_runtime_workers | [`tokio::runtime::RuntimeMetrics::num_workers`] | runtime_name?, runtime_id? |
//! | tokio_runtime_blocking_threads | [`tokio::runtime::RuntimeMetrics::num_blocking_threads`] | runtime_name?, runtime_id? |
//! | tokio_runtime_num_alive_tasks | [`tokio::runtime::RuntimeMetrics::num_alive_tasks`] | runtime_name?, runtime_id? |
//! | tokio_runtime_idle_blocking_threads | [`tokio::runtime::RuntimeMetrics::num_idle_blocking_threads`] | runtime_name?, runtime_id? |
//! | tokio_runtime_remote_schedules_total | [`tokio::runtime::RuntimeMetrics::remote_schedule_count`] | runtime_name?, runtime_id? |
//! | tokio_runtime_budget_forced_yields_total | [`tokio::runtime::RuntimeMetrics::budget_forced_yield_count`] | runtime_name?, runtime_id? |
//! | tokio_runtime_io_driver_fd_registrations_total | [`tokio::runtime::RuntimeMetrics::io_driver_fd_registered_count`] | runtime_name?, runtime_id? |
//! | tokio_runtime_io_driver_fd_deregistrations_total | [`tokio::runtime::RuntimeMetrics::io_driver_fd_deregistered_count`] | runtime_name?, runtime_id? |
//! | tokio_runtime_io_driver_fd_readies_total | [`tokio::runtime::RuntimeMetrics::io_driver_ready_count`] | runtime_name?, runtime_id? |
//! | tokio_runtime_global_queue_depth | [`tokio::runtime::RuntimeMetrics::global_queue_depth`] | runtime_name?, runtime_id? |
//! | tokio_runtime_blocking_queue_depth | [`tokio::runtime::RuntimeMetrics::blocking_queue_depth`] | runtime_name?, runtime_id? |
//! | tokio_runtime_worker_parks_total | [`tokio::runtime::RuntimeMetrics::worker_park_count`] | runtime_name?, runtime_id?, worker_idx |
//! | tokio_runtime_worker_noops_total | [`tokio::runtime::RuntimeMetrics::worker_noop_count`] | runtime_name?, runtime_id?, worker_idx |
//! | tokio_runtime_worker_task_steals_total | [`tokio::runtime::RuntimeMetrics::worker_steal_count`] | runtime_name?, runtime_id?, worker_idx |
//! | tokio_runtime_worker_steal_operations_total | [`tokio::runtime::RuntimeMetrics::worker_steal_operations`] | runtime_name?, runtime_id?, worker_idx |
//! | tokio_runtime_worker_polls_total | [`tokio::runtime::RuntimeMetrics::worker_poll_count`] | runtime_name?, runtime_id?, worker_idx |
//! | tokio_runtime_worker_busy_duration_micros_total | [`tokio::runtime::RuntimeMetrics::worker_total_busy_duration`] | runtime_name?, runtime_id?, worker_idx |
//! | tokio_runtime_worker_local_schedules_total | [`tokio::runtime::RuntimeMetrics::worker_local_schedule_count`] | runtime_name?, runtime_id?, worker_idx |
//! | tokio_runtime_worker_overflows_total | [`tokio::runtime::RuntimeMetrics::worker_overflow_count`] | runtime_name?, runtime_id?, worker_idx |
//! | tokio_runtime_worker_local_queue_depth | [`tokio::runtime::RuntimeMetrics::worker_local_queue_depth`] | runtime_name?, runtime_id?, worker_idx |
//! | tokio_runtime_worker_mean_poll_time_micros | [`tokio::runtime::RuntimeMetrics::worker_mean_poll_time`] | runtime_name?, runtime_id?, worker_idx |
//!
//! # Example
//! ```no_run
//! # use std::thread;
//! # use std::time::Duration;
//! # use rustfoundry::telemetry::tokio_runtime_metrics::{record_runtime_metrics_sample, register_runtime};
//! // create and monitor 8 runtimes spawned on other threads, then poll in the background from this one
//! for i in 0..8 {
//! let r = tokio::runtime::Builder::new_current_thread().enable_all().build().unwrap();
//!
//! register_runtime(None, Some(i), r.handle());
//!
//! thread::spawn(move || r.block_on(async {
//! loop {
//! println!("Poll");
//! tokio::time::sleep(Duration::from_secs(1)).await;
//! }
//! }));
//! }
//!
//! loop {
//! record_runtime_metrics_sample();
//!
//! // record metrics roughly twice a second
//! std::thread::sleep(Duration::from_secs_f32(0.5));
//! }
//! ```
//!
//! [`rustfoundry metrics api`]: crate::telemetry::metrics
use crateRuntimeHandle;
use Slab;
use Arc;
use Handle;
static MONITOR: Mutex = new;
/// Key for removing runtimes registered with the global monitor.
;
/// Add a runtime to the global monitor, optionally with a name and/or id in case you are monitoring multiple runtimes.
///
/// Runtimes should be uniquely identifiable by label/id tuple.
///
/// You can use IDs as either unique IDs among all runtimes or unique IDs within a namespace based on the runtime name.
///
/// This function returns a key which can later be used to remove the registered runtime.
/// Try and deregister a runtime, returning true if a runtime is tracked for the specified key, and false otherwise.
/// Record a sample of runtime metrics for each tracked runtime.