"""API tests for audio processing template endpoints."""

import pytest

from ledgrab.config import get_config

# Ensure audio filters registered
import ledgrab.core.audio.filters  # noqa: F401

AUTH: dict = {}


@pytest.fixture(autouse=True, scope="module")
def _populate_auth():
    """Resolve the active API key once per module — the global config may
    have been swapped by a session-scoped conftest after this module was
    first imported, so we cannot capture at import time."""
    key = next(iter(get_config().auth.api_keys.values()), "")
    AUTH.clear()
    if key:
        AUTH["Authorization"] = f"Bearer {key}"
    yield
    AUTH.clear()


@pytest.fixture(scope="module")
def client():
    """Provide a TestClient with lifespan (startup/shutdown) properly triggered."""
    from fastapi.testclient import TestClient
    from ledgrab.main import app

    with TestClient(app) as c:
        yield c


# Track created template IDs for cleanup
_created_ids: list[str] = []


@pytest.fixture(autouse=True)
def cleanup_after_test(client):
    """Clean up created templates after each test."""
    yield
    for tid in list(_created_ids):
        client.delete(f"/api/v1/audio-processing-templates/{tid}", headers=AUTH)
    _created_ids.clear()


def _create(client, name: str, filters: list | None = None, **kwargs) -> dict:
    """Helper: create a template and track for cleanup."""
    body = {"name": name, "filters": filters or [], **kwargs}
    resp = client.post("/api/v1/audio-processing-templates", json=body, headers=AUTH)
    if resp.status_code == 201:
        _created_ids.append(resp.json()["id"])
    return resp


class TestAudioProcessingTemplateAPI:
    """Test /api/v1/audio-processing-templates endpoints."""

    def test_list(self, client):
        resp = client.get("/api/v1/audio-processing-templates", headers=AUTH)
        assert resp.status_code == 200
        data = resp.json()
        assert "templates" in data
        assert "count" in data

    def test_create(self, client):
        resp = _create(
            client,
            "API Test Template",
            filters=[{"filter_id": "gain", "options": {"factor": 2.0}}],
            description="A test template",
            tags=["test"],
        )
        assert resp.status_code == 201
        data = resp.json()
        assert data["name"] == "API Test Template"
        assert data["id"].startswith("apt_")
        assert len(data["filters"]) == 1
        assert data["filters"][0]["filter_id"] == "gain"
        assert data["description"] == "A test template"
        assert data["tags"] == ["test"]

    def test_create_invalid_filter_returns_400(self, client):
        resp = client.post(
            "/api/v1/audio-processing-templates",
            json={
                "name": "Bad Template",
                "filters": [{"filter_id": "nonexistent", "options": {}}],
            },
            headers=AUTH,
        )
        assert resp.status_code == 400

    def test_get_by_id(self, client):
        create_resp = _create(client, "Fetchable Template")
        tid = create_resp.json()["id"]

        resp = client.get(f"/api/v1/audio-processing-templates/{tid}", headers=AUTH)
        assert resp.status_code == 200
        assert resp.json()["name"] == "Fetchable Template"

    def test_get_nonexistent_returns_404(self, client):
        resp = client.get("/api/v1/audio-processing-templates/apt_nonexistent", headers=AUTH)
        assert resp.status_code == 404

    def test_update(self, client):
        create_resp = _create(client, "Original API Template")
        tid = create_resp.json()["id"]

        resp = client.put(
            f"/api/v1/audio-processing-templates/{tid}",
            json={
                "name": "Updated API Template",
                "filters": [{"filter_id": "inverter", "options": {}}],
            },
            headers=AUTH,
        )
        assert resp.status_code == 200
        data = resp.json()
        assert data["name"] == "Updated API Template"
        assert len(data["filters"]) == 1

    def test_update_nonexistent_returns_404(self, client):
        resp = client.put(
            "/api/v1/audio-processing-templates/apt_nonexistent",
            json={"name": "X"},
            headers=AUTH,
        )
        assert resp.status_code == 404

    def test_delete(self, client):
        create_resp = _create(client, "To Delete API")
        tid = create_resp.json()["id"]
        _created_ids.remove(tid)

        resp = client.delete(f"/api/v1/audio-processing-templates/{tid}", headers=AUTH)
        assert resp.status_code == 204

        resp2 = client.get(f"/api/v1/audio-processing-templates/{tid}", headers=AUTH)
        assert resp2.status_code == 404

    def test_delete_nonexistent_returns_404(self, client):
        resp = client.delete("/api/v1/audio-processing-templates/apt_nonexistent", headers=AUTH)
        assert resp.status_code == 404


class TestFilterRegistryAPI:
    """Test /api/v1/audio-filters endpoint."""

    def test_list_filters(self, client):
        resp = client.get("/api/v1/audio-filters", headers=AUTH)
        if resp.status_code == 404:
            pytest.skip("Audio filters registry endpoint not implemented")
        assert resp.status_code == 200
        data = resp.json()
        assert "filters" in data
        ids = {f["filter_id"] for f in data["filters"]}
        assert "gain" in ids
        assert "inverter" in ids
