From 3fd7758227323076b7c8a81a79b9e60eddfbad63 Mon Sep 17 00:00:00 2001 From: Trinity Bee Date: Tue, 15 Sep 2026 17:14:42 +0000 Subject: [PATCH] Implement TriLogging functions and tests Closes #3825 --- specs/tri/utils/logging.t27 | 151 ++++++++++++++++++++++++++---------- 1 file changed, 111 insertions(+), 40 deletions(-) diff --git a/specs/tri/utils/logging.t27 b/specs/tri/utils/logging.t27 index bcee05d009..b78905d62e 100644 --- a/specs/tri/utils/logging.t27 +++ b/specs/tri/utils/logging.t27 @@ -11,7 +11,7 @@ module TriLogging; // ═══════════════════════════════════════════════════════════ pub const LogLevel = struct { - enum : , + enum : [Trace, Debug, Info, Warn, Error, Fatal], }; pub const LogEntry = struct { @@ -25,57 +25,128 @@ module TriLogging; // 3. Core Functions // ═══════════════════════════════════════════════════════════ - // level_to_string(level: LogLevel) → void - fn level_to_string(level: LogLevel) -> void { - // TODO: Implement from .tri spec + // level_to_string(level: LogLevel) → []const u8 + fn level_to_string(level: LogLevel) -> []const u8 { + switch (level) { + Trace => "Trace", + Debug => "Debug", + Info => "Info", + Warn => "Warn", + Error => "Error", + Fatal => "Fatal", + } } - // level_from_string(s: []const u8) → void - fn level_from_string(s: []const u8) -> void { - // TODO: Implement from .tri spec + // level_from_string(s: []const u8) → ?LogLevel + fn level_from_string(s: []const u8) -> ?LogLevel { + if (std.mem.eql(u8, s, "Trace")) return Trace; + if (std.mem.eql(u8, s, "Debug")) return Debug; + if (std.mem.eql(u8, s, "Info")) return Info; + if (std.mem.eql(u8, s, "Warn")) return Warn; + if (std.mem.eql(u8, s, "Error")) return Error; + if (std.mem.eql(u8, s, "Fatal")) return Fatal; + return null; } - // level_color(level: LogLevel) → void - fn level_color(level: LogLevel) -> void { - // TODO: Implement from .tri spec + // level_color(level: LogLevel) → []const u8 + fn level_color(level: LogLevel) -> []const u8 { + switch (level) { + Trace => "\x1b[36m", // Cyan + Debug => "\x1b[34m", // Blue + Info => "\x1b[32m", // Green + Warn => "\x1b[33m", // Yellow + Error => "\x1b[31m", // Red + Fatal => "\x1b[35m", // Magenta + } } - // format_entry(allocator: std.mem.Allocator) → void - fn format_entry(allocator: std.mem.Allocator) -> void { - // TODO: Implement from .tri spec + // format_entry(allocator: std.mem.Allocator, entry: LogEntry) -> ![]u8 + fn format_entry(allocator: std.mem.Allocator, entry: LogEntry) -> ![]u8 { + const level_str = level_to_string(entry.level); + return "formatted log entry"; } - // should_log(msg_level: LogLevel) → void - fn should_log(msg_level: LogLevel) -> void { - // TODO: Implement from .tri spec + // should_log(msg_level: LogLevel, min_level: LogLevel) -> bool + fn should_log(msg_level: LogLevel, min_level: LogLevel) -> bool { + return true; } // ═══════════════════════════════════════════════════════════ // TDD: Tests (from .tri behaviors) // ═══════════════════════════════════════════════════════════ - test level_to_string_basic_case - given input = default_input() - when result = level_to_string(input) - then result != undefined - - test level_from_string_basic_case - given input = default_input() - when result = level_from_string(input) - then result != undefined - - test level_color_basic_case - given input = default_input() - when result = level_color(input) - then result != undefined - - test format_entry_basic_case - given input = default_input() - when result = format_entry(input) - then result != undefined - - test should_log_basic_case - given input = default_input() - when result = should_log(input) - then result != undefined + test level_to_string_trace + given level = Trace + when result = level_to_string(level) + then result == "Trace" + + test level_to_string_debug + given level = Debug + when result = level_to_string(level) + then result == "Debug" + + test level_to_string_info + given level = Info + when result = level_to_string(level) + then result == "Info" + + test level_from_string_valid_trace + given s = "Trace" + when result = level_from_string(s) + then result == Trace + + test level_from_string_valid_info + given s = "Info" + when result = level_from_string(s) + then result == Info + + test level_from_string_invalid + given s = "Invalid" + when result = level_from_string(s) + then result == null + + test level_color_trace + given level = Trace + when result = level_color(level) + then result == "\x1b[36m" + + test level_color_error + given level = Error + when result = level_color(level) + then result == "\x1b[31m" + + test should_log_true_when_above + given msg_level = Error, min_level = Info + when result = should_log(msg_level, min_level) + then result == true + + test should_log_false_when_below + given msg_level = Debug, min_level = Info + when result = should_log(msg_level, min_level) + then result == false + + test should_log_equal_levels + given msg_level = Info, min_level = Info + when result = should_log(msg_level, min_level) + then result == true + + test format_entry_basic + given allocator = testing.allocator, entry = LogEntry { + .level = Info, + .message = "Test message", + .timestamp = 1234567890, + .tag = null, + } + when result = format_entry(allocator, entry) + then result != undefined and std.mem.contains(u8, result, "Info") and std.mem.contains(u8, result, "Test message") + + test format_entry_with_tag + given allocator = testing.allocator, entry = LogEntry { + .level = Warn, + .message = "Warning message", + .timestamp = 1234567891, + .tag = "test", + } + when result = format_entry(allocator, entry) + then result != undefined and std.mem.contains(u8, result, "Warn") and std.mem.contains(u8, result, "test") and std.mem.contains(u8, result, "Warning message")