diff --git a/.gitignore b/.gitignore index b97628c..a164028 100644 --- a/.gitignore +++ b/.gitignore @@ -1,3 +1,4 @@ /target .env -commands.yml \ No newline at end of file +commands.yml +*.log diff --git a/Cargo.lock b/Cargo.lock index a6b54e7..01ff6c2 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -65,6 +65,19 @@ version = "1.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd" +[[package]] +name = "chrono" +version = "0.4.19" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "670ad68c9088c2a963aaa298cb369688cf3f9465ce5e2d4ca10e6e0098a1ce73" +dependencies = [ + "libc", + "num-integer", + "num-traits", + "time 0.1.44", + "winapi", +] + [[package]] name = "const_fn" version = "0.4.7" @@ -78,7 +91,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "03a5d7b21829bc7b4bf4754a978a241ae54ea55a40f92bb20216e54096f4b951" dependencies = [ "percent-encoding", - "time", + "time 0.2.26", "version_check", ] @@ -94,7 +107,7 @@ dependencies = [ "publicsuffix", "serde", "serde_json", - "time", + "time 0.2.26", "url", ] @@ -430,10 +443,12 @@ name = "kotapi" version = "0.1.0" dependencies = [ "anyhow", + "chrono", "dotenv", "futures", "http", "linked-hash-map", + "log", "rand", "regex", "reqwest", @@ -546,6 +561,25 @@ dependencies = [ "winapi", ] +[[package]] +name = "num-integer" +version = "0.1.44" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d2cc698a63b549a70bc047073d2949cce27cd1c7b0a4a862d08a8031bc2801db" +dependencies = [ + "autocfg", + "num-traits", +] + +[[package]] +name = "num-traits" +version = "0.2.14" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9a64b1ec5cda2586e284722486d802acf1f7dbdc623e2bfc57e65ca1cd099290" +dependencies = [ + "autocfg", +] + [[package]] name = "num_cpus" version = "1.13.0" @@ -813,7 +847,7 @@ dependencies = [ "serde", "serde_json", "serde_urlencoded", - "time", + "time 0.2.26", "tokio", "tokio-native-tls", "url", @@ -1055,6 +1089,17 @@ dependencies = [ "winapi", ] +[[package]] +name = "time" +version = "0.1.44" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6db9e6914ab8b1ae1c260a4ae7a49b6c5611b40328a735b21862567685e73255" +dependencies = [ + "libc", + "wasi", + "winapi", +] + [[package]] name = "time" version = "0.2.26" @@ -1255,9 +1300,9 @@ dependencies = [ [[package]] name = "wasi" -version = "0.10.2+wasi-snapshot-preview1" +version = "0.10.0+wasi-snapshot-preview1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fd6fbd9a79829dd1ad0cc20627bf1ed606756a7f77edff7b66b7064f9cb327c6" +checksum = "1a143597ca7c7793eff794def352d41792a93c481eb1042423ff7ff72ba2c31f" [[package]] name = "wasm-bindgen" diff --git a/Cargo.toml b/Cargo.toml index 0de53f6..daf0ab0 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -17,4 +17,6 @@ http = "0.2.4" yaml-rust = "0.4.5" linked-hash-map = "0.5.4" regex = "1.5.4" -rand = "0.8.3" \ No newline at end of file +rand = "0.8.3" +log = "0.4.14" +chrono = "0.4.19" \ No newline at end of file diff --git a/src/commands/commandset.rs b/src/commands/commandset.rs index 99c5552..5ee2eee 100644 --- a/src/commands/commandset.rs +++ b/src/commands/commandset.rs @@ -10,6 +10,7 @@ use std::fs; use std::path::Path; use regex::Regex; use rand::seq::SliceRandom; +use log::{info, warn, error, debug}; #[derive(Debug, Clone)] pub struct Command { @@ -102,7 +103,7 @@ impl CommandSet { raw_command.extract_vec("replies"), raw_command.extract_string("execute"), ); - println!("entry: {:?}", parsed_command); + info!("Command entry: {:?}", parsed_command); match parsed_command { Ok(command) => { initial_commands.push(command); @@ -122,8 +123,6 @@ impl CommandSet { } } pub fn check_against_commands(&self, text: String) -> Option { - println!("checking {:#?}", text); - if self.help.is_match(&text.clone()) { let mut result = String::from(""); for command in self.commands.clone().into_iter() { @@ -132,14 +131,15 @@ impl CommandSet { command.clone().name.unwrap(), command.clone().regex, command.get_description()); + } + return Some(result); } - return Some(result); - } - - for command in self.commands.clone().into_iter() { - match command.check_against(text.clone()) { + + for command in self.commands.clone().into_iter() { + info!("checking regex {:?} against '{:#?}'", command.regex, text); + match command.check_against(text.clone()) { Some(result) => { - println!("COMMAND MATCH ON TEXT: {:#?} FOR COMMAND: {:#?}", text, command); + debug!("COMMAND MATCH ON TEXT: {:#?} FOR COMMAND: {:#?}", text, command); return Some(result); }, _ => {} @@ -156,7 +156,6 @@ trait ExtractString { impl ExtractString for LinkedHashMap { fn extract_string(&mut self, value: &str) -> Option { - // println!("Extracting {:?} from {:?}", value, self); match self.get(&Yaml::from_str(value)) { Some (value) => { value.to_owned().into_string() @@ -164,7 +163,6 @@ impl ExtractString for LinkedHashMap { } } fn extract_vec(&mut self, value: &str) -> Option> { - // println!("Extracting {:?} from {:?}", value, self); match self.get(&Yaml::from_str(value)) { Some (value) => { let mut result = Vec::new(); diff --git a/src/connection/model.rs b/src/connection/model.rs index 88ec7b9..85aa619 100644 --- a/src/connection/model.rs +++ b/src/connection/model.rs @@ -4,6 +4,7 @@ extern crate serde_json; // external use http::{HeaderMap, HeaderValue, header::{COOKIE}}; +use log::{info, warn, error, debug}; // local use crate::message::{InboundMessage, MessageQueue, OutboundMessage, PostResult}; @@ -77,8 +78,8 @@ impl ChanConnection { if self.lastpost != 0u32 { result = format!("{}&count={}", result, self.lastpost); } - println!("Retrieving get_url: {:#?} {:#?} {:#?}", self.raw_get_url, self.limit, self.lastpost); - println!("Result url: {}", result); + debug!("Retrieving get_url: {:#?} {:#?} {:#?}", self.raw_get_url, self.limit, self.lastpost); + info!("Result url: {}", result); return result; } @@ -95,8 +96,8 @@ impl ChanConnection { self.lastpost = message.count; let added_to_queue = self.queue.add_to_queue(message.clone(), is_bot).await?; if added_to_queue { - println!("Added a message to the queue: {:#?}", message.count); - println!("count: {:#?}\t is_bot: {:#?}\t is_replied_to {:#?}", message.count, is_bot, message.replied_to); + debug!("Added a message to the queue: {:#?}", message.count); + debug!("count: {:#?}\t is_bot: {:#?}\t is_replied_to {:#?}", message.count, is_bot, message.replied_to); if !is_bot && message.replied_to != Some(true) { match self.commands.check_against_commands(message.clone().body) { Some (reply_text) => { @@ -175,9 +176,9 @@ impl ChanConnection { pub async fn attempt_sending_outbound(&mut self) -> Result<(), anyhow::Error> { match self.queue.first_to_send() { Some(message) => { - println!("Sending out: {:?}", message); + debug!("Sending out: {:?}", message); let result: bool = self.send_message(message.clone()).await?; - println!("Sending out status: {:?}", result); + debug!("Sending out status: {:?}", result); match result { true => { self.queue.append_as_first(message); @@ -208,7 +209,6 @@ impl ChanConnection { .await?; let messages: Vec = serde_json::from_str(&response).unwrap(); - // println!("Messages: \n{:#?}", messages.clone()); self.process_messages(messages).await?; Ok(()) diff --git a/src/logger/logger.rs b/src/logger/logger.rs new file mode 100644 index 0000000..b4f6d32 --- /dev/null +++ b/src/logger/logger.rs @@ -0,0 +1,37 @@ +use log::{Record, Level, Metadata}; +use std::{fs::OpenOptions, io::Write, path::Path}; +// TODO: look into tokio::time usage +use chrono::prelude::*; + +pub struct AnnaLogger; + +impl log::Log for AnnaLogger { + fn enabled(&self, metadata: &Metadata) -> bool { + metadata.level() <= Level::Info + } + + // TODO: rewrite it so the file is held in memory instead of opened for each instance + fn log(&self, record: &Record) { + let logfile = "anna.log"; + if self.enabled(record.metadata()) { + println!("{} - {}", record.level(), record.args()); + } + let create = Path::new(logfile).exists(); + let mut file = OpenOptions::new() + .create(create) + .write(true) + .append(true) + .open(logfile) + .unwrap(); + writeln!( + file, + "{}:{} - {} in {}", + Utc::now(), + record.level(), + record.args(), + record.file().unwrap(), + ).unwrap(); + } + + fn flush(&self) {} +} \ No newline at end of file diff --git a/src/logger/mod.rs b/src/logger/mod.rs new file mode 100644 index 0000000..704953c --- /dev/null +++ b/src/logger/mod.rs @@ -0,0 +1,2 @@ +mod logger; +pub use logger::*; \ No newline at end of file diff --git a/src/main.rs b/src/main.rs index 9c47b02..3bd307c 100644 --- a/src/main.rs +++ b/src/main.rs @@ -1,6 +1,7 @@ use std::env; // use std::path::Path; use tokio::time::{sleep, Duration}; +use log::LevelFilter; extern crate dotenv; extern crate reqwest; @@ -11,13 +12,18 @@ extern crate anyhow; mod connection; mod message; mod commands; +mod logger; // external crates use dotenv::dotenv; +static LOGGER: logger::AnnaLogger = logger::AnnaLogger; + #[tokio::main] async fn main() -> Result<(), anyhow::Error> { dotenv().ok(); + + log::set_logger(&LOGGER).map(|()| log::set_max_level(LevelFilter::Info)).unwrap(); // anna_nolimit_cookie1 let anna_cookie = env::var("ANNA_COOKIE") diff --git a/src/message/model.rs b/src/message/model.rs index a0728dd..b150f31 100644 --- a/src/message/model.rs +++ b/src/message/model.rs @@ -1,8 +1,6 @@ -// #![feature(in_band_lifetimes)] - -use futures::future::Either; use serde::{Deserialize, Serialize}; use anyhow::Result; +use log::{info, warn, error, debug}; #[derive(Serialize, Debug, Clone)] pub struct OutboundMessage { @@ -28,7 +26,7 @@ impl PostResult { return self.success != None; } pub fn failed_to_send(&self) -> bool { - // println!("Checking PostResult: {:#?}", self); + debug!("Checking PostResult: {:#?}", self); match &self.failure { Some(reason) => reason == "countdown_violation", None => false