"""Generic Webhook service provider — receives arbitrary HTTP payloads."""

from __future__ import annotations

from typing import TYPE_CHECKING, Any

from notify_bridge_core.providers.base import ServiceProvider, ServiceProviderType
from notify_bridge_core.templates.variables import TemplateVariableDefinition

if TYPE_CHECKING:
    from notify_bridge_core.models.events import ServiceEvent

# Provider-specific variables (user-defined variables from payload_mappings
# are dynamic and documented separately in the template editor).
WEBHOOK_VARIABLES: list[TemplateVariableDefinition] = [
    TemplateVariableDefinition(
        name="raw_payload",
        type="dict",
        description="Full incoming JSON payload as a dict (use raw_payload.field or raw_payload | tojson)",
        example='{"action": "opened", "issue": {"title": "Bug"}}',
        provider_type=ServiceProviderType.WEBHOOK,
    ),
    TemplateVariableDefinition(
        name="event_type_raw",
        type="string",
        description="Raw event type extracted from payload via event_type_path (or 'webhook_received')",
        example="webhook_received",
        provider_type=ServiceProviderType.WEBHOOK,
    ),
    TemplateVariableDefinition(
        name="source_ip",
        type="string",
        description="IP address of the webhook sender",
        example="192.168.1.100",
        provider_type=ServiceProviderType.WEBHOOK,
    ),
]


class WebhookServiceProvider(ServiceProvider):
    """Generic webhook provider — no polling, receives events via HTTP POST."""

    provider_type = ServiceProviderType.WEBHOOK

    def __init__(self, name: str = "Webhook") -> None:
        self._name = name

    async def connect(self) -> bool:
        return True

    async def disconnect(self) -> None:
        pass

    async def poll(
        self,
        collection_ids: list[str],
        tracker_state: dict[str, Any],
    ) -> tuple[list[ServiceEvent], dict[str, Any]]:
        # Webhook-based provider — never polled
        return [], tracker_state

    def get_available_variables(self) -> list[TemplateVariableDefinition]:
        return WEBHOOK_VARIABLES

    def get_provider_config_schema(self) -> dict[str, Any]:
        return {
            "type": "object",
            "properties": {
                "auth_mode": {
                    "type": "string",
                    "enum": ["hmac_sha256", "bearer_token", "none"],
                    "default": "none",
                    "description": "Authentication mode for incoming webhooks",
                },
                "webhook_secret": {
                    "type": "string",
                    "description": "Secret for HMAC-SHA256 or Bearer token authentication",
                },
                "payload_mappings": {
                    "type": "array",
                    "items": {
                        "type": "object",
                        "properties": {
                            "variable": {"type": "string"},
                            "jsonpath": {"type": "string"},
                            "default": {"type": "string"},
                        },
                        "required": ["variable", "jsonpath"],
                    },
                    "description": "JSONPath rules to extract template variables from payload",
                },
                "event_type_path": {
                    "type": "string",
                    "description": "JSONPath to extract event type from payload",
                },
                "collection_path": {
                    "type": "string",
                    "description": "JSONPath to extract collection identifier from payload",
                },
            },
        }

    async def list_collections(self) -> list[dict[str, Any]]:
        return []

    async def test_connection(self) -> dict[str, Any]:
        return {"ok": True, "message": "Webhook provider is ready to receive events"}
