"""Example: Using the async client for concurrent operations."""

import asyncio
from sed_sh import AsyncSedSH


async def main():
    # Initialize async client with context manager
    async with AsyncSedSH() as client:

        # Example 1: Create multiple short URLs concurrently
        print("=== Example 1: Concurrent URL shortening ===")
        urls = [
            "https://github.com/anthropics",
            "https://docs.sed.sh",
            "https://www.sed.sh/links",
            "https://www.sed.sh/malware",
            "https://www.sed.sh/inbox",
        ]

        # Create all links concurrently
        link_tasks = [client.links.create(url) for url in urls]
        links = await asyncio.gather(*link_tasks)

        print(f"Created {len(links)} short URLs:")
        for link in links:
            print(f"  - {link['shortUrl']} -> {link['targetUrl']}")
        print()

        # Example 2: Create inbox and check for messages concurrently
        print("=== Example 2: Concurrent inbox operations ===")

        # Create multiple inboxes at once
        inbox_tasks = [client.inbox.create() for _ in range(3)]
        inboxes = await asyncio.gather(*inbox_tasks)

        print(f"Created {len(inboxes)} inboxes:")
        for inbox in inboxes:
            print(f"  - {inbox['email']}")

        # Check messages in all inboxes concurrently
        message_tasks = [
            client.inbox.get_messages(inbox['code'])
            for inbox in inboxes
        ]
        all_messages = await asyncio.gather(*message_tasks)

        total_messages = sum(len(msgs['messages']) for msgs in all_messages)
        print(f"Total messages across all inboxes: {total_messages}")
        print()

        # Example 3: List multiple resources concurrently
        print("=== Example 3: Concurrent resource listing ===")

        # Fetch all resource lists at the same time
        lists = await asyncio.gather(
            client.links.list(),
            client.inbox.list(),
            client.routes.list_endpoints(),
            client.reports.list_templates(),
        )

        links_list, inboxes_list, endpoints_list, templates_list = lists

        print(f"Links: {len(links_list['links'])}")
        print(f"Inboxes: {len(inboxes_list['inboxes'])}")
        print(f"Endpoints: {len(endpoints_list['endpoints'])}")
        print(f"Templates: {len(templates_list['templates'])}")
        print()

        # Example 4: Create mock API endpoints concurrently
        print("=== Example 4: Concurrent endpoint creation ===")

        endpoints_to_create = [
            {
                "name": "Users API",
                "method": "GET",
                "path": "/api/users",
                "response_status": 200,
                "response_body": '{"users": []}',
            },
            {
                "name": "Posts API",
                "method": "GET",
                "path": "/api/posts",
                "response_status": 200,
                "response_body": '{"posts": []}',
            },
            {
                "name": "Comments API",
                "method": "GET",
                "path": "/api/comments",
                "response_status": 200,
                "response_body": '{"comments": []}',
            },
        ]

        endpoint_tasks = [
            client.routes.create_endpoint(**ep_config)
            for ep_config in endpoints_to_create
        ]
        endpoints = await asyncio.gather(*endpoint_tasks)

        print(f"Created {len(endpoints)} mock endpoints:")
        for ep in endpoints:
            print(f"  - {ep['method']} {ep['path']}: {ep['url']}")
        print()

        # Example 5: Generate multiple PDFs concurrently
        print("=== Example 5: Concurrent PDF generation ===")

        # First create a template
        template_html = """
        <html>
        <body>
            <h1>Report for {{name}}</h1>
            <p>Status: {{status}}</p>
        </body>
        </html>
        """

        template = await client.reports.create_template(
            name="Status Report",
            html=template_html
        )
        print(f"Created template: {template['templateId']}")

        # Generate multiple PDFs concurrently
        pdf_data = [
            {"name": "Project A", "status": "In Progress"},
            {"name": "Project B", "status": "Completed"},
            {"name": "Project C", "status": "Planning"},
        ]

        pdf_tasks = [
            client.reports.generate_pdf(template['templateId'], data)
            for data in pdf_data
        ]
        pdfs = await asyncio.gather(*pdf_tasks)

        print(f"Generated {len(pdfs)} PDFs:")
        for i, pdf in enumerate(pdfs):
            print(f"  - PDF {i+1}: {pdf['sizeBytes']} bytes "
                  f"({pdf['computeTimeSeconds']:.2f}s)")
        print()

        # Example 6: Cleanup - delete resources concurrently
        print("=== Example 6: Concurrent cleanup ===")

        cleanup_tasks = []

        # Delete links
        for link in links:
            cleanup_tasks.append(client.links.delete(link['code']))

        # Delete inboxes
        for inbox in inboxes:
            cleanup_tasks.append(client.inbox.delete(inbox['code']))

        # Delete endpoints
        for ep in endpoints:
            cleanup_tasks.append(client.routes.delete_endpoint(ep['endpointId']))

        # Delete template
        cleanup_tasks.append(client.reports.delete_template(template['templateId']))

        # Execute all deletions concurrently
        await asyncio.gather(*cleanup_tasks)
        print(f"Cleaned up {len(cleanup_tasks)} resources concurrently")
        print()

        # Example 7: Error handling with asyncio.gather
        print("=== Example 7: Error handling ===")

        try:
            # Try to delete non-existent resources
            results = await asyncio.gather(
                client.links.delete("nonexistent"),
                client.inbox.delete("nonexistent"),
                return_exceptions=True  # Return exceptions instead of raising
            )

            for i, result in enumerate(results):
                if isinstance(result, Exception):
                    print(f"  Operation {i+1} failed: {type(result).__name__}")
                else:
                    print(f"  Operation {i+1} succeeded")
        except Exception as e:
            print(f"Error: {e}")
        print()

    print("=== Done! Session automatically closed ===")


# Run the async main function
if __name__ == "__main__":
    asyncio.run(main())
