"""Integration tests for the Legnext SDK.

These tests make real API calls and require a valid API key.
Set LEGNEXT_API_KEY in your .env file or environment variables to run these tests.

Quick Start:
1. Install dev dependencies: uv pip install -e ".[dev]"
2. Create .env file: cp .env.example .env
3. Add API key to .env: LEGNEXT_API_KEY=your_api_key_here

Running Tests with uv:

Run all integration tests:
    uv run pytest tests/test_integration.py -v -m integration

Test account balance:
    uv run pytest tests/test_integration.py::test_account_balance -v -m integration

Test diffusion image generation:
    uv run pytest tests/test_integration.py::test_diffusion_generate_image -v -m integration

Skip integration tests (unit tests only):
    uv run pytest -m "not integration" -v
"""

import os

import pytest

from legnext import AsyncClient, Client
from legnext.types.enums import JobStatus


@pytest.mark.integration
def test_account_balance(real_api_key):
    """Test account balance API with real API key."""
    client = Client(api_key=real_api_key)
    balance = client.account.balance()

    # Verify response structure
    assert balance is not None
    assert balance.account_id is not None
    assert balance.balance_usd is not None
    assert balance.available_points is not None

    # Print balance info for verification
    print("\n✅ Account Balance Test:")
    print(f"   Account ID: {balance.account_id}")
    print(f"   Balance USD: {balance.balance_usd}")
    print(f"   Available Points: {balance.available_points}")
    print(f"   Available Credits: {balance.available_credits}")
    print(f"   Low Balance Alert: {balance.low_balance_alert}")


@pytest.mark.integration
@pytest.mark.asyncio
async def test_account_balance_async(real_api_key):
    """Test account balance API with async client."""
    async with AsyncClient(api_key=real_api_key) as client:
        balance = await client.account.balance()

        assert balance is not None
        assert balance.account_id is not None
        assert balance.balance_usd is not None


@pytest.mark.integration
def test_task_get(real_api_key):
    """Test getting task status with a real job ID.

    Note: This test requires a valid job_id. You may need to:
    1. Create a task first using client.midjourney.diffusion()
    2. Use that job_id here
    3. Or skip this test if you don't have a job_id
    """
    client = Client(api_key=real_api_key)

    # Example: Use a job_id from your account
    # Replace with an actual job_id from your account, or skip this test
    job_id = os.getenv("LEGNEXT_TEST_JOB_ID")
    if not job_id:
        pytest.skip("LEGNEXT_TEST_JOB_ID not set - skipping task get test")

    task = client.tasks.get(job_id=job_id)
    assert task is not None
    assert task.job_id == job_id
    assert task.status in [JobStatus.PENDING, JobStatus.COMPLETED, JobStatus.FAILED]


@pytest.mark.integration
def test_client_initialization_with_real_key(real_api_key):
    """Test that client initializes correctly with real API key."""
    client = Client(api_key=real_api_key)
    assert client._http.api_key == real_api_key
    assert client._http.base_url == "https://api.legnext.ai/api"

    # Verify all resources are available
    assert hasattr(client, "account")
    assert hasattr(client, "midjourney")
    assert hasattr(client, "tasks")


@pytest.mark.integration
@pytest.mark.asyncio
async def test_async_client_initialization_with_real_key(real_api_key):
    """Test that async client initializes correctly with real API key."""
    async with AsyncClient(api_key=real_api_key) as client:
        assert client._http.api_key == real_api_key
        assert hasattr(client, "account")
        assert hasattr(client, "midjourney")
        assert hasattr(client, "tasks")


@pytest.mark.integration
def test_diffusion_generate_image(real_api_key):
    """Test diffusion image generation API.

    This test creates a real image generation task and waits for completion.
    Note: This will consume API quota/points.
    """
    client = Client(api_key=real_api_key)

    # Generate an image
    print("\n🖼️  Starting image generation...")
    response = client.midjourney.diffusion(
        text="a beautiful sunset over mountains, photorealistic, 4k"
    )

    assert response is not None
    assert response.job_id is not None
    assert response.status == JobStatus.PENDING

    print(f"   Job ID: {response.job_id}")
    print(f"   Status: {response.status}")

    # Wait for completion (with timeout)
    print("\n⏳ Waiting for image generation to complete...")

    def progress_callback(task):
        print(f"   Status: {task.status}")

    result = client.tasks.wait_for_completion(
        response.job_id,
        timeout=300.0,  # 5 minutes timeout
        poll_interval=5.0,  # Check every 5 seconds
        on_progress=progress_callback,
    )

    # Verify completion
    assert result.status == JobStatus.COMPLETED
    assert result.output is not None
    assert result.output.image_urls is not None
    assert len(result.output.image_urls) > 0

    print("\n✅ Image generation completed!")
    print(f"   Generated {len(result.output.image_urls)} images:")
    for i, url in enumerate(result.output.image_urls, 1):
        print(f"   Image {i}: {url}")

    if result.output.seed:
        print(f"   Seed: {result.output.seed}")


@pytest.mark.integration
@pytest.mark.asyncio
async def test_diffusion_generate_image_async(real_api_key):
    """Test async diffusion image generation API."""
    async with AsyncClient(api_key=real_api_key) as client:
        # Generate an image
        print("\n🖼️  Starting async image generation...")
        response = await client.midjourney.diffusion(text="a cute robot, cartoon style, colorful")

        assert response is not None
        assert response.job_id is not None
        assert response.status == JobStatus.PENDING

        print(f"   Job ID: {response.job_id}")

        # Wait for completion
        print("\n⏳ Waiting for completion...")
        result = await client.tasks.wait_for_completion(
            response.job_id, timeout=300.0, poll_interval=5.0
        )

        assert result.status == JobStatus.COMPLETED
        assert result.output is not None
        assert result.output.image_urls is not None
        assert len(result.output.image_urls) > 0

        print("\n✅ Async image generation completed!")
        print(f"   Generated {len(result.output.image_urls)} images")
