170 lines
5.9 KiB
Python
170 lines
5.9 KiB
Python
#!/usr/bin/env python3
|
|
import pytest
|
|
from unittest import mock
|
|
from sqlalchemy.orm import Session
|
|
from fastapi.testclient import TestClient
|
|
from datetime import datetime, timedelta
|
|
|
|
from app.main import app
|
|
from app.models import User, Team, Event, QRCode
|
|
from app.views.admin import get_user_statistics, get_team_statistics
|
|
from app.views.admin import get_event_statistics, get_system_health
|
|
|
|
# Fixture for mocking the database session
|
|
@pytest.fixture
|
|
def mock_db():
|
|
"""Create a mock database session for testing."""
|
|
mock_session = mock.MagicMock(spec=Session)
|
|
return mock_session
|
|
|
|
# Test cases for user statistics
|
|
def test_get_user_statistics(mock_db):
|
|
"""Test getting user statistics."""
|
|
# Setup mock query results
|
|
mock_db.query().count.side_effect = [100, 80, 20]
|
|
mock_db.query().filter().count.return_value = 10
|
|
|
|
# Get last 30 days
|
|
thirty_days_ago = datetime.now() - timedelta(days=30)
|
|
mock_db.query().filter().filter().count.return_value = 15
|
|
|
|
# Get the statistics
|
|
stats = get_user_statistics(mock_db)
|
|
|
|
# Assert the expected results
|
|
assert stats["total_users"] == 100
|
|
assert stats["active_users"] == 80
|
|
assert stats["verified_users"] == 20
|
|
assert stats["admin_users"] == 10
|
|
assert stats["new_registrations_30d"] == 15
|
|
|
|
# Test cases for team statistics
|
|
def test_get_team_statistics(mock_db):
|
|
"""Test getting team statistics."""
|
|
# Setup mock query results
|
|
mock_db.query().count.side_effect = [50, 45]
|
|
mock_db.query().filter().count.return_value = 5
|
|
|
|
# Team distribution mock
|
|
mock_team_distribution = [
|
|
{"member_count": 0, "count": 5},
|
|
{"member_count": 1, "count": 10},
|
|
{"member_count": 2, "count": 15},
|
|
{"member_count": 3, "count": 10},
|
|
{"member_count": 4, "count": 7},
|
|
{"member_count": 5, "count": 3}
|
|
]
|
|
mock_db.query().group_by().all.return_value = mock_team_distribution
|
|
|
|
# Get the statistics
|
|
stats = get_team_statistics(mock_db)
|
|
|
|
# Assert the expected results
|
|
assert stats["total_teams"] == 50
|
|
assert stats["active_teams"] == 45
|
|
assert stats["public_teams"] == 5
|
|
assert stats["team_distribution"] == mock_team_distribution
|
|
|
|
# Test cases for event statistics
|
|
def test_get_event_statistics(mock_db):
|
|
"""Test getting event statistics."""
|
|
# Setup mock query results
|
|
mock_db.query().count.side_effect = [30, 25, 5]
|
|
|
|
# Setup mock for upcoming events
|
|
today = datetime.now().date()
|
|
upcoming_events = [
|
|
mock.MagicMock(name="Event 1", event_date=today + timedelta(days=1), location="Location 1"),
|
|
mock.MagicMock(name="Event 2", event_date=today + timedelta(days=3), location="Location 2"),
|
|
mock.MagicMock(name="Event 3", event_date=today + timedelta(days=7), location="Location 3")
|
|
]
|
|
mock_db.query().filter().order_by().limit().all.return_value = upcoming_events
|
|
|
|
# Setup mock for attendance rates
|
|
mock_attendance_rates = [
|
|
{"event_id": 1, "event_name": "Event A", "attendee_count": 25},
|
|
{"event_id": 2, "event_name": "Event B", "attendee_count": 18},
|
|
{"event_id": 3, "event_name": "Event C", "attendee_count": 30}
|
|
]
|
|
mock_db.query().join().group_by().order_by().limit().all.return_value = mock_attendance_rates
|
|
|
|
# Get the statistics
|
|
stats = get_event_statistics(mock_db)
|
|
|
|
# Assert the expected results
|
|
assert stats["total_events"] == 30
|
|
assert stats["past_events"] == 25
|
|
assert stats["upcoming_events_count"] == 5
|
|
assert len(stats["upcoming_events"]) == 3
|
|
assert stats["attendance_rates"] == mock_attendance_rates
|
|
|
|
# Test cases for system health
|
|
def test_get_system_health(mock_db):
|
|
"""Test getting system health information."""
|
|
# Mock database status
|
|
mock_db.execute().fetchall.return_value = [{"status": "online"}]
|
|
|
|
# Get the health information
|
|
health_info = get_system_health(mock_db)
|
|
|
|
# Assert expected results
|
|
assert health_info["database_status"] == "online"
|
|
assert "uptime" in health_info
|
|
assert "recent_errors" in health_info
|
|
|
|
# Integration test for admin dashboard endpoint
|
|
@mock.patch("app.views.admin.get_db")
|
|
def test_admin_dashboard_endpoint(mock_get_db, mock_db):
|
|
"""Test the admin dashboard endpoint."""
|
|
# Setup mock DB to be returned from get_db
|
|
mock_get_db.return_value = mock_db
|
|
|
|
# Mock user stats
|
|
mock_user_stats = {
|
|
"total_users": 100,
|
|
"active_users": 80,
|
|
"verified_users": 20,
|
|
"admin_users": 10,
|
|
"new_registrations_30d": 15
|
|
}
|
|
|
|
# Mock team stats
|
|
mock_team_stats = {
|
|
"total_teams": 50,
|
|
"active_teams": 45,
|
|
"public_teams": 5,
|
|
"team_distribution": []
|
|
}
|
|
|
|
# Mock event stats
|
|
mock_event_stats = {
|
|
"total_events": 30,
|
|
"past_events": 25,
|
|
"upcoming_events_count": 5,
|
|
"upcoming_events": [],
|
|
"attendance_rates": []
|
|
}
|
|
|
|
# Mock system health
|
|
mock_system_health = {
|
|
"database_status": "online",
|
|
"uptime": "3 days, 2 hours",
|
|
"recent_errors": []
|
|
}
|
|
|
|
# Setup mock return values for our statistics functions
|
|
with mock.patch("app.views.admin.get_user_statistics", return_value=mock_user_stats), \
|
|
mock.patch("app.views.admin.get_team_statistics", return_value=mock_team_stats), \
|
|
mock.patch("app.views.admin.get_event_statistics", return_value=mock_event_stats), \
|
|
mock.patch("app.views.admin.get_system_health", return_value=mock_system_health), \
|
|
mock.patch("app.views.admin.require_admin", return_value=lambda f: f):
|
|
|
|
client = TestClient(app)
|
|
response = client.get("/admin/dashboard")
|
|
|
|
# Assert the response
|
|
assert response.status_code == 200
|
|
assert "user_stats" in response.context
|
|
assert "team_stats" in response.context
|
|
assert "event_stats" in response.context
|
|
assert "system_health" in response.context |