|
1 | 1 | import re |
2 | 2 | from datetime import datetime, timedelta |
3 | 3 |
|
4 | | -from logscope.viewer import line_passes_level, line_passes_search, parse_level_filter, line_passes_filters |
| 4 | +from logscope.viewer import line_passes_level, line_passes_search, parse_level_filter, line_passes_filters, line_passes_min_level |
5 | 5 | from logscope.parser import LogEntry |
6 | 6 |
|
7 | 7 |
|
@@ -121,3 +121,49 @@ def test_line_passes_filters_exact_boundary(): |
121 | 121 |
|
122 | 122 | # Exact until should pass (inclusive) |
123 | 123 | assert line_passes_filters(entry, None, None, None, entry_time, pattern=None, use_regex=False, case_sensitive=False, invert_match=False) is True |
| 124 | + |
| 125 | + |
| 126 | +def test_line_passes_min_level_threshold(): |
| 127 | + """Test --min-level threshold filtering.""" |
| 128 | + # TRACE is lowest, FATAL is highest |
| 129 | + assert line_passes_min_level("TRACE", None) is True |
| 130 | + assert line_passes_min_level("TRACE", "TRACE") is True |
| 131 | + assert line_passes_min_level("TRACE", "DEBUG") is False |
| 132 | + assert line_passes_min_level("ERROR", "WARN") is True |
| 133 | + assert line_passes_min_level("ERROR", "ERROR") is True |
| 134 | + assert line_passes_min_level("ERROR", "CRITICAL") is False |
| 135 | + assert line_passes_min_level("FATAL", "ERROR") is True |
| 136 | + assert line_passes_min_level("FATAL", "FATAL") is True |
| 137 | + assert line_passes_min_level("INFO", "DEBUG") is True |
| 138 | + |
| 139 | + |
| 140 | +def test_line_passes_min_level_unknown_level(): |
| 141 | + """Test that UNKNOWN level is treated as lowest severity (same as TRACE).""" |
| 142 | + assert line_passes_min_level("UNKNOWN", None) is True |
| 143 | + # UNKNOWN has same severity as TRACE (0), so it passes TRACE threshold |
| 144 | + assert line_passes_min_level("UNKNOWN", "TRACE") is True |
| 145 | + # But fails higher thresholds |
| 146 | + assert line_passes_min_level("UNKNOWN", "DEBUG") is False |
| 147 | + assert line_passes_min_level("UNKNOWN", "INFO") is False |
| 148 | + |
| 149 | + |
| 150 | +def test_line_passes_min_level_case_insensitive(): |
| 151 | + """Test that min_level comparison is case-insensitive.""" |
| 152 | + assert line_passes_min_level("ERROR", "error") is True |
| 153 | + assert line_passes_min_level("ERROR", "WaRn") is True |
| 154 | + assert line_passes_min_level("INFO", "DEBUG") is True |
| 155 | + |
| 156 | + |
| 157 | +def test_line_passes_filters_with_min_level(): |
| 158 | + """Test --min-level combined with other filters.""" |
| 159 | + entry = make_entry(datetime(2026, 4, 5, 10, 0, 0), level="ERROR", message="error message") |
| 160 | + |
| 161 | + # Combined with level filter - ERROR passes both ERROR level set and min_level WARN |
| 162 | + assert line_passes_filters(entry, {"ERROR"}, None, None, None, pattern=None, use_regex=False, case_sensitive=False, invert_match=False, min_level="WARN") is True |
| 163 | + |
| 164 | + # ERROR doesn't pass level filter for INFO only |
| 165 | + assert line_passes_filters(entry, {"INFO"}, None, None, None, pattern=None, use_regex=False, case_sensitive=False, invert_match=False, min_level=None) is False |
| 166 | + |
| 167 | + # Combined with time filter |
| 168 | + since = datetime(2026, 4, 5, 9, 0, 0) |
| 169 | + assert line_passes_filters(entry, None, None, since, None, pattern=None, use_regex=False, case_sensitive=False, invert_match=False, min_level="WARN") is True |
0 commit comments