From 7bd1990eb3e36f02ad53cb2fbf7450c605dafb89 Mon Sep 17 00:00:00 2001 From: antifallobst Date: Thu, 29 Jun 2023 20:17:54 +0200 Subject: [PATCH] feature (logging): added a logging backend and spreaded a few info log calls over the codebase --- Cargo.lock | 229 ++++++++++++++++++++++++++++++++++++++++++++++++ Cargo.toml | 4 +- src/accounts.rs | 42 +++++---- src/app/mod.rs | 6 +- src/main.rs | 20 ++++- src/ui/mod.rs | 39 ++++++--- 6 files changed, 302 insertions(+), 38 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 8b77802..93c16c6 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -58,6 +58,21 @@ dependencies = [ "memchr", ] +[[package]] +name = "android-tzdata" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e999941b234f3131b00bc13c22d06e8c5ff726d1b6318ac7eb276997bbb4fef0" + +[[package]] +name = "android_system_properties" +version = "0.1.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "819e7219dbd41043ac279b19830f2efc897156490d7fd6ea916720117ee66311" +dependencies = [ + "libc", +] + [[package]] name = "anyhow" version = "1.0.71" @@ -70,6 +85,12 @@ version = "0.13.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "d301b3b94cb4b2f23d7917810addbbaff90738e0ca2be692bd027e70d7e0330c" +[[package]] +name = "arc-swap" +version = "1.6.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bddcadddf5e9015d310179a59bb28c4d4b9920ad0f11e8e14dbadf654890c9a6" + [[package]] name = "arrayref" version = "0.3.7" @@ -324,6 +345,21 @@ dependencies = [ "zeroize", ] +[[package]] +name = "chrono" +version = "0.4.26" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ec837a71355b28f6556dbd569b37b3f363091c0bd4b2e735674521b4c5fd9bc5" +dependencies = [ + "android-tzdata", + "iana-time-zone", + "js-sys", + "num-traits", + "time", + "wasm-bindgen", + "winapi", +] + [[package]] name = "cipher" version = "0.3.0" @@ -535,6 +571,17 @@ dependencies = [ "const-oid", ] +[[package]] +name = "derivative" +version = "2.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fcc3dd5e9e9c0b295d6e1e4d811fb6f157d5ffd784b8d202fc62eac8035a770b" +dependencies = [ + "proc-macro2 1.0.63", + "quote 1.0.29", + "syn 1.0.109", +] + [[package]] name = "derive_builder" version = "0.11.2" @@ -566,6 +613,12 @@ dependencies = [ "syn 1.0.109", ] +[[package]] +name = "destructure_traitobject" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3c877555693c14d2f84191cfd3ad8582790fc52b5e2274b40b59cf5f5cea25c7" + [[package]] name = "digest" version = "0.9.0" @@ -1004,6 +1057,12 @@ version = "1.0.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "c4a1e36c821dbe04574f602848a19f742f4fb3c98d40449f11bcad18d6b17421" +[[package]] +name = "humantime" +version = "2.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9a3a5bfb195931eeb336b2a7b4d761daec841b97f947d34394601737a7bba5e4" + [[package]] name = "hyper" version = "0.14.27" @@ -1041,6 +1100,29 @@ dependencies = [ "tokio-native-tls", ] +[[package]] +name = "iana-time-zone" +version = "0.1.57" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2fad5b825842d2b38bd206f3e81d6957625fd7f0a361e345c30e01a0ae2dd613" +dependencies = [ + "android_system_properties", + "core-foundation-sys", + "iana-time-zone-haiku", + "js-sys", + "wasm-bindgen", + "windows", +] + +[[package]] +name = "iana-time-zone-haiku" +version = "0.1.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f31827a206f56af32e590ba56d5d2d085f558508192593743f16b2306495269f" +dependencies = [ + "cc", +] + [[package]] name = "ident_case" version = "1.0.1" @@ -1185,6 +1267,12 @@ version = "0.2.147" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "b4668fb0ea861c1df094127ac5f1da3409a82116a4ba74fca2e58ef927159bb3" +[[package]] +name = "linked-hash-map" +version = "0.5.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0717cef1bc8b636c6e1c1bbdefc09e6322da8a9321966e8928ef80d20f7f770f" + [[package]] name = "linux-raw-sys" version = "0.3.8" @@ -1206,6 +1294,41 @@ name = "log" version = "0.4.19" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "b06a4cde4c0f271a446782e3eff8de789548ce57dbc8eca9292c27f4a42004b4" +dependencies = [ + "serde", +] + +[[package]] +name = "log-mdc" +version = "0.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a94d21414c1f4a51209ad204c1776a3d0765002c76c6abcb602a6f09f1e881c7" + +[[package]] +name = "log4rs" +version = "1.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d36ca1786d9e79b8193a68d480a0907b612f109537115c6ff655a3a1967533fd" +dependencies = [ + "anyhow", + "arc-swap", + "chrono", + "derivative", + "fnv", + "humantime", + "libc", + "log", + "log-mdc", + "parking_lot 0.12.1", + "serde", + "serde-value", + "serde_json", + "serde_yaml", + "thiserror", + "thread-id", + "typemap-ors", + "winapi", +] [[package]] name = "lru" @@ -1471,6 +1594,15 @@ dependencies = [ "winapi", ] +[[package]] +name = "num-traits" +version = "0.2.15" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "578ede34cf02f8924ab9447f50c28075b4d3e5b269972345e7e0372b38c6cdcd" +dependencies = [ + "autocfg 1.1.0", +] + [[package]] name = "num_cpus" version = "1.15.0" @@ -1546,6 +1678,15 @@ dependencies = [ "vcpkg", ] +[[package]] +name = "ordered-float" +version = "2.10.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7940cf2ca942593318d07fcf2596cdca60a85c9e7fab408a5e21a4f9dcd40d87" +dependencies = [ + "num-traits", +] + [[package]] name = "overload" version = "0.1.1" @@ -2193,6 +2334,16 @@ dependencies = [ "serde_derive", ] +[[package]] +name = "serde-value" +version = "0.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f3a1a3341211875ef120e117ea7fd5228530ae7e7036a779fdc9117be6b3282c" +dependencies = [ + "ordered-float", + "serde", +] + [[package]] name = "serde_bytes" version = "0.11.9" @@ -2236,6 +2387,18 @@ dependencies = [ "serde", ] +[[package]] +name = "serde_yaml" +version = "0.8.26" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "578a7433b776b56a35785ed5ce9a7e777ac0598aac5a6dd1b4b18a307c7fc71b" +dependencies = [ + "indexmap 1.9.3", + "ryu", + "serde", + "yaml-rust", +] + [[package]] name = "sha2" version = "0.9.9" @@ -2434,6 +2597,17 @@ dependencies = [ "syn 2.0.22", ] +[[package]] +name = "thread-id" +version = "4.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3ee93aa2b8331c0fec9091548843f2c90019571814057da3b783f9de09349d73" +dependencies = [ + "libc", + "redox_syscall 0.2.16", + "winapi", +] + [[package]] name = "thread_local" version = "1.1.7" @@ -2444,6 +2618,17 @@ dependencies = [ "once_cell", ] +[[package]] +name = "time" +version = "0.1.45" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1b797afad3f312d1c66a56d11d0316f916356d11bd158fbc6ca6389ff6bf805a" +dependencies = [ + "libc", + "wasi 0.10.0+wasi-snapshot-preview1", + "winapi", +] + [[package]] name = "tinyvec" version = "1.6.0" @@ -2608,6 +2793,8 @@ version = "0.1.0" dependencies = [ "anyhow", "crossterm", + "log", + "log4rs", "matrix-sdk", "serde", "tokio", @@ -2645,6 +2832,15 @@ dependencies = [ "tui", ] +[[package]] +name = "typemap-ors" +version = "1.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a68c24b707f02dd18f1e4ccceb9d49f2058c2fb86384ef9972592904d7a28867" +dependencies = [ + "unsafe-any-ors", +] + [[package]] name = "typenum" version = "1.16.0" @@ -2700,6 +2896,15 @@ dependencies = [ "subtle", ] +[[package]] +name = "unsafe-any-ors" +version = "1.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e0a303d30665362d9680d7d91d78b23f5f899504d4f08b3c4cf08d055d87c0ad" +dependencies = [ + "destructure_traitobject", +] + [[package]] name = "url" version = "2.4.0" @@ -2797,6 +3002,12 @@ version = "0.9.0+wasi-snapshot-preview1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "cccddf32554fecc6acb585f82a32a72e28b48f8c4c1883ddfeeeaa96f7d8e519" +[[package]] +name = "wasi" +version = "0.10.0+wasi-snapshot-preview1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1a143597ca7c7793eff794def352d41792a93c481eb1042423ff7ff72ba2c31f" + [[package]] name = "wasi" version = "0.11.0+wasi-snapshot-preview1" @@ -2924,6 +3135,15 @@ version = "0.4.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "712e227841d057c1ee1cd2fb22fa7e5a5461ae8e48fa2ca79ec42cfc1931183f" +[[package]] +name = "windows" +version = "0.48.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e686886bc078bc1b0b600cac0147aadb815089b6e4da64016cbd754b6342700f" +dependencies = [ + "windows-targets", +] + [[package]] name = "windows-sys" version = "0.42.0" @@ -3077,6 +3297,15 @@ dependencies = [ "zeroize", ] +[[package]] +name = "yaml-rust" +version = "0.4.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "56c1936c4cc7a1c9ab21a1ebb602eb942ba868cbd44a99cb7cdc5892335e1c85" +dependencies = [ + "linked-hash-map", +] + [[package]] name = "zeroize" version = "1.3.0" diff --git a/Cargo.toml b/Cargo.toml index f2cb96a..66c18a6 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -14,4 +14,6 @@ matrix-sdk = "0.6" anyhow = "1.0" tokio = { version = "1.0", features = ["macros", "rt-multi-thread"] } tracing-subscriber = "0.3" -serde = "1.0" \ No newline at end of file +serde = "1.0" +log = "0.4" +log4rs = "1.2" \ No newline at end of file diff --git a/src/accounts.rs b/src/accounts.rs index de042c8..2ab3072 100644 --- a/src/accounts.rs +++ b/src/accounts.rs @@ -1,4 +1,3 @@ -use std::borrow::{Borrow, BorrowMut}; use std::fs; use matrix_sdk::{Client, config::SyncSettings, @@ -8,6 +7,7 @@ use matrix_sdk::{Client, Session}; use anyhow::{Error, Result}; use serde::{Deserialize, Serialize}; +use log::{error, warn, info}; #[derive(Debug, Clone, Serialize, Deserialize)] pub struct Account { @@ -46,6 +46,7 @@ impl AccountsManager { pub fn new(config:Option) -> Self { return match config { Some(s) => { + info!("Loading serialized AccountsManager"); let accounts_data:AccountsData = serde_json::from_str(&s).expect("failed to deserialize json"); let mut clients = Vec::new(); clients.resize(accounts_data.accounts.len(), None); @@ -56,12 +57,15 @@ impl AccountsManager { clients, } }, - None => Self { - current_account: 0, - num_accounts: 0, - accounts: Vec::new(), - clients: Vec::new(), - }, + None => { + info!("Creating empty AccountsManager"); + Self { + current_account: 0, + num_accounts: 0, + accounts: Vec::new(), + clients: Vec::new(), + } + } } } @@ -75,22 +79,18 @@ impl AccountsManager { .build() .await?; - client - .login_username(username, password) + client.login_username(username, password) .initial_device_display_name("Trinitrix") .send() .await?; let session = client.session().expect("failed to get session"); - println!("logged in as '{username}' device ID: {}", session.device_id.as_str()); - - let account = Account { homeserver: homeserver.to_string(), id, name: client.account().get_display_name().await?.expect("failed to fetch display name"), - session, + session: session.clone(), sync_token: None }; @@ -98,9 +98,10 @@ impl AccountsManager { self.current_account = id; self.accounts.push(account); self.clients.push(Some(client)); - self.save()?; + info!("Logged in as '{}' device ID: {}", session.user_id.to_string(), session.device_id.to_string()); + Ok(id) } @@ -108,25 +109,26 @@ impl AccountsManager { self.logout().await?; // log out the current account let account = if account_id >= self.num_accounts { + error!("Tried to log in with an invalid account ID {}", account_id); return Err(Error::msg("Invalid account ID")); } else { self.get(account_id).expect("Account lookup failed") }; - if self.clients.get(account_id as usize).expect("client lookup failed").is_none() { + info!("No client cached for account: '{}' -> requesting a new one", &account.session.user_id); let client = Client::builder() .homeserver_url(&account.homeserver) .sled_store(format!("userdata/{account_id}"), Some("supersecure")) ? .build() .await?; client.restore_login(account.session.clone()).await?; - - println!("restored account: '{}' device ID: {}", &account.session.user_id, &account.session.device_id); } else { - println!("using cached client for account: '{}' device ID: {}", &account.session.user_id, &account.session.device_id); + info!("Using cached client for account: '{}'", &account.session.user_id); }; + info!("Restored account: '{}' device ID: {}", &account.session.user_id, &account.session.device_id); + self.current_account = account_id; Ok(()) @@ -142,7 +144,7 @@ impl AccountsManager { Some(c) => c, }; - println!("logged out {}", client.session().unwrap().user_id); + info!("Logged out '{}' locally", client.session().unwrap().user_id); client.logout().await?; Ok(()) @@ -157,6 +159,8 @@ impl AccountsManager { let serialized = serde_json::to_string(&accounts_data)?; fs::write("userdata/accounts.json", serialized)?; + info!("Saved serialized accounts config (userdata/accounts.json)"); + Ok(()) } diff --git a/src/app/mod.rs b/src/app/mod.rs index 576ed76..3ed81ac 100644 --- a/src/app/mod.rs +++ b/src/app/mod.rs @@ -1,9 +1,10 @@ -use std::path::Path; use crate::accounts; +use std::path::Path; use matrix_sdk::{Client}; use accounts::Account; use accounts::AccountsManager; +use log::{error, warn, info}; pub struct Message { pub author: String, @@ -25,6 +26,7 @@ impl App { pub fn new() -> Self { let path:&std::path::Path = Path::new("userdata/accounts.json"); let config = if path.exists() { + info!("Reading account config (userdata/accounts.json)"); Some(std::fs::read_to_string(path).expect("failed to read accounts config")) } else { None @@ -45,6 +47,8 @@ impl App { room.messages.push(Message {author: "someone".to_string(), message: "test".to_string()}); + info!("Filling in test data"); + self.rooms.push(room); } diff --git a/src/main.rs b/src/main.rs index e1e8934..d0d7887 100644 --- a/src/main.rs +++ b/src/main.rs @@ -2,21 +2,35 @@ mod ui; mod accounts; mod app; +use crate::ui::UI; use matrix_sdk::ruma::exports::serde_json; use tokio::time::{sleep, Duration}; use std::{io, thread}; -use crate::app::Message; -use crate::ui::UI; +use log::{error, warn, info, LevelFilter}; +use log4rs::append::file::FileAppender; +use log4rs::encode::pattern::PatternEncoder; +use log4rs::config::{Appender, Config, Root}; #[tokio::main] async fn main() -> anyhow::Result<()> { - tracing_subscriber::fmt::init(); + let logfile = FileAppender::builder() + .encoder(Box::new(PatternEncoder::new("{l} - {m}\n"))) + .build("userdata/output.log")?; + + let config = Config::builder() + .appender(Appender::builder().build("logfile", Box::new(logfile))) + .build(Root::builder() + .appender("logfile") + .build(LevelFilter::Info))?; + + log4rs::init_config(config)?; let mut app = app::App::new(); app.fill_test_data(); let mut ui = UI::new(); if app.accounts_manager.num_accounts() == 0 { + info!("No saved sessions found -> jumping into setup"); ui.setup(&mut app).await?; } diff --git a/src/ui/mod.rs b/src/ui/mod.rs index ace147d..e00d752 100644 --- a/src/ui/mod.rs +++ b/src/ui/mod.rs @@ -1,5 +1,6 @@ -use std::cmp; use crate::app::{App}; + +use std::cmp; use crossterm::{ event::{self, DisableMouseCapture, EnableMouseCapture, Event, read}, execute, @@ -9,13 +10,14 @@ use crossterm::{ use anyhow::{Error, Result}; use std::io::Stdout; use std::io; -use tui::{backend::CrosstermBackend, layout::{Constraint, Direction, Layout, Rect}, widgets::{Block, Borders, Widget}, Terminal, Frame}; +use tui::{backend::CrosstermBackend, layout::{Constraint, Direction, Layout}, widgets::{Block, Borders, Widget}, Terminal, Frame}; use tui::layout::Alignment; use tui::style::{Color, Modifier, Style}; use tui::text::{Spans, Span, Text}; use tui::widgets::{Paragraph, Wrap}; use tui_textarea::{Input, Key, TextArea}; use tui_textarea::Key::Char; +use log::{error, warn, info}; #[derive(Clone, Copy)] enum SetupInputPosition { @@ -46,7 +48,8 @@ fn terminal_prepare() -> Result { enable_raw_mode()?; let mut stdout = io::stdout(); execute!(stdout, EnterAlternateScreen, EnableMouseCapture)?; - return Ok(stdout); + info!("Prepared terminal"); + Ok(stdout) } fn textarea_activate(textarea: &mut TextArea) { @@ -81,6 +84,19 @@ fn cycle_main_input_position(input_position: &MainInputPosition) -> MainInputPos } } +impl Drop for UI<'_> { + fn drop(&mut self) { + info!("Destructing UI"); + disable_raw_mode().expect("While destructing UI -> Failed to disable raw mode"); + execute!( + self.terminal.backend_mut(), + LeaveAlternateScreen, + DisableMouseCapture + ).expect("While destructing UI -> Failed execute backend commands (LeaveAlternateScreen and DisableMouseCapture)"); + self.terminal.show_cursor().expect("While destructing UI -> Failed to re-enable cursor"); + } +} + impl UI<'_> { pub fn new() -> Self { let stdout = terminal_prepare().expect("failed to prepare terminal"); @@ -95,6 +111,8 @@ impl UI<'_> { .title("Message Compose") .borders(Borders::ALL)); + info!("Initialized UI"); + Self { terminal, input_position: MainInputPosition::Rooms, @@ -217,6 +235,8 @@ impl UI<'_> { } pub async fn main(&mut self, app: &mut App) -> Result<()> { + info!("Starting main UI"); + textarea_activate(&mut self.message_compose); self.terminal.clear().expect("failed to clear screen"); @@ -243,6 +263,8 @@ impl UI<'_> { } pub async fn setup(&mut self, app: &mut App) -> Result<()> { + info!("Starting setup UI"); + let mut input_index = SetupInputPosition::Homeserver; let mut strings: Vec = Vec::new(); strings.resize(3, "".to_string()); @@ -370,15 +392,4 @@ impl UI<'_> { }; } } - - pub fn close(&mut self) -> Result<()>{ - disable_raw_mode()?; - execute!( - self.terminal.backend_mut(), - LeaveAlternateScreen, - DisableMouseCapture - )?; - self.terminal.show_cursor()?; - Ok(()) - } }