import pytest from datetime import datetime from src.models.data_structures import ( Author, Commit, FileChange, CommitAnalysis, CodeChurnAnalysis, RiskyCommitAnalysis, VelocityAnalysis, ) class TestAuthor: """Test Author dataclass.""" def test_author_creation(self): """Test creating an Author.""" author = Author( name="John Doe", email="john@example.com", commit_count=100, lines_added=5000, lines_deleted=1000, ) assert author.name == "John Doe" assert author.email == "john@example.com" assert author.commit_count == 100 class TestCommit: """Test Commit dataclass.""" def test_commit_creation(self): """Test creating a Commit.""" commit = Commit( sha="abc123", message="Test commit", author="John Doe", author_email="john@example.com", timestamp=datetime.now(), ) assert commit.sha == "abc123" assert commit.message == "Test commit" assert commit.lines_added == 0 assert commit.lines_deleted == 0 def test_commit_with_changes(self): """Test creating a Commit with changes.""" commit = Commit( sha="abc123", message="Test commit", author="John Doe", author_email="john@example.com", timestamp=datetime.now(), lines_added=100, lines_deleted=50, files_changed=["src/main.py", "tests/test.py"], is_merge=False, is_revert=False, ) assert len(commit.files_changed) == 2 assert commit.lines_added == 100 class TestFileChange: """Test FileChange dataclass.""" def test_file_change_creation(self): """Test creating a FileChange.""" change = FileChange( filepath="src/main.py", lines_added=50, lines_deleted=10, change_type="M", ) assert change.filepath == "src/main.py" assert change.lines_added == 50 class TestCommitAnalysis: """Test CommitAnalysis dataclass.""" def test_commit_analysis_creation(self): """Test creating a CommitAnalysis.""" analysis = CommitAnalysis( total_commits=100, unique_authors=5, commits_by_hour={"10:00": 10, "14:00": 15}, commits_by_day={"Monday": 20, "Tuesday": 15}, commits_by_week={"2024-W01": 50}, top_authors=[], average_commits_per_day=3.3, ) assert analysis.total_commits == 100 assert analysis.unique_authors == 5 class TestCodeChurnAnalysis: """Test CodeChurnAnalysis dataclass.""" def test_code_churn_analysis_creation(self): """Test creating a CodeChurnAnalysis.""" analysis = CodeChurnAnalysis( total_lines_added=5000, total_lines_deleted=1000, net_change=4000, churn_by_file={}, churn_by_author={}, high_churn_commits=[], average_churn_per_commit=50.0, ) assert analysis.total_lines_added == 5000 assert analysis.net_change == 4000 class TestRiskyCommitAnalysis: """Test RiskyCommitAnalysis dataclass.""" def test_risky_commit_analysis_creation(self): """Test creating a RiskyCommitAnalysis.""" analysis = RiskyCommitAnalysis( total_risky_commits=10, large_change_commits=[], merge_commits=[], revert_commits=[], risk_score=5.5, ) assert analysis.total_risky_commits == 10 class TestVelocityAnalysis: """Test VelocityAnalysis dataclass.""" def test_velocity_analysis_creation(self): """Test creating a VelocityAnalysis.""" analysis = VelocityAnalysis( commits_per_day=5.0, commits_per_week=35.0, commits_per_month=150.0, velocity_trend="stable", top_contributors=[], most_active_day="Monday", most_active_hour="10:00", ) assert analysis.commits_per_day == 5.0 assert analysis.velocity_trend == "stable"