All checks were successful
- Add 55 unit tests for hosting module (hosted site service, client service service, stats service) with full fixture setup - Fix table_empty_state macro: add x_message param for dynamic Alpine.js expressions rendered via x-text instead of server-side Jinja - Fix hosting templates (sites, clients) using message= with Alpine expressions that rendered as literal text - Fix prospecting templates (leads, scan-jobs, prospects) using nonexistent subtitle= param, migrated to x_message= - Align hosting and prospecting admin templates with shared design system Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
67 lines
2.4 KiB
Python
67 lines
2.4 KiB
Python
# app/modules/hosting/tests/unit/test_stats_service.py
|
|
"""
|
|
Unit tests for hosting StatsService.
|
|
"""
|
|
|
|
import pytest
|
|
|
|
from app.modules.hosting.services.stats_service import StatsService
|
|
|
|
|
|
@pytest.mark.unit
|
|
@pytest.mark.hosting
|
|
class TestStatsService:
|
|
"""Tests for hosting StatsService."""
|
|
|
|
def setup_method(self):
|
|
self.service = StatsService()
|
|
|
|
def test_dashboard_stats_empty(self, db):
|
|
"""Test dashboard stats with no data."""
|
|
stats = self.service.get_dashboard_stats(db)
|
|
assert stats["total_sites"] == 0
|
|
assert stats["live_sites"] == 0
|
|
assert stats["poc_sites"] == 0
|
|
assert stats["active_services"] == 0
|
|
assert stats["monthly_revenue_cents"] == 0
|
|
assert stats["upcoming_renewals"] == 0
|
|
|
|
def test_dashboard_stats_with_site(self, db, hosted_site):
|
|
"""Test dashboard stats with a draft site."""
|
|
stats = self.service.get_dashboard_stats(db)
|
|
assert stats["total_sites"] >= 1
|
|
assert stats["poc_sites"] >= 1 # draft counts as POC
|
|
assert stats["sites_by_status"].get("draft", 0) >= 1
|
|
|
|
def test_dashboard_stats_with_services(
|
|
self, db, hosted_site, client_service_domain, client_service_email
|
|
):
|
|
"""Test dashboard stats with active services."""
|
|
stats = self.service.get_dashboard_stats(db)
|
|
assert stats["active_services"] >= 2
|
|
assert stats["monthly_revenue_cents"] >= 3000 # 2500 + 500
|
|
|
|
def test_dashboard_stats_services_by_type(
|
|
self, db, hosted_site, client_service_domain, client_service_email
|
|
):
|
|
"""Test services_by_type breakdown."""
|
|
stats = self.service.get_dashboard_stats(db)
|
|
assert "domain" in stats["services_by_type"]
|
|
assert "email" in stats["services_by_type"]
|
|
|
|
def test_dashboard_stats_upcoming_renewals(
|
|
self, db, hosted_site, client_service_expiring
|
|
):
|
|
"""Test upcoming renewals count."""
|
|
stats = self.service.get_dashboard_stats(db)
|
|
assert stats["upcoming_renewals"] >= 1
|
|
|
|
def test_dashboard_stats_sites_by_status(
|
|
self, db, hosted_site, hosted_site_poc_ready
|
|
):
|
|
"""Test sites_by_status breakdown."""
|
|
stats = self.service.get_dashboard_stats(db)
|
|
assert isinstance(stats["sites_by_status"], dict)
|
|
total_from_breakdown = sum(stats["sites_by_status"].values())
|
|
assert total_from_breakdown == stats["total_sites"]
|