"""Additional edge case tests for formatters to ensure robustness.""" from arcade_cli.formatters import ( HtmlFormatter, JsonFormatter, MarkdownFormatter, TextFormatter, ) class MockEvaluation: """Mock EvaluationResult for testing.""" def __init__( self, passed: bool = True, warning: bool = False, score: float = 1.0, failure_reason: str | None = None, results: list[dict] | None = None, ): self.passed = passed self.warning = warning self.score = score self.failure_reason = failure_reason self.results = results or [] def make_empty_results() -> list[list[dict]]: """Create empty evaluation results.""" return [[{"model": "gpt-4o", "suite_name": "empty_suite", "rubric": "Test", "cases": []}]] class TestFormatterEdgeCases: """Test edge cases that might not be covered elsewhere.""" def test_empty_results_all_formatters(self) -> None: """All formatters should handle empty results gracefully.""" results = make_empty_results() for formatter_class in [TextFormatter, MarkdownFormatter, HtmlFormatter, JsonFormatter]: formatter = formatter_class() output = formatter.format(results) assert output # Should produce some output assert "0" in output or "Total: 0" in output.lower() or '"total_cases": 0' in output def test_failed_only_with_zero_original_total(self) -> None: """Should handle original_counts with zero total without crashing.""" results = make_empty_results() # Edge case: original_counts with 0 total (shouldn't happen in practice but should be safe) original_counts = (0, 0, 0, 0) for formatter_class in [TextFormatter, MarkdownFormatter, HtmlFormatter, JsonFormatter]: formatter = formatter_class() # Should not raise ZeroDivisionError output = formatter.format(results, failed_only=True, original_counts=original_counts) assert output # Should produce some output def test_failed_only_with_empty_results_but_nonzero_original(self) -> None: """Should handle case where filtered results are empty but original had cases.""" results = make_empty_results() # All cases were filtered out, but there were originally 5 cases (all passed) original_counts = (5, 5, 0, 0) for formatter_class in [TextFormatter, MarkdownFormatter, HtmlFormatter, JsonFormatter]: formatter = formatter_class() output = formatter.format(results, failed_only=True, original_counts=original_counts) assert output # Should show original counts assert "5" in output def test_all_formatters_handle_none_original_counts(self) -> None: """All formatters should handle None original_counts gracefully.""" results = [[{ "model": "gpt-4o", "suite_name": "test", "rubric": "Test", "cases": [{ "name": "test_case", "input": "test", "evaluation": MockEvaluation(passed=False, score=0.0), }], }]] for formatter_class in [TextFormatter, MarkdownFormatter, HtmlFormatter, JsonFormatter]: formatter = formatter_class() # Should not crash with None original_counts output = formatter.format(results, failed_only=True, original_counts=None) assert output def test_comparative_with_missing_track_data(self) -> None: """Comparative formatters should handle missing track gracefully.""" # Create comparative result where one track is missing data results = [[ { "model": "gpt-4o", "suite_name": "Test Suite [track_a]", "track_name": "track_a", "rubric": None, "cases": [{ "name": "test_case", "input": "test", "evaluation": MockEvaluation(passed=True, score=1.0), }], }, { "model": "gpt-4o", "suite_name": "Test Suite [track_b]", "track_name": "track_b", "rubric": None, "cases": [], # Empty cases for this track }, ]] for formatter_class in [TextFormatter, MarkdownFormatter, HtmlFormatter, JsonFormatter]: formatter = formatter_class() output = formatter.format(results) assert output # Should mention both tracks assert "track_a" in output assert "track_b" in output def test_html_formatter_escapes_all_special_chars(self) -> None: """HTML formatter must escape all special characters to prevent XSS.""" results = [[{ "model": "gpt-4o", "suite_name": "Suite & Test", "rubric": "Test", "cases": [{ "name": "", "input": "test' OR '1'='1", "evaluation": MockEvaluation( passed=False, score=0.0, failure_reason="Error: ", ), }], }]] formatter = HtmlFormatter() output = formatter.format(results) # The template includes a legitimate