"""
GuardrailX Python SDK - Utilities

Helper functions for common operations.
"""

from typing import Any, Dict, Optional, Union

from .types import GatewayDecision, PolicyDecision


def is_allowed(decision: Union[Dict[str, Any], PolicyDecision, GatewayDecision]) -> bool:
    """
    Check if a decision allows the request.
    
    Args:
        decision: Policy or gateway decision
        
    Returns:
        True if action is allow or log
    """
    action = decision.get("action") if isinstance(decision, dict) else decision.action
    return action in ("allow", "log")


def is_blocked(decision: Union[Dict[str, Any], PolicyDecision, GatewayDecision]) -> bool:
    """
    Check if a decision blocks the request.
    
    Args:
        decision: Policy or gateway decision
        
    Returns:
        True if action is block or deny
    """
    action = decision.get("action") if isinstance(decision, dict) else decision.action
    return action in ("block", "deny")


def is_masked(decision: Union[Dict[str, Any], PolicyDecision, GatewayDecision]) -> bool:
    """
    Check if a decision requires masking.
    
    Args:
        decision: Policy or gateway decision
        
    Returns:
        True if action is mask
    """
    action = decision.get("action") if isinstance(decision, dict) else decision.action
    return action == "mask"


def is_error(decision: Union[Dict[str, Any], GatewayDecision]) -> bool:
    """
    Check if a decision is an error.
    
    Args:
        decision: Gateway decision
        
    Returns:
        True if action is error
    """
    action = decision.get("action") if isinstance(decision, dict) else decision.action
    return action == "error"


def get_masked_content(decision: Union[Dict[str, Any], GatewayDecision]) -> Optional[Any]:
    """
    Extract masked content from a gateway decision.
    
    Args:
        decision: Gateway decision
        
    Returns:
        Masked content or None
    """
    if isinstance(decision, dict):
        return decision.get("masked")
    return getattr(decision, "masked", None)


def get_reason(decision: Union[Dict[str, Any], PolicyDecision, GatewayDecision]) -> str:
    """
    Get the reason for a decision.
    
    Args:
        decision: Policy or gateway decision
        
    Returns:
        Reason string
    """
    if isinstance(decision, dict):
        if decision.get("reason"):
            return decision["reason"]
        if decision.get("matched_rules"):
            return f"Matched rules: {', '.join(decision['matched_rules'])}"
        return f"Action: {decision.get('action', 'unknown')}"
    
    if hasattr(decision, "reason") and decision.reason:
        return decision.reason
    if hasattr(decision, "matched_rules") and decision.matched_rules:
        return f"Matched rules: {', '.join(decision.matched_rules)}"
    return f"Action: {decision.action}"


def create_retry_config(max_retries: int = 3, base_delay: int = 250) -> Dict[str, int]:
    """
    Create a retry configuration.
    
    Args:
        max_retries: Maximum number of retry attempts
        base_delay: Base delay in milliseconds
        
    Returns:
        Retry configuration dictionary
    """
    return {
        "retries": max_retries,
        "retry_delay_ms": base_delay
    }


def create_tenant_headers(
    tenant_id: str,
    user_id: Optional[str] = None,
    api_key: Optional[str] = None
) -> Dict[str, str]:
    """
    Create headers for multi-tenant requests.
    
    Args:
        tenant_id: Tenant identifier
        user_id: Optional user identifier
        api_key: Optional API key
        
    Returns:
        Headers dictionary
    """
    headers = {"x-guardrailx-tenant": tenant_id}
    
    if user_id:
        headers["x-guardrailx-user"] = user_id
    
    if api_key:
        headers["x-guardrailx-api-key"] = api_key
    
    return headers


def format_decision(decision: Union[Dict[str, Any], PolicyDecision, GatewayDecision]) -> str:
    """
    Format a policy decision for logging.
    
    Args:
        decision: Policy or gateway decision
        
    Returns:
        Formatted decision string
    """
    if isinstance(decision, dict):
        action = decision.get("action", "unknown")
        policy_id = decision.get("policy_id")
        rule_id = decision.get("rule_id")
        tenant_id = decision.get("tenant_id")
        trace_id = decision.get("trace_id")
    else:
        action = decision.action
        policy_id = getattr(decision, "policy_id", None)
        rule_id = getattr(decision, "rule_id", None)
        tenant_id = getattr(decision, "tenant_id", None)
        trace_id = getattr(decision, "trace_id", None) if hasattr(decision, "trace_id") else None
    
    parts = [f"Action: {action}"]
    
    if policy_id:
        parts.append(f"Policy: {policy_id}")
    if rule_id:
        parts.append(f"Rule: {rule_id}")
    if tenant_id:
        parts.append(f"Tenant: {tenant_id}")
    if trace_id:
        parts.append(f"Trace: {trace_id}")
    
    return " | ".join(parts)
