diff --git a/test/test-runner/src/logging.rs b/test/test-runner/src/logging.rs index 3c9aad9d15c6..224c32977572 100644 --- a/test/test-runner/src/logging.rs +++ b/test/test-runner/src/logging.rs @@ -1,10 +1,12 @@ use log::{Level, LevelFilter, Metadata, Record, SetLoggerError}; use once_cell::sync::Lazy; +use std::ffi::OsStr; use std::path::{Path, PathBuf}; use test_rpc::logging::Error; use test_rpc::logging::{LogFile, LogOutput, Output}; use tokio::{ - fs::read_to_string, + fs::File, + io::{self, AsyncBufReadExt, BufReader}, sync::{ broadcast::{channel, Receiver, Sender}, Mutex, @@ -12,6 +14,12 @@ use tokio::{ }; const MAX_OUTPUT_BUFFER: usize = 10_000; +/// Only consider files that end with ".log" +const INCLUDE_LOG_FILE_EXT: &str = "log"; +/// Ignore log files that contain ".old" +const EXCLUDE_LOG_FILE_CONTAIN: &str = ".old"; +/// Maximum number of lines that each log file may contain +const TRUNCATE_LOG_FILE_LINES: usize = 100; pub static LOGGER: Lazy = Lazy::new(|| { let (sender, listener) = channel(MAX_OUTPUT_BUFFER); @@ -69,7 +77,7 @@ async fn read_settings_file() -> Result { let mut settings_path = mullvad_paths::get_default_settings_dir() .map_err(|error| Error::Logs(format!("{}", error)))?; settings_path.push("settings.json"); - read_to_string(&settings_path) + read_truncated(&settings_path) .await .map_err(|error| Error::Logs(format!("{}: {}", settings_path.display(), error))) } @@ -82,7 +90,7 @@ async fn read_log_files() -> Result>, Error> { .map_err(|error| Error::Logs(format!("{}", error)))?; let mut log_files = Vec::new(); for path in paths { - let log_file = read_to_string(&path) + let log_file = read_truncated(&path) .await .map_err(|error| Error::Logs(format!("{}: {}", path.display(), error))) .map(|content| LogFile { @@ -98,14 +106,33 @@ async fn list_logs>(log_dir: T) -> Result, Error> { let mut dir_entries = tokio::fs::read_dir(&log_dir) .await .map_err(|e| Error::Logs(format!("{}: {}", log_dir.as_ref().display(), e)))?; - let log_extension = Some(std::ffi::OsStr::new("log")); let mut paths = Vec::new(); while let Ok(Some(entry)) = dir_entries.next_entry().await { let path = entry.path(); - if path.extension() == log_extension { + if let Some(u8_path) = path.to_str() { + if u8_path.contains(EXCLUDE_LOG_FILE_CONTAIN) { + continue; + } + } + if path.extension() == Some(OsStr::new(INCLUDE_LOG_FILE_EXT)) { paths.push(path); } } Ok(paths) } + +async fn read_truncated>(path: T) -> io::Result { + let mut output = vec![]; + let reader = BufReader::new(File::open(path).await?); + let mut lines = reader.lines(); + while let Some(line) = lines.next_line().await? { + output.push(line); + } + if output.len() > TRUNCATE_LOG_FILE_LINES { + let drop_count = output.len() - TRUNCATE_LOG_FILE_LINES; + // not the most efficient + output.drain(0..drop_count); + } + Ok(output.join("\n")) +}