#!/usr/bin/env python3
"""
Test HTML Rendering in Notes Field

This script tests that the notes field HTML content is properly rendered
in the output HTML file instead of being escaped.
"""

import asyncio
import json
import logging
import sys
import tempfile
from pathlib import Path
import os

# Add the current directory to the path so we can import modules
sys.path.insert(0, os.path.dirname(os.path.abspath(__file__)))

from snapshot_downloader import SnapshotDownloader


class HTMLRenderingTester:
    """Test class for HTML rendering functionality."""

    def __init__(self):
        """Initialize the tester."""
        self.logger = logging.getLogger(__name__)

    def test_notes_html_rendering(self):
        """Test that HTML in notes field is properly rendered."""
        print("=" * 60)
        print("TEST: HTML Rendering in Notes Field")
        print("=" * 60)

        with tempfile.TemporaryDirectory() as temp_dir:
            downloader = SnapshotDownloader(output_dir=temp_dir)

            print("1. Testing snapshot with HTML content in notes...")

            # Create mock snapshot with HTML content in notes
            mock_snapshot = {
                "id": "test_html_rendering",
                "type": "Snapshot",
                "code": "Snapshot",
                "child": {
                    "forename": "Test",
                    "surname": "Child"
                },
                "author": {
                    "forename": "Test",
                    "surname": "Teacher"
                },
                "startTime": "2024-01-15T10:30:00",
                "notes": """<p>This is a <strong>bold</strong> statement about the child's progress.</p>
<p><br></p>
<p>The child demonstrated <em>excellent</em> skills in:</p>
<p>• Communication</p>
<p>• Problem solving</p>
<p><br></p>
<p><span style="color: rgb(255, 0, 0);">Important note:</span> Continue encouraging creative play.</p>
<p><span style="font-size: 14px;">Next steps: Focus on fine motor skills development.</span></p>""",
                "frameworkIndicatorCount": 15,
                "signed": False
            }

            # Generate HTML for the snapshot
            html_content = downloader.format_snapshot_html(mock_snapshot)

            print("2. Checking HTML content rendering...")

            # Check that HTML tags are NOT escaped (should be rendered) within notes-content
            if 'notes-content"><p>' in html_content or 'notes-content"><strong>' in html_content:
                print("   ✅ HTML paragraph tags are rendered (not escaped)")
            else:
                print("   ❌ HTML paragraph tags are escaped instead of rendered")
                # Debug output to see what we actually got
                start = html_content.find('notes-content')
                if start != -1:
                    sample = html_content[start:start+150]
                    print(f"   Debug - Found: {sample}")
                return False

            if "<strong>bold</strong>" in html_content:
                print("   ✅ HTML strong tags are rendered (not escaped)")
            else:
                print("   ❌ HTML strong tags are escaped instead of rendered")
                return False

            if "<em>excellent</em>" in html_content:
                print("   ✅ HTML emphasis tags are rendered (not escaped)")
            else:
                print("   ❌ HTML emphasis tags are escaped instead of rendered")
                return False

            if 'style="color: rgb(255, 0, 0);"' in html_content:
                print("   ✅ Inline CSS styles are preserved")
            else:
                print("   ❌ Inline CSS styles are not preserved")
                return False

            print("\n3. Testing complete HTML file generation...")

            # Generate complete HTML file
            mock_snapshots = [mock_snapshot]
            html_file = downloader.generate_html_file(
                mock_snapshots, "2024-01-01", "2024-01-31"
            )

            if html_file.exists():
                print("   ✅ HTML file created successfully")

                # Read and check file content
                with open(html_file, 'r', encoding='utf-8') as f:
                    file_content = f.read()

                # Check for proper HTML structure
                if 'class="notes-content"' in file_content:
                    print("   ✅ Notes content wrapper class present")
                else:
                    print("   ❌ Notes content wrapper class missing")
                    return False

                # Check that HTML content is rendered in the file
                if "<p>This is a <strong>bold</strong> statement" in file_content:
                    print("   ✅ HTML content properly rendered in file")
                else:
                    print("   ❌ HTML content not properly rendered in file")
                    print("   Debug: Looking for HTML content in file...")
                    # Show a sample of the content for debugging
                    start = file_content.find('notes-content')
                    if start != -1:
                        sample = file_content[start:start+200]
                        print(f"   Sample content: {sample}")
                    return False

                # Check for CSS styles that handle HTML content
                if ".notes-content" in file_content:
                    print("   ✅ CSS styles for notes content included")
                else:
                    print("   ❌ CSS styles for notes content missing")
                    return False

            else:
                print("   ❌ HTML file was not created")
                return False

            print("\n4. Testing XSS safety with potentially dangerous content...")

            # Test with potentially dangerous content to ensure basic safety
            dangerous_snapshot = {
                "id": "test_xss_safety",
                "type": "Snapshot",
                "startTime": "2024-01-15T10:30:00",
                "notes": '<p>Safe content</p><script>alert("xss")</script><p>More safe content</p>',
            }

            dangerous_html = downloader.format_snapshot_html(dangerous_snapshot)

            # The script tag should still be present (we're not sanitizing, just rendering)
            # But we should document this as a security consideration
            if '<script>' in dangerous_html:
                print("   ⚠️  Script tags are rendered (consider content sanitization for production)")
            else:
                print("   ✅ Script tags are filtered/escaped")

        print("\n✅ HTML rendering test completed!")
        return True

    def test_complex_html_scenarios(self):
        """Test various complex HTML scenarios."""
        print("\n" + "=" * 60)
        print("TEST: Complex HTML Scenarios")
        print("=" * 60)

        with tempfile.TemporaryDirectory() as temp_dir:
            downloader = SnapshotDownloader(output_dir=temp_dir)

            test_cases = [
                {
                    "name": "Nested HTML Tags",
                    "notes": '<p>Child showed <strong>excellent <em>progress</em></strong> today.</p>',
                    "should_contain": ['<strong>', '<em>', 'excellent', 'progress']
                },
                {
                    "name": "Line Breaks and Paragraphs",
                    "notes": '<p>First paragraph.</p><p><br></p><p>Second paragraph after break.</p>',
                    "should_contain": ['<p>First paragraph.</p>', '<p><br></p>', '<p>Second paragraph']
                },
                {
                    "name": "Styled Text",
                    "notes": '<p><span style="color: rgb(0, 0, 255); font-size: 16px;">Blue text</span></p>',
                    "should_contain": ['style="color: rgb(0, 0, 255)', 'font-size: 16px', 'Blue text']
                },
                {
                    "name": "Mixed Content",
                    "notes": '<p>Normal text</p><p>• Bullet point 1</p><p>• Bullet point 2</p><p><strong>Next steps:</strong> Continue activities.</p>',
                    "should_contain": ['Normal text', '• Bullet', '<strong>Next steps:</strong>']
                }
            ]

            for i, test_case in enumerate(test_cases, 1):
                print(f"\n{i}. Testing: {test_case['name']}")

                mock_snapshot = {
                    "id": f"test_case_{i}",
                    "type": "Snapshot",
                    "startTime": "2024-01-15T10:30:00",
                    "notes": test_case['notes']
                }

                html_content = downloader.format_snapshot_html(mock_snapshot)

                # Check that all expected content is present and rendered
                all_found = True
                for expected in test_case['should_contain']:
                    if expected in html_content:
                        print(f"   ✅ Found: {expected[:30]}...")
                    else:
                        print(f"   ❌ Missing: {expected[:30]}...")
                        all_found = False

                if not all_found:
                    print(f"   ❌ Test case '{test_case['name']}' failed")
                    return False
                else:
                    print(f"   ✅ Test case '{test_case['name']}' passed")

        print("\n✅ Complex HTML scenarios test completed!")
        return True

    def test_empty_and_edge_cases(self):
        """Test edge cases for notes field."""
        print("\n" + "=" * 60)
        print("TEST: Edge Cases")
        print("=" * 60)

        with tempfile.TemporaryDirectory() as temp_dir:
            downloader = SnapshotDownloader(output_dir=temp_dir)

            edge_cases = [
                {
                    "name": "Empty notes",
                    "notes": "",
                    "expected": "No description provided"
                },
                {
                    "name": "None notes",
                    "notes": None,
                    "expected": "No description provided"
                },
                {
                    "name": "Only whitespace",
                    "notes": "   \n\t   ",
                    "expected": "   \n\t   "  # Should preserve whitespace
                },
                {
                    "name": "Plain text (no HTML)",
                    "notes": "Just plain text without HTML tags.",
                    "expected": "Just plain text without HTML tags."
                }
            ]

            for i, test_case in enumerate(edge_cases, 1):
                print(f"\n{i}. Testing: {test_case['name']}")

                mock_snapshot = {
                    "id": f"edge_case_{i}",
                    "type": "Snapshot",
                    "startTime": "2024-01-15T10:30:00"
                }

                if test_case['notes'] is not None:
                    mock_snapshot['notes'] = test_case['notes']

                html_content = downloader.format_snapshot_html(mock_snapshot)

                if test_case['expected'] in html_content:
                    print(f"   ✅ Correctly handled: {test_case['name']}")
                else:
                    print(f"   ❌ Failed: {test_case['name']}")
                    print(f"   Expected: {test_case['expected']}")
                    # Show relevant part of HTML for debugging
                    start = html_content.find('notes-content')
                    if start != -1:
                        sample = html_content[start:start+100]
                        print(f"   Found: {sample}")
                    return False

        print("\n✅ Edge cases test completed!")
        return True

    def run_all_tests(self):
        """Run all HTML rendering tests."""
        print("🚀 Starting HTML Rendering Tests")
        print("=" * 80)

        try:
            success = True

            success &= self.test_notes_html_rendering()
            success &= self.test_complex_html_scenarios()
            success &= self.test_empty_and_edge_cases()

            if success:
                print("\n" + "=" * 80)
                print("🎉 ALL HTML RENDERING TESTS PASSED!")
                print("=" * 80)
                print("✅ HTML content in notes field is properly rendered")
                print("✅ Complex HTML scenarios work correctly")
                print("✅ Edge cases are handled appropriately")
                print("✅ CSS styles support HTML content rendering")
                print("\n⚠️  Security Note:")
                print("   HTML content is rendered as-is for rich formatting.")
                print("   Consider content sanitization if accepting user input.")
            else:
                print("\n❌ SOME HTML RENDERING TESTS FAILED")

            return success

        except Exception as e:
            print(f"\n❌ HTML RENDERING TESTS FAILED: {e}")
            import traceback
            traceback.print_exc()
            return False


def show_html_rendering_info():
    """Show information about HTML rendering in notes."""
    print("\n" + "=" * 80)
    print("📝 HTML RENDERING IN NOTES FIELD")
    print("=" * 80)

    print("\n🎨 What's Rendered:")
    print("• <p> tags for paragraphs")
    print("• <strong> and <em> for bold/italic text")
    print("• <br> tags for line breaks")
    print("• <span> with style attributes for colors/fonts")
    print("• Bullet points and lists")
    print("• All inline CSS styles")

    print("\n💡 Example HTML Content:")
    print('<p>Child showed <strong>excellent</strong> progress today.</p>')
    print('<p><br></p>')
    print('<p><span style="color: rgb(255, 0, 0);">Important:</span> Continue activities.</p>')

    print("\n📋 Becomes:")
    print("Child showed excellent progress today.")
    print("")
    print("Important: Continue activities. (in red)")

    print("\n🔒 Security Considerations:")
    print("• HTML content is rendered as-is from the API")
    print("• Content comes from trusted ParentZone staff")
    print("• Script tags and other content are preserved")
    print("• Consider sanitization for untrusted input")

    print("\n🎯 Benefits:")
    print("• Rich text formatting preserved")
    print("• Professional-looking reports")
    print("• Colors and styling from original content")
    print("• Better readability and presentation")


def main():
    """Main test function."""
    # Setup logging
    logging.basicConfig(
        level=logging.INFO,
        format='%(asctime)s - %(name)s - %(levelname)s - %(message)s'
    )

    tester = HTMLRenderingTester()

    # Run tests
    success = tester.run_all_tests()

    # Show information
    if success:
        show_html_rendering_info()

    return 0 if success else 1


if __name__ == "__main__":
    exit(main())
