"""runtime_requirements() on the real registered adapters (Auth, Forms, Feature
Packs) -- proves the hosting-neutral contract against actual production adapters,
complementing the fake-capability tests in test_capability_runtime_requirements.py.
"""
from __future__ import annotations

from types import SimpleNamespace
from uuid import uuid4

import pytest
from src.domain.capabilities.adapters import (
    AuthV2Provisioner,
    FeaturePackProvisioner,
    FormsProvisioner,
)
from src.domain.capabilities.lifecycle import CapabilityState


class _FakeResult:
    def __init__(self, rows=None, scalars_list=None):
        self._rows = rows or []
        self._scalars_list = scalars_list or []

    def all(self):
        return self._rows

    def scalars(self):
        return SimpleNamespace(all=lambda: self._scalars_list)


class _FakeDB:
    """Returns queued results in the exact order ``_required_capability_keys``
    issues them: pack_slug lookup, then pack-row lookup."""

    def __init__(self, *results: _FakeResult, reconciliation_row=None):
        self._results = list(results)
        self._reconciliation_row = reconciliation_row

    async def execute(self, _query):
        return self._results.pop(0)

    async def get(self, _model, _project_id):
        return self._reconciliation_row


@pytest.mark.asyncio
async def test_auth_v2_runtime_requirements_has_no_secret_values():
    provisioner = AuthV2Provisioner(
        db=None, cloud_base_url="https://cloud.example", cloud_token="tok"
    )
    requirements = await provisioner.runtime_requirements(uuid4())

    assert requirements.capability_key == "auth"
    assert requirements.capability_version == 2
    assert [r.path_prefix for r in requirements.routes] == ["/api/auth"]
    public_keys = {c.key for c in requirements.config if c.visibility == "public"}
    trusted_keys = {c.key for c in requirements.config if c.visibility == "trusted"}
    assert public_keys and trusted_keys
    # Requirement objects name config *keys*, never hold any secret material.
    serialized = requirements.to_dict()
    assert "tok" not in str(serialized)
    assert "cloud_token" not in str(serialized)


class _ContactPackResult:
    """One installed contact-capture pack, no discoverable project/App Block plan --
    exactly what the composition resolver needs to resolve the canonical "contact"
    form runtime."""

    def scalars(self):
        row = SimpleNamespace(pack_slug="contact-capture", status="installed", config={})
        return SimpleNamespace(all=lambda: [row])

    def scalar_one_or_none(self):
        return None


class _ContactPackInstalledDB:
    async def execute(self, _query):
        return _ContactPackResult()


@pytest.mark.asyncio
async def test_forms_runtime_requirements_declares_submission_route():
    requirements = await FormsProvisioner(_ContactPackInstalledDB()).runtime_requirements(uuid4())

    assert requirements.capability_key == "forms"
    assert [r.path_prefix for r in requirements.routes] == ["/api/forms"]
    assert "p2hs-forms" in requirements.platform_services
    assert any(c.key == "forms_definition:contact" for c in requirements.config)


@pytest.mark.asyncio
async def test_forms_status_is_ready_when_contact_pack_is_installed():
    status = await FormsProvisioner(_ContactPackInstalledDB()).status(uuid4())

    assert status.state == CapabilityState.READY
    assert status.details["forms"] == ["contact"]


@pytest.mark.asyncio
async def test_feature_pack_runtime_requirements_empty_when_no_packs_installed():
    db = _FakeDB(_FakeResult(rows=[]))
    provisioner = FeaturePackProvisioner(db, capability_providers={})

    requirements = await provisioner.runtime_requirements(uuid4())

    assert requirements.capability_key == "feature_packs"
    assert requirements.routes == ()
    assert requirements.platform_services == ()


@pytest.mark.asyncio
async def test_feature_pack_runtime_requirements_aggregates_auth_when_a_pack_requires_it():
    pack_row = SimpleNamespace(
        slug="staff-directory",
        composition={
            "schema_version": 2,
            "requires": [{"kind": "primitive", "id": "auth.roles"}],
        },
    )
    db = _FakeDB(
        _FakeResult(rows=[("staff-directory",)]),
        _FakeResult(scalars_list=[pack_row]),
    )
    auth_provisioner = AuthV2Provisioner(
        db=None, cloud_base_url="https://cloud.example", cloud_token="tok"
    )
    provisioner = FeaturePackProvisioner(db, capability_providers={"auth": auth_provisioner})

    requirements = await provisioner.runtime_requirements(uuid4())

    assert requirements.capability_key == "feature_packs"
    assert [r.path_prefix for r in requirements.routes] == ["/api/auth"]
    assert "p2hs-auth" in requirements.platform_services


@pytest.mark.asyncio
async def test_feature_pack_status_resolves_compatible_capability_versions_without_conflict():
    """Two installed packs formally declare (kind="capability") the auth capability
    at different minimum versions -- resolve_dependencies should pick the higher
    floor and report no conflict, proving the wiring from
    FeaturePackContract.required_capabilities() through
    FeaturePackProvisioner._capability_dependency_resolution() into status().issues.
    """
    pack_a = SimpleNamespace(
        slug="booking",
        composition={
            "schema_version": 2,
            "requires": [{"kind": "capability", "id": "auth", "min_version": "1"}],
        },
    )
    pack_b = SimpleNamespace(
        slug="crm",
        composition={
            "schema_version": 2,
            "requires": [{"kind": "capability", "id": "auth", "min_version": "2"}],
        },
    )
    def make_provisioner():
        db = _FakeDB(
            _FakeResult(rows=[("booking",), ("crm",)]),
            _FakeResult(scalars_list=[pack_a, pack_b]),
        )
        return FeaturePackProvisioner(db, capability_providers={})

    status = await make_provisioner().status(uuid4())
    assert status.issues == ()

    resolution = await make_provisioner()._capability_dependency_resolution(uuid4())
    auth = next(r for r in resolution.order if r.key == "auth")
    assert auth.version == 2
    assert resolution.ok


@pytest.mark.asyncio
async def test_feature_pack_runtime_requirements_never_imports_hosting_code():
    """Aggregation stays hosting-neutral: it only ever re-exposes what the injected
    capability providers already declared, never a hosting-specific detail."""
    import src.domain.capabilities.adapters as adapters_module

    source = adapters_module.__file__
    with open(source, encoding="utf-8") as handle:
        text = handle.read()

    for forbidden in ("cloudflare_pages", "cloudflare_w4p", "wrangler", "w4p_static"):
        assert forbidden not in text
