From 3cad55d20fd0ac2fe382cee983ee8739cf32773d Mon Sep 17 00:00:00 2001 From: Yuri Rousseff <49888082+YuriRDev@users.noreply.github.com> Date: Thu, 11 Apr 2024 20:27:38 -0300 Subject: [PATCH] feat(worker/monitor): add metrics collector (#6) Co-authored-by: Eduardo Lemos --- Cargo.lock | 324 ++++++++++++++++++++++++++++++++ Cargo.toml | 5 + proto/src/common/node.rs | 9 +- worker/Cargo.toml | 4 + worker/src/main.rs | 22 ++- worker/src/monitor/collector.rs | 51 +++++ worker/src/monitor/mod.rs | 1 + 7 files changed, 410 insertions(+), 6 deletions(-) create mode 100644 worker/src/monitor/collector.rs create mode 100644 worker/src/monitor/mod.rs diff --git a/Cargo.lock b/Cargo.lock index eadbab2..a05e117 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -2,12 +2,42 @@ # It is not intended for manual editing. version = 3 +[[package]] +name = "addr2line" +version = "0.21.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8a30b2e23b9e17a9f90641c7ab1549cd9b44f296d3ccbf309d2863cfe398a0cb" +dependencies = [ + "gimli", +] + +[[package]] +name = "adler" +version = "1.0.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f26201604c87b1e01bd3d98f8d5d9a8fcbb815e8cedb41ffccbeb4bf593a35fe" + [[package]] name = "autocfg" version = "1.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "d468802bab17cbc0cc575e9b053f41e72aa36bfa6b7f55e3529ffa43161b97fa" +[[package]] +name = "backtrace" +version = "0.3.71" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "26b05800d2e817c8b3b4b54abd461726265fa9789ae34330622f2db9ee696f9d" +dependencies = [ + "addr2line", + "cc", + "cfg-if", + "libc", + "miniz_oxide", + "object", + "rustc-demangle", +] + [[package]] name = "bty" version = "0.1.0-pre.1" @@ -19,6 +49,12 @@ dependencies = [ "uuid", ] +[[package]] +name = "cc" +version = "1.0.90" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8cd6604a82acf3039f1144f54b8eb34e91ffba622051189e71b781822d5ee1f5" + [[package]] name = "cfg-if" version = "1.0.0" @@ -35,10 +71,57 @@ dependencies = [ "serde", ] +[[package]] +name = "core-foundation-sys" +version = "0.8.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "06ea2b9bc92be3c2baa9334a323ebca2d6f074ff852cd1d7b11064035cd3868f" + +[[package]] +name = "crossbeam-deque" +version = "0.8.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "613f8cc01fe9cf1a3eb3d7f488fd2fa8388403e97039e2f73692932e291a770d" +dependencies = [ + "crossbeam-epoch", + "crossbeam-utils", +] + +[[package]] +name = "crossbeam-epoch" +version = "0.9.18" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5b82ac4a3c2ca9c3460964f020e1402edd5753411d7737aa39c3714ad1b5420e" +dependencies = [ + "crossbeam-utils", +] + +[[package]] +name = "crossbeam-utils" +version = "0.8.19" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "248e3bacc7dc6baa3b21e405ee045c3047101a49145e7e9eca583ab4c2ca5345" + [[package]] name = "ctl" version = "0.1.0" +[[package]] +name = "either" +version = "1.10.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "11157ac094ffbdde99aa67b23417ebdd801842852b500e395a45a9c0aac03e4a" + +[[package]] +name = "eyre" +version = "0.6.12" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7cd915d99f24784cdc19fd37ef22b97e3ff0ae756c7e492e9fbfe897d61e2aec" +dependencies = [ + "indenter", + "once_cell", +] + [[package]] name = "getrandom" version = "0.2.12" @@ -50,6 +133,24 @@ dependencies = [ "wasi", ] +[[package]] +name = "gimli" +version = "0.28.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4271d37baee1b8c7e4b708028c57d816cf9d2434acb33a549475f78c181f6253" + +[[package]] +name = "hermit-abi" +version = "0.3.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d231dfb89cfffdbc30e7fc41579ed6066ad03abda9e567ccafae602b97ec5024" + +[[package]] +name = "indenter" +version = "0.3.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ce23b50ad8242c51a442f3ff322d56b02f08852c77e4c0b4d3fd684abc89c683" + [[package]] name = "itoa" version = "1.0.10" @@ -62,6 +163,30 @@ version = "0.2.153" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "9c198f91728a82281a64e1f4f9eeb25d82cb32a5de251c6bd1b5154d63a8e7bd" +[[package]] +name = "memchr" +version = "2.7.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "523dc4f511e55ab87b694dc30d0f820d60906ef06413f93d4d7a1385599cc149" + +[[package]] +name = "miniz_oxide" +version = "0.7.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9d811f3e15f28568be3407c8e7fdb6514c1cda3cb30683f15b6a1a1dc4ea14a7" +dependencies = [ + "adler", +] + +[[package]] +name = "ntapi" +version = "0.4.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e8a3895c6391c39d7fe7ebc444a87eb2991b2a0bc718fdabd071eec617fc68e4" +dependencies = [ + "winapi", +] + [[package]] name = "num-traits" version = "0.2.18" @@ -71,12 +196,43 @@ dependencies = [ "autocfg", ] +[[package]] +name = "num_cpus" +version = "1.16.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4161fcb6d602d4d2081af7c3a45852d875a03dd337a6bfdd6e06407b61342a43" +dependencies = [ + "hermit-abi", + "libc", +] + +[[package]] +name = "object" +version = "0.32.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a6a622008b6e321afc04970976f62ee297fdbaa6f95318ca343e3eebb9648441" +dependencies = [ + "memchr", +] + +[[package]] +name = "once_cell" +version = "1.19.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3fdb12b2476b595f9358c5161aa467c2438859caa136dec86c26fdd2efe17b92" + [[package]] name = "paste" version = "1.0.14" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "de3145af08024dea9fa9914f381a17b8fc6034dfb00f3a84013f7ff43f29ed4c" +[[package]] +name = "pin-project-lite" +version = "0.2.13" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8afb450f006bf6385ca15ef45d71d2288452bc3683ce2e2cacc0d18e4be60b58" + [[package]] name = "proc-macro2" version = "1.0.79" @@ -106,6 +262,32 @@ dependencies = [ "proc-macro2", ] +[[package]] +name = "rayon" +version = "1.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e4963ed1bc86e4f3ee217022bd855b297cef07fb9eac5dfa1f788b220b49b3bd" +dependencies = [ + "either", + "rayon-core", +] + +[[package]] +name = "rayon-core" +version = "1.12.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1465873a3dfdaa8ae7cb14b4383657caab0b3e8a0aa9ae8e04b044854c8dfce2" +dependencies = [ + "crossbeam-deque", + "crossbeam-utils", +] + +[[package]] +name = "rustc-demangle" +version = "0.1.23" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d626bb9dae77e28219937af045c257c28bfd3f69333c512553507f5f9798cb76" + [[package]] name = "ryu" version = "1.0.17" @@ -154,6 +336,44 @@ dependencies = [ "unicode-ident", ] +[[package]] +name = "sysinfo" +version = "0.30.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0c385888ef380a852a16209afc8cfad22795dd8873d69c9a14d2e2088f118d18" +dependencies = [ + "cfg-if", + "core-foundation-sys", + "libc", + "ntapi", + "once_cell", + "rayon", + "windows", +] + +[[package]] +name = "tokio" +version = "1.36.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "61285f6515fa018fb2d1e46eb21223fff441ee8db5d0f1435e8ab4f5cdb80931" +dependencies = [ + "backtrace", + "num_cpus", + "pin-project-lite", + "tokio-macros", +] + +[[package]] +name = "tokio-macros" +version = "2.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5b8a1e28f2deaa14e508979454cb3a223b10b938b45af148bc0986de36f1923b" +dependencies = [ + "proc-macro2", + "quote", + "syn", +] + [[package]] name = "unicode-ident" version = "1.0.12" @@ -176,6 +396,110 @@ version = "0.11.0+wasi-snapshot-preview1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "9c8d87e72b64a3b4db28d11ce29237c246188f4f51057d65a7eab63b7987e423" +[[package]] +name = "winapi" +version = "0.3.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5c839a674fcd7a98952e593242ea400abe93992746761e38641405d28b00f419" +dependencies = [ + "winapi-i686-pc-windows-gnu", + "winapi-x86_64-pc-windows-gnu", +] + +[[package]] +name = "winapi-i686-pc-windows-gnu" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ac3b87c63620426dd9b991e5ce0329eff545bccbbb34f3be09ff6fb6ab51b7b6" + +[[package]] +name = "winapi-x86_64-pc-windows-gnu" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "712e227841d057c1ee1cd2fb22fa7e5a5461ae8e48fa2ca79ec42cfc1931183f" + +[[package]] +name = "windows" +version = "0.52.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e48a53791691ab099e5e2ad123536d0fff50652600abaf43bbf952894110d0be" +dependencies = [ + "windows-core", + "windows-targets", +] + +[[package]] +name = "windows-core" +version = "0.52.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "33ab640c8d7e35bf8ba19b884ba838ceb4fba93a4e8c65a9059d08afcfc683d9" +dependencies = [ + "windows-targets", +] + +[[package]] +name = "windows-targets" +version = "0.52.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7dd37b7e5ab9018759f893a1952c9420d060016fc19a472b4bb20d1bdd694d1b" +dependencies = [ + "windows_aarch64_gnullvm", + "windows_aarch64_msvc", + "windows_i686_gnu", + "windows_i686_msvc", + "windows_x86_64_gnu", + "windows_x86_64_gnullvm", + "windows_x86_64_msvc", +] + +[[package]] +name = "windows_aarch64_gnullvm" +version = "0.52.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bcf46cf4c365c6f2d1cc93ce535f2c8b244591df96ceee75d8e83deb70a9cac9" + +[[package]] +name = "windows_aarch64_msvc" +version = "0.52.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "da9f259dd3bcf6990b55bffd094c4f7235817ba4ceebde8e6d11cd0c5633b675" + +[[package]] +name = "windows_i686_gnu" +version = "0.52.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b474d8268f99e0995f25b9f095bc7434632601028cf86590aea5c8a5cb7801d3" + +[[package]] +name = "windows_i686_msvc" +version = "0.52.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1515e9a29e5bed743cb4415a9ecf5dfca648ce85ee42e15873c3cd8610ff8e02" + +[[package]] +name = "windows_x86_64_gnu" +version = "0.52.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5eee091590e89cc02ad514ffe3ead9eb6b660aedca2183455434b93546371a03" + +[[package]] +name = "windows_x86_64_gnullvm" +version = "0.52.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "77ca79f2451b49fa9e2af39f0747fe999fcda4f5e241b2898624dca97a1f2177" + +[[package]] +name = "windows_x86_64_msvc" +version = "0.52.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "32b752e52a2da0ddfbdbcc6fceadfeede4c939ed16d13e648833a61dfb611ed8" + [[package]] name = "worker" version = "0.1.0" +dependencies = [ + "eyre", + "proto", + "sysinfo", + "tokio", +] diff --git a/Cargo.toml b/Cargo.toml index 39389c3..b94b850 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -18,8 +18,12 @@ chrono = { version = "0.4", default-features = false, features = [ "std", "serde", ] } +eyre = "0.6.12" +reqwest = { version = "0.12.1" , features = ["json"] } serde = { version = "1", features = ["derive"] } serde_json = "1" +sysinfo = "0.30.7" +tokio = "1.36.0" uuid = { version = "1", features = ["serde", "v4"] } [workspace.lints.clippy] @@ -27,3 +31,4 @@ all = "warn" pedantic = "warn" wildcard_imports = "allow" module_name_repetitions = "allow" +cast_precision_loss = "allow" diff --git a/proto/src/common/node.rs b/proto/src/common/node.rs index fd24ce7..3cf8159 100644 --- a/proto/src/common/node.rs +++ b/proto/src/common/node.rs @@ -22,9 +22,10 @@ pub enum NodeKind { #[derive(Debug, Serialize, Deserialize)] pub struct Metrics { + /// The average CPU usage. pub cpu_usage: f64, - /// The total memory, in MiB. - pub mem_total_mib: f64, - /// The used memory, in MiB. - pub mem_used_mib: f64, + /// The total memory, in bytes. + pub mem_total: u64, + /// The used memory, in bytes. + pub mem_used: u64, } diff --git a/worker/Cargo.toml b/worker/Cargo.toml index 698f95d..7d8d599 100644 --- a/worker/Cargo.toml +++ b/worker/Cargo.toml @@ -7,3 +7,7 @@ edition.workspace = true workspace = true [dependencies] +eyre.workspace = true +proto.workspace = true +sysinfo.workspace = true +tokio = { workspace = true, features = ["rt-multi-thread", "macros", "time"] } diff --git a/worker/src/main.rs b/worker/src/main.rs index e7a11a9..2b6f31f 100644 --- a/worker/src/main.rs +++ b/worker/src/main.rs @@ -1,3 +1,21 @@ -fn main() { - println!("Hello, world!"); +use eyre::Result; +use tokio::time::{sleep, Duration}; + +use crate::monitor::collector::MetricsCollector; + +pub mod monitor; + +/// `clap` crate report interval placeholder +/// The value 500 is for quick visualization purposes. +const REPORT_INTERVAL_IN_MILLIS: u64 = 500; + +#[tokio::main] +async fn main() -> Result<()> { + let mut metrics_report: MetricsCollector = MetricsCollector::new(); + + loop { + sleep(Duration::from_millis(REPORT_INTERVAL_IN_MILLIS)).await; + let metrics = metrics_report.get_metrics(); + println!("{metrics:#?}"); + } } diff --git a/worker/src/monitor/collector.rs b/worker/src/monitor/collector.rs new file mode 100644 index 0000000..c6c4afa --- /dev/null +++ b/worker/src/monitor/collector.rs @@ -0,0 +1,51 @@ +use proto::common::node::Metrics; +use sysinfo::System; + +/// Responsable for collecting metrics about the System, such as +/// CPU Percentage Usage, Free Memory Space. +#[derive(Default)] +pub struct MetricsCollector { + system: System, +} + +impl MetricsCollector { + /// Instantiates a new [`MetricsCollector`]. + #[must_use] + pub fn new() -> Self { + MetricsCollector::default() + } + + /// Retruns the [`Metrics`] struct for the current system. + #[must_use] + pub fn get_metrics(&mut self) -> Metrics { + self.system.refresh_memory(); + self.system.refresh_cpu(); + + Metrics { + cpu_usage: self.get_cpu_usage(), + mem_total: self.get_total_memory(), + mem_used: self.get_used_memory(), + } + } + + fn get_cpu_usage(&mut self) -> f64 { + let amount_cpus = self.system.cpus().len(); + + let sum_cpus_usages: f64 = self + .system + .cpus() + .iter() + .map(|cpu| f64::from(cpu.cpu_usage())) + .sum(); + + sum_cpus_usages / amount_cpus as f64 + } + + fn get_total_memory(&mut self) -> u64 { + self.system.total_memory() + } + + fn get_used_memory(&mut self) -> u64 { + self.system.used_memory() + } +} diff --git a/worker/src/monitor/mod.rs b/worker/src/monitor/mod.rs new file mode 100644 index 0000000..e024786 --- /dev/null +++ b/worker/src/monitor/mod.rs @@ -0,0 +1 @@ +pub mod collector;