""" Tests for enhanced error handling system """ import pytest from flask import jsonify from app import db from app.models import User from app.utils.error_handlers import get_user_friendly_message, register_error_handlers @pytest.mark.unit @pytest.mark.error_handling def test_user_friendly_message_404(): """Test that 404 error has user-friendly message""" message = get_user_friendly_message(404) assert message is not None assert 'title' in message assert 'message' in message assert 'recovery' in message assert message['title'] == 'Page Not Found' assert 'not found' in message['message'].lower() @pytest.mark.unit @pytest.mark.error_handling def test_user_friendly_message_500(): """Test that 500 error has user-friendly message""" message = get_user_friendly_message(500) assert message is not None assert message['title'] == 'Server Error' assert 'server error' in message['message'].lower() or 'error occurred' in message['message'].lower() @pytest.mark.unit @pytest.mark.error_handling def test_user_friendly_message_401(): """Test that 401 error has user-friendly message""" message = get_user_friendly_message(401) assert message is not None assert message['title'] == 'Authentication Required' assert 'log in' in message['message'].lower() or 'login' in message['message'].lower() @pytest.mark.unit @pytest.mark.error_handling def test_user_friendly_message_403(): """Test that 403 error has user-friendly message""" message = get_user_friendly_message(403) assert message is not None assert message['title'] == 'Access Denied' assert 'permission' in message['message'].lower() or 'access' in message['message'].lower() @pytest.mark.unit @pytest.mark.error_handling def test_user_friendly_message_unknown_status(): """Test that unknown status codes have fallback message""" message = get_user_friendly_message(999) assert message is not None assert 'title' in message assert 'message' in message assert 'recovery' in message @pytest.mark.unit @pytest.mark.error_handling def test_user_friendly_message_with_description(): """Test that error messages can include custom descriptions""" message = get_user_friendly_message(400, 'Custom error description') assert message is not None assert 'Custom error description' in message['message'] @pytest.mark.unit @pytest.mark.error_handling def test_recovery_options_include_dashboard(): """Test that recovery options include dashboard""" message = get_user_friendly_message(404) assert 'Go to Dashboard' in message['recovery'] @pytest.mark.unit @pytest.mark.error_handling def test_error_handling_enhanced_file_exists(): """Test that error handling enhanced file exists""" import os error_file = os.path.join( os.path.dirname(os.path.dirname(__file__)), 'app', 'static', 'error-handling-enhanced.js' ) assert os.path.exists(error_file), "Error handling enhanced file should exist" @pytest.mark.unit @pytest.mark.error_handling def test_error_handling_retry_functionality(): """Test that retry functionality is implemented""" import os error_file = os.path.join( os.path.dirname(os.path.dirname(__file__)), 'app', 'static', 'error-handling-enhanced.js' ) if os.path.exists(error_file): with open(error_file, 'r', encoding='utf-8') as f: content = f.read() assert 'retryFetch' in content, "Retry functionality should be implemented" assert 'showErrorWithRetry' in content, "Retry button should be shown" @pytest.mark.unit @pytest.mark.error_handling def test_offline_queue_functionality(): """Test that offline queue functionality is implemented""" import os error_file = os.path.join( os.path.dirname(os.path.dirname(__file__)), 'app', 'static', 'error-handling-enhanced.js' ) if os.path.exists(error_file): with open(error_file, 'r', encoding='utf-8') as f: content = f.read() assert 'queueForOffline' in content, "Offline queue should be implemented" assert 'processOfflineQueue' in content, "Offline queue processing should exist" @pytest.mark.unit @pytest.mark.error_handling def test_graceful_degradation(): """Test that graceful degradation is implemented""" import os error_file = os.path.join( os.path.dirname(os.path.dirname(__file__)), 'app', 'static', 'error-handling-enhanced.js' ) if os.path.exists(error_file): with open(error_file, 'r', encoding='utf-8') as f: content = f.read() assert 'setupGracefulDegradation' in content, "Graceful degradation should be implemented" assert 'checkRequiredFeatures' in content, "Feature checking should exist" @pytest.mark.unit @pytest.mark.error_handling def test_error_handling_js_loaded(authenticated_client): """Test that error handling JavaScript is loaded in base template""" response = authenticated_client.get('/dashboard') assert response.status_code == 200 # Check that error-handling-enhanced.js is included assert b'error-handling-enhanced.js' in response.data @pytest.mark.unit @pytest.mark.error_handling def test_api_health_endpoint(client): """Test that API health endpoint exists""" response = client.get('/api/health') assert response.status_code == 200 data = response.get_json() assert data is not None assert 'status' in data assert data['status'] == 'ok' @pytest.mark.unit @pytest.mark.error_handling def test_error_handlers_registered(app): """Test that error handlers are registered""" # Error handlers should be registered during app creation assert app is not None # Check that error handlers are callable with app.app_context(): message = get_user_friendly_message(404) assert message is not None @pytest.mark.smoke @pytest.mark.error_handling def test_error_template_updates(client): """Smoke test: Verify error templates have retry buttons""" # Test 404 page response = client.get('/nonexistent-page') assert response.status_code == 404 html = response.data.decode('utf-8') # Should have retry/recovery options assert 'Go to Dashboard' in html or 'Go Back' in html @pytest.mark.unit @pytest.mark.error_handling def test_error_handling_network_monitoring(): """Test that network monitoring is implemented""" import os error_file = os.path.join( os.path.dirname(os.path.dirname(__file__)), 'app', 'static', 'error-handling-enhanced.js' ) if os.path.exists(error_file): with open(error_file, 'r', encoding='utf-8') as f: content = f.read() assert 'setupNetworkMonitoring' in content, "Network monitoring should be implemented" assert 'checkOnlineStatus' in content, "Online status checking should exist" @pytest.mark.unit @pytest.mark.error_handling def test_error_handling_offline_indicator(): """Test that offline indicator is implemented""" import os error_file = os.path.join( os.path.dirname(os.path.dirname(__file__)), 'app', 'static', 'error-handling-enhanced.js' ) if os.path.exists(error_file): with open(error_file, 'r', encoding='utf-8') as f: content = f.read() assert 'showOfflineIndicator' in content, "Offline indicator should be implemented" assert 'offline-indicator' in content, "Offline indicator element should exist" @pytest.mark.unit @pytest.mark.error_handling def test_error_handling_recovery_options(): """Test that recovery options are implemented""" import os error_file = os.path.join( os.path.dirname(os.path.dirname(__file__)), 'app', 'static', 'error-handling-enhanced.js' ) if os.path.exists(error_file): with open(error_file, 'r', encoding='utf-8') as f: content = f.read() assert 'getRecoveryOptions' in content, "Recovery options should be implemented" assert 'error-recovery-btn' in content, "Recovery buttons should exist"