"""
Flava Function MCP Tools for CQA Test Application
FastMCP-based Flava Function integration for FaaS management and operations
"""

import os
import logging
from typing import Dict
import httpx
from fastmcp import FastMCP
from lib.athenz_client import AthenzClient

logger = logging.getLogger(__name__)

# Configuration from environment variables
BASE_URL = os.getenv("FLAVA_FUNCTION_BASE_URL")

# Flava configuration - simplified
FLAVA_ENVIRONMENT = os.getenv("FLAVA_ENVIRONMENT", "stage")  # stage, dev, prod
FLAVA_PROJECT = os.getenv("FLAVA_PROJECT", "flava-qa")  # project name

# Auto-generate provider domain: flava-{product}.{environment}.{project}
PROVIDER_DOMAIN = f"flava-faas.{FLAVA_ENVIRONMENT}.{FLAVA_PROJECT}"

# Check required environment variables
required_vars = []
if not BASE_URL:
    required_vars.append("FLAVA_FUNCTION_BASE_URL")

if required_vars:
    logger.warning("Missing required environment variables: %s", required_vars)
    logger.warning(
        "Flava Function tools may not function properly without these variables"
    )

# Initialize Athenz client with fixed paths and configuration
# Use fixed paths for Athenz certificates
KEY_PATH = "/var/run/athenz/service.key.pem"
CERT_PATH = "/var/run/athenz/service.cert.pem"

ATHENZ_CLIENT = None

# Check if Athenz certificate files exist before attempting initialization
if os.path.exists(KEY_PATH) and os.path.exists(CERT_PATH):
    try:
        ATHENZ_CLIENT = AthenzClient(
            account_name=None,  # Pass None for account_name
            provider_domain=PROVIDER_DOMAIN,
            key_path=KEY_PATH,
            cert_path=CERT_PATH,
            use_proxy=False,
        )
        logger.info(
            "✅ Athenz client initialized with domain: %s",
            PROVIDER_DOMAIN,
        )
    except Exception as athenz_exception:
        logger.warning(
            "⚠️  Failed to initialize Athenz client: %s", str(athenz_exception)
        )
        logger.warning("Authentication will fall back to basic headers")
else:
    logger.info(
        "ℹ️  Athenz certificates not found (%s, %s), using basic authentication",
        KEY_PATH,
        CERT_PATH,
    )

# Create FastMCP instance for Flava Function tools
faas_mcp = FastMCP("CQA Flava Function MCP Server")


# Authentication function to get headers with access token
def get_auth_headers() -> Dict[str, str]:
    """Get authentication headers for Flava Function API."""
    headers = {"Content-Type": "application/json"}

    # Try to get access token if Athenz client is available
    if ATHENZ_CLIENT:
        try:
            access_token = ATHENZ_CLIENT.get_access_token()
            if access_token:
                headers["Authorization"] = f"Bearer {access_token}"
                logger.debug("✅ Added Athenz access token to headers")
            else:
                logger.warning("⚠️  No access token received from Athenz client")
        except Exception as auth_exception:
            logger.warning("⚠️  Failed to get access token: %s", str(auth_exception))
    else:
        logger.debug("ℹ️  No Athenz client available, using basic headers")

    return headers


def get_functions(
    project: str = FLAVA_PROJECT, limit: int = 10, offset: int = 0
) -> Dict:
    """Get functions from Flava API."""
    try:
        if not BASE_URL:
            return {"error": "FLAVA_FUNCTION_BASE_URL not configured"}

        headers = get_auth_headers()

        url = f"{BASE_URL}/projects/{project}/functions"
        params = {"limit": limit}
        if offset > 0:
            params["offset"] = offset

        logger.info("🌐 Making API request to: %s", url)
        logger.info("📋 Request params: %s", params)

        with httpx.Client(follow_redirects=True) as client:
            response = client.get(url, headers=headers, params=params, timeout=30.0)

            logger.info("📨 Response status: %s", response.status_code)

            if response.status_code == 200:
                data = response.json()
                return {
                    "success": True,
                    "project": project,
                    "functions": data,
                    "count": len(data) if isinstance(data, list) else 1,
                    "limit": limit,
                    "offset": offset,
                }

            return {
                "error": f"API request failed: {response.status_code}",
                "status_code": response.status_code,
                "response": response.text,
            }
    except Exception as api_exception:
        logger.error("Error in get_functions: %s", str(api_exception))
        return {"error": f"Error: {str(api_exception)}"}


def get_function_details(project: str, function_name: str) -> Dict:
    """Get function details from Flava API."""
    try:
        if not BASE_URL:
            return {"error": "FLAVA_FUNCTION_BASE_URL not configured"}

        headers = get_auth_headers()

        url = f"{BASE_URL}/projects/{project}/functions/{function_name}"

        with httpx.Client() as client:
            response = client.get(url, headers=headers, timeout=30.0)

            if response.status_code == 200:
                data = response.json()
                return {
                    "success": True,
                    "project": project,
                    "function_name": function_name,
                    "details": data,
                }

            return {
                "error": f"API request failed: {response.status_code}",
                "status_code": response.status_code,
                "response": response.text,
            }
    except Exception as api_exception:
        logger.error("Error in get_function_details: %s", str(api_exception))
        return {"error": f"Error: {str(api_exception)}"}


@faas_mcp.tool
def flava_get_functions(
    project: str = FLAVA_PROJECT, limit: int = 10, offset: int = 0
) -> Dict:
    """Get list of functions from Flava API.

    Args:
        project: Flava project name (default: from FLAVA_PROJECT env var)
        limit: Maximum number of results to return (default: 10)
        offset: Number of results to skip for pagination (default: 0)
    """
    logger.info("Executing flava_get_functions for project: %s", project)

    if offset < 0:
        return {"error": "Offset must be 0 or greater"}

    return get_functions(project, limit, offset)


@faas_mcp.tool
def flava_get_function_details(
    function_name: str, project: str = FLAVA_PROJECT
) -> Dict:
    """Get detailed information for a specific function.

    Args:
        function_name: The name of the function to get details for
        project: Flava project name (default: from FLAVA_PROJECT env var)
    """
    logger.info(
        "Executing flava_get_function_details for function: %s in project: %s",
        function_name,
        project,
    )

    if not function_name:
        return {"error": "function_name is required"}

    return get_function_details(project, function_name)


def get_flava_function_mcp_server():
    """Get the configured Flava Function MCP server instance"""
    return faas_mcp


def get_flava_function_mcp_info():
    """Get Flava Function MCP server information"""
    return {
        "server_name": "cqa-flava-function-mcp",
        "server_version": "1.0.0",
        "base_url": BASE_URL,
        "flava_environment": FLAVA_ENVIRONMENT,
        "flava_project": FLAVA_PROJECT,
        "provider_domain": PROVIDER_DOMAIN,
        "athenz_configured": bool(ATHENZ_CLIENT),
    }
