"""
Risicare Error Taxonomy

A comprehensive classification system for AI agent failures based on
the Multi-Agent Systems Taxonomy (MAST) and extended for LLM-specific errors.

The taxonomy is organized into 10 modules with 154 total error codes:
- 10 modules (5 single-agent + 5 multi-agent)
- 3-4 categories per module (REASONING has 4)
- 4-5 error codes per category

SINGLE-AGENT MODULES (5 modules):
1. PERCEPTION - Input processing and understanding failures
2. REASONING - Cognitive and logic failures
3. TOOL - Tool and action execution failures
4. MEMORY - State and context management failures
5. OUTPUT - Response generation failures

MULTI-AGENT MODULES (5 modules):
6. COORDINATION - Multi-agent workflow failures
7. COMMUNICATION - Inter-agent messaging failures
8. ORCHESTRATION - Agent lifecycle management failures
9. CONSENSUS - Agreement and conflict resolution failures
10. RESOURCES - Shared resource management failures
"""

from __future__ import annotations

import re
from dataclasses import dataclass, field
from typing import Any, Dict, List, Optional, Tuple


# =============================================================================
# Base Types
# =============================================================================

@dataclass(frozen=True)
class ErrorCode:
    """
    A unique error code with module and category information.

    Format: {MODULE}.{CATEGORY}.{SUBCATEGORY}
    Example: PERCEPTION.INPUT.MALFORMED
    """
    code: str
    module: str
    category: str
    subcategory: str
    severity: int  # 1-5, 5 being most severe
    description: str
    remediation: str

    def to_dict(self) -> Dict[str, Any]:
        """Convert to dictionary."""
        return {
            "code": self.code,
            "module": self.module,
            "category": self.category,
            "subcategory": self.subcategory,
            "severity": self.severity,
            "description": self.description,
            "remediation": self.remediation,
        }


@dataclass
class ErrorCategory:
    """A category of errors within a module."""
    name: str
    description: str
    module_name: str = ""
    error_codes: List[ErrorCode] = field(default_factory=list)

    def add_error(
        self,
        subcategory: str,
        severity: int,
        description: str,
        remediation: str,
    ) -> ErrorCode:
        """Add an error code to this category."""
        code = ErrorCode(
            code=f"{self.module_name}.{self.name}.{subcategory}",
            module=self.module_name,
            category=self.name,
            subcategory=subcategory,
            severity=severity,
            description=description,
            remediation=remediation,
        )
        self.error_codes.append(code)
        _ERROR_CODE_REGISTRY[code.code] = code
        return code


@dataclass
class TaxonomyModule:
    """A taxonomy module containing related error categories."""
    name: str
    description: str
    categories: List[ErrorCategory] = field(default_factory=list)

    def add_category(self, name: str, description: str) -> ErrorCategory:
        """Add a category to this module."""
        category = ErrorCategory(name=name, description=description, module_name=self.name)
        self.categories.append(category)
        return category

    def get_category(self, name: str) -> Optional[ErrorCategory]:
        """Get a category by name."""
        for cat in self.categories:
            if cat.name == name:
                return cat
        return None

    @property
    def all_error_codes(self) -> List[ErrorCode]:
        """Get all error codes in this module."""
        codes = []
        for cat in self.categories:
            codes.extend(cat.error_codes)
        return codes


# Global registry for error code lookup
_ERROR_CODE_REGISTRY: Dict[str, ErrorCode] = {}


# =============================================================================
# Module 1: PERCEPTION
# =============================================================================

PERCEPTION = TaxonomyModule(
    name="PERCEPTION",
    description="Input processing and understanding failures"
)

_input = PERCEPTION.add_category("INPUT", "Raw input processing failures")
_input.add_error("MALFORMED", 3, "Input data is malformed or corrupted", "Validate input format before processing")
_input.add_error("TRUNCATED", 2, "Input was truncated due to length limits", "Implement chunking or summarization")
_input.add_error("ENCODING", 3, "Character encoding issues in input", "Normalize encoding to UTF-8")
_input.add_error("SCHEMA_MISMATCH", 4, "Input doesn't match expected schema", "Validate against schema before processing")
_input.add_error("INJECTION", 5, "Potential prompt injection detected", "Implement input sanitization")

_parsing = PERCEPTION.add_category("PARSING", "Structured data extraction failures")
_parsing.add_error("JSON_INVALID", 3, "Failed to parse JSON from input", "Use robust JSON parsing with error recovery")
_parsing.add_error("XML_INVALID", 3, "Failed to parse XML from input", "Validate XML structure")
_parsing.add_error("DATE_FORMAT", 2, "Date/time parsing failure", "Normalize date formats")
_parsing.add_error("NUMBER_FORMAT", 2, "Numeric parsing failure", "Handle locale-specific number formats")
_parsing.add_error("REFERENCE_BROKEN", 3, "Broken reference or link in input", "Validate references before processing")

_context = PERCEPTION.add_category("CONTEXT", "Context understanding failures")
_context.add_error("MISSING", 4, "Required context is missing", "Ensure all required context is provided")
_context.add_error("STALE", 3, "Context is outdated or stale", "Implement context freshness checks")
_context.add_error("CONFLICTING", 4, "Conflicting information in context", "Implement conflict resolution")
_context.add_error("OVERFLOW", 3, "Context exceeds model limits", "Implement context compression or summarization")
_context.add_error("IRRELEVANT", 2, "Context includes irrelevant information", "Improve context filtering")


# =============================================================================
# Module 2: REASONING
# =============================================================================

REASONING = TaxonomyModule(
    name="REASONING",
    description="Cognitive and logic failures"
)

_logic = REASONING.add_category("LOGIC", "Logical reasoning failures")
_logic.add_error("CONTRADICTION", 4, "Self-contradictory reasoning", "Add consistency checks")
_logic.add_error("CIRCULAR", 3, "Circular reasoning detected", "Detect and break circular dependencies")
_logic.add_error("INCOMPLETE", 3, "Incomplete reasoning chain", "Require complete reasoning traces")
_logic.add_error("INVALID_INFERENCE", 4, "Invalid logical inference", "Validate inference steps")
_logic.add_error("MISSING_PREMISE", 3, "Missing premise in argument", "Ensure all premises are explicit")

_hallucination = REASONING.add_category("HALLUCINATION", "Fabricated or incorrect information")
_hallucination.add_error("FACTUAL", 5, "Factually incorrect statement", "Implement fact checking against knowledge base")
_hallucination.add_error("ENTITY", 4, "Non-existent entity referenced", "Validate entity existence")
_hallucination.add_error("CAPABILITY", 3, "Claimed non-existent capability", "Validate capability claims")
_hallucination.add_error("TEMPORAL", 4, "Incorrect temporal information", "Validate temporal claims")
_hallucination.add_error("CITATION", 3, "Fabricated citation or reference", "Validate all citations")

_planning = REASONING.add_category("PLANNING", "Plan formulation failures")
_planning.add_error("INFEASIBLE", 4, "Plan is not executable", "Validate plan feasibility before execution")
_planning.add_error("SUBOPTIMAL", 2, "Plan is significantly suboptimal", "Implement plan optimization")
_planning.add_error("INCOMPLETE", 3, "Plan has missing steps", "Validate plan completeness")
_planning.add_error("UNSAFE", 5, "Plan violates safety constraints", "Add safety constraint validation")
_planning.add_error("SCOPE_CREEP", 2, "Plan exceeds task scope", "Validate plan scope")

_decision = REASONING.add_category("DECISION", "Decision-making failures")
_decision.add_error("INDECISIVE", 2, "Unable to make a decision", "Add decision timeout and defaults")
_decision.add_error("PREMATURE", 3, "Decision made without sufficient information", "Require minimum information threshold")
_decision.add_error("BIASED", 4, "Biased decision-making detected", "Implement bias detection and correction")
_decision.add_error("OSCILLATING", 3, "Oscillating between decisions", "Add decision stability checks")
_decision.add_error("OVERCONFIDENT", 3, "Overconfident in uncertain decisions", "Calibrate confidence scores")


# =============================================================================
# Module 3: TOOL
# =============================================================================

TOOL = TaxonomyModule(
    name="TOOL",
    description="Tool and action execution failures"
)

_invocation = TOOL.add_category("INVOCATION", "Tool calling failures")
_invocation.add_error("NOT_FOUND", 4, "Tool not found or unavailable", "Validate tool availability before planning")
_invocation.add_error("INVALID_ARGS", 4, "Invalid arguments to tool", "Validate arguments against schema")
_invocation.add_error("TYPE_MISMATCH", 3, "Argument type mismatch", "Implement type coercion")
_invocation.add_error("MISSING_REQUIRED", 4, "Missing required argument", "Validate required arguments")
_invocation.add_error("PERMISSION_DENIED", 4, "Permission denied for tool", "Check permissions before invocation")

_execution = TOOL.add_category("EXECUTION", "Tool execution failures")
_execution.add_error("TIMEOUT", 3, "Tool execution timed out", "Implement timeout handling")
_execution.add_error("CRASHED", 5, "Tool crashed during execution", "Add crash recovery")
_execution.add_error("RATE_LIMITED", 3, "Tool rate limited", "Implement rate limit handling with backoff")
_execution.add_error("DEPENDENCY_FAILED", 4, "Tool dependency failed", "Validate dependencies before execution")
_execution.add_error("RESOURCE_EXHAUSTED", 4, "Tool exhausted resources", "Implement resource limits")

_result = TOOL.add_category("RESULT", "Tool result handling failures")
_result.add_error("UNPARSEABLE", 4, "Cannot parse tool result", "Implement robust result parsing")
_result.add_error("UNEXPECTED_FORMAT", 3, "Unexpected result format", "Validate result schema")
_result.add_error("PARTIAL", 2, "Partial result returned", "Handle partial results gracefully")
_result.add_error("EMPTY", 2, "Empty result returned", "Handle empty results")
_result.add_error("ERROR_IN_RESULT", 3, "Error embedded in result", "Parse and handle result errors")


# =============================================================================
# Module 4: MEMORY
# =============================================================================

MEMORY = TaxonomyModule(
    name="MEMORY",
    description="State and context management failures"
)

_state = MEMORY.add_category("STATE", "State management failures")
_state.add_error("CORRUPTED", 5, "State corruption detected", "Implement state checksums")
_state.add_error("INCONSISTENT", 4, "Inconsistent state across components", "Use transactional state updates")
_state.add_error("LOST", 5, "State was lost", "Implement state persistence")
_state.add_error("STALE", 3, "State is outdated", "Implement state freshness checks")
_state.add_error("OVERFLOW", 3, "State size exceeded limits", "Implement state pruning")

_retrieval = MEMORY.add_category("RETRIEVAL", "Memory retrieval failures")
_retrieval.add_error("NOT_FOUND", 3, "Requested memory not found", "Handle missing memories gracefully")
_retrieval.add_error("WRONG_MATCH", 4, "Retrieved wrong memory", "Improve retrieval precision")
_retrieval.add_error("OUTDATED", 3, "Retrieved outdated memory", "Implement memory freshness")
_retrieval.add_error("INCOMPLETE", 2, "Retrieved incomplete memory", "Store complete memory records")
_retrieval.add_error("TOO_MANY", 2, "Too many memories retrieved", "Implement result ranking and filtering")

_context_window = MEMORY.add_category("CONTEXT_WINDOW", "Context window management failures")
_context_window.add_error("EXCEEDED", 3, "Context window exceeded", "Implement context summarization")
_context_window.add_error("FRAGMENTED", 2, "Context is fragmented", "Implement context consolidation")
_context_window.add_error("PRIORITY_ERROR", 3, "Wrong context priority", "Improve context prioritization")
_context_window.add_error("DROPPED", 3, "Important context was dropped", "Implement context importance scoring")


# =============================================================================
# Module 5: OUTPUT
# =============================================================================

OUTPUT = TaxonomyModule(
    name="OUTPUT",
    description="Response generation failures"
)

_format = OUTPUT.add_category("FORMAT", "Output formatting failures")
_format.add_error("INVALID_JSON", 3, "Invalid JSON output", "Use structured output parsing")
_format.add_error("SCHEMA_VIOLATION", 4, "Output violates schema", "Validate against output schema")
_format.add_error("MALFORMED", 3, "Malformed output structure", "Implement output validation")
_format.add_error("TRUNCATED", 2, "Output was truncated", "Handle output length limits")
_format.add_error("ENCODING", 2, "Output encoding issues", "Normalize output encoding")

_quality = OUTPUT.add_category("QUALITY", "Output quality failures")
_quality.add_error("INCOMPLETE", 3, "Incomplete response", "Validate response completeness")
_quality.add_error("IRRELEVANT", 3, "Response is irrelevant to query", "Improve response relevance")
_quality.add_error("VERBOSE", 2, "Overly verbose response", "Implement response length optimization")
_quality.add_error("UNCLEAR", 2, "Unclear or ambiguous response", "Add clarity checks")
_quality.add_error("REPETITIVE", 2, "Repetitive content in response", "Detect and reduce repetition")

_safety = OUTPUT.add_category("SAFETY", "Output safety failures")
_safety.add_error("HARMFUL_CONTENT", 5, "Potentially harmful content", "Implement content filtering")
_safety.add_error("PII_LEAK", 5, "PII leaked in output", "Implement PII detection and masking")
_safety.add_error("BIAS", 4, "Biased content in output", "Implement bias detection")
_safety.add_error("POLICY_VIOLATION", 4, "Output violates policy", "Add policy compliance checks")
_safety.add_error("COPYRIGHT", 3, "Potential copyright violation", "Implement copyright checks")


# =============================================================================
# Module 6: COORDINATION (Multi-Agent)
# =============================================================================

COORDINATION = TaxonomyModule(
    name="COORDINATION",
    description="Multi-agent workflow coordination failures"
)

_workflow = COORDINATION.add_category("WORKFLOW", "Workflow management failures")
_workflow.add_error("DEADLOCK", 5, "Agents in deadlock", "Implement deadlock detection and resolution")
_workflow.add_error("LIVELOCK", 4, "Agents in livelock", "Implement livelock detection")
_workflow.add_error("STARVATION", 4, "Agent starvation", "Implement fair scheduling")
_workflow.add_error("CYCLE", 3, "Cyclic dependency in workflow", "Validate workflow DAG")
_workflow.add_error("ORPHANED", 3, "Orphaned task or agent", "Implement orphan detection")

_handoff = COORDINATION.add_category("HANDOFF", "Task handoff failures")
_handoff.add_error("INCOMPLETE", 4, "Incomplete handoff information", "Validate handoff completeness")
_handoff.add_error("WRONG_RECIPIENT", 4, "Task sent to wrong agent", "Validate recipient capabilities")
_handoff.add_error("LOST", 5, "Handoff was lost", "Implement handoff acknowledgment")
_handoff.add_error("DUPLICATED", 3, "Duplicate handoffs", "Implement idempotent handoffs")
_handoff.add_error("DELAYED", 2, "Handoff significantly delayed", "Monitor handoff latency")

_sync = COORDINATION.add_category("SYNCHRONIZATION", "Agent synchronization failures")
_sync.add_error("RACE_CONDITION", 5, "Race condition between agents", "Implement proper locking")
_sync.add_error("OUT_OF_ORDER", 4, "Out of order execution", "Implement ordering guarantees")
_sync.add_error("SPLIT_BRAIN", 5, "Split brain scenario", "Implement leader election")
_sync.add_error("CLOCK_SKEW", 3, "Significant clock skew", "Use logical clocks")
_sync.add_error("VERSION_MISMATCH", 3, "Version mismatch between agents", "Implement version negotiation")


# =============================================================================
# Module 7: COMMUNICATION (Multi-Agent)
# =============================================================================

COMMUNICATION = TaxonomyModule(
    name="COMMUNICATION",
    description="Inter-agent messaging failures"
)

_delivery = COMMUNICATION.add_category("DELIVERY", "Message delivery failures")
_delivery.add_error("UNDELIVERABLE", 4, "Message could not be delivered", "Implement message retry")
_delivery.add_error("DELAYED", 2, "Message significantly delayed", "Monitor message latency")
_delivery.add_error("DUPLICATED", 3, "Duplicate message delivered", "Implement idempotent handlers")
_delivery.add_error("OUT_OF_ORDER", 3, "Messages delivered out of order", "Implement message ordering")
_delivery.add_error("EXPIRED", 3, "Message expired before delivery", "Implement TTL handling")

_content = COMMUNICATION.add_category("CONTENT", "Message content failures")
_content.add_error("MALFORMED", 4, "Malformed message content", "Validate message schema")
_content.add_error("INCOMPATIBLE", 4, "Incompatible message format", "Implement format negotiation")
_content.add_error("TOO_LARGE", 3, "Message exceeds size limit", "Implement message chunking")
_content.add_error("AMBIGUOUS", 3, "Ambiguous message content", "Require structured messages")
_content.add_error("CORRUPTED", 4, "Message content corrupted", "Implement message checksums")

_routing = COMMUNICATION.add_category("ROUTING", "Message routing failures")
_routing.add_error("NO_ROUTE", 4, "No route to destination", "Implement route discovery")
_routing.add_error("WRONG_ROUTE", 4, "Message routed incorrectly", "Validate routing rules")
_routing.add_error("LOOP", 4, "Message routing loop", "Implement loop detection")
_routing.add_error("BROADCAST_STORM", 3, "Broadcast message storm", "Implement broadcast throttling")
_routing.add_error("PARTITION", 4, "Network partition detected", "Handle partition gracefully")


# =============================================================================
# Module 8: ORCHESTRATION (Multi-Agent)
# =============================================================================

ORCHESTRATION = TaxonomyModule(
    name="ORCHESTRATION",
    description="Agent lifecycle and management failures"
)

_lifecycle = ORCHESTRATION.add_category("LIFECYCLE", "Agent lifecycle failures")
_lifecycle.add_error("SPAWN_FAILED", 4, "Failed to spawn agent", "Implement spawn retry")
_lifecycle.add_error("CRASHED", 5, "Agent crashed", "Implement crash recovery")
_lifecycle.add_error("HUNG", 4, "Agent is unresponsive", "Implement health checks")
_lifecycle.add_error("ZOMBIE", 3, "Zombie agent detected", "Implement zombie cleanup")
_lifecycle.add_error("CLEANUP_FAILED", 3, "Failed to cleanup agent", "Implement forced cleanup")

_scaling = ORCHESTRATION.add_category("SCALING", "Scaling failures")
_scaling.add_error("SCALE_UP_FAILED", 4, "Failed to scale up", "Implement scale retry")
_scaling.add_error("SCALE_DOWN_FAILED", 3, "Failed to scale down", "Implement forced scale down")
_scaling.add_error("OVERLOADED", 4, "System overloaded", "Implement load shedding")
_scaling.add_error("UNDERUTILIZED", 2, "System underutilized", "Implement auto-scaling")
_scaling.add_error("QUOTA_EXCEEDED", 3, "Quota exceeded", "Implement quota management")

_delegation = ORCHESTRATION.add_category("DELEGATION", "Task delegation failures")
_delegation.add_error("NO_AVAILABLE_AGENT", 4, "No agent available for delegation", "Implement agent pool")
_delegation.add_error("CAPABILITY_MISMATCH", 4, "Agent lacks required capability", "Match capabilities to tasks")
_delegation.add_error("OVERLOADED_AGENT", 3, "Target agent overloaded", "Implement load balancing")
_delegation.add_error("CIRCULAR_DELEGATION", 4, "Circular delegation detected", "Track delegation chain")
_delegation.add_error("EXCESSIVE_DEPTH", 3, "Delegation chain too deep", "Limit delegation depth")


# =============================================================================
# Module 9: CONSENSUS (Multi-Agent)
# =============================================================================

CONSENSUS = TaxonomyModule(
    name="CONSENSUS",
    description="Agreement and conflict resolution failures"
)

_agreement = CONSENSUS.add_category("AGREEMENT", "Agreement failures")
_agreement.add_error("TIMEOUT", 3, "Consensus timeout", "Implement timeout handling")
_agreement.add_error("QUORUM_FAILED", 4, "Failed to reach quorum", "Handle quorum failures")
_agreement.add_error("INCONSISTENT", 5, "Inconsistent agreement state", "Implement consensus validation")
_agreement.add_error("REJECTED", 3, "Proposal rejected", "Handle rejection gracefully")
_agreement.add_error("STALE_VOTE", 2, "Stale vote received", "Implement vote freshness")

_conflict = CONSENSUS.add_category("CONFLICT", "Conflict resolution failures")
_conflict.add_error("UNRESOLVED", 4, "Conflict unresolved", "Implement conflict escalation")
_conflict.add_error("RESOLUTION_REJECTED", 3, "Resolution rejected by parties", "Implement resolution retry")
_conflict.add_error("CASCADING", 5, "Cascading conflicts", "Implement conflict isolation")
_conflict.add_error("BIAS", 4, "Biased conflict resolution", "Implement fair resolution")
_conflict.add_error("DEADLOCK", 5, "Conflict resolution deadlock", "Implement deadlock breaking")

_voting = CONSENSUS.add_category("VOTING", "Voting failures")
_voting.add_error("INVALID_VOTE", 3, "Invalid vote received", "Validate vote format")
_voting.add_error("DUPLICATE_VOTE", 3, "Duplicate vote detected", "Implement vote deduplication")
_voting.add_error("COERCED_VOTE", 5, "Vote coercion detected", "Implement vote privacy")
_voting.add_error("SPLIT_VOTE", 2, "Split vote result", "Implement tiebreaker")
_voting.add_error("ABSTENTION_FLOOD", 3, "Too many abstentions", "Handle abstentions")


# =============================================================================
# Module 10: RESOURCES (Multi-Agent)
# =============================================================================

RESOURCES = TaxonomyModule(
    name="RESOURCES",
    description="Shared resource management failures"
)

_access = RESOURCES.add_category("ACCESS", "Resource access failures")
_access.add_error("DENIED", 4, "Resource access denied", "Implement access control")
_access.add_error("NOT_FOUND", 3, "Resource not found", "Handle missing resources")
_access.add_error("LOCKED", 3, "Resource is locked", "Implement lock timeout")
_access.add_error("EXPIRED", 3, "Resource access expired", "Handle expiration")
_access.add_error("REVOKED", 4, "Resource access revoked", "Handle revocation gracefully")

_contention = RESOURCES.add_category("CONTENTION", "Resource contention failures")
_contention.add_error("DEADLOCK", 5, "Resource deadlock", "Implement deadlock prevention")
_contention.add_error("STARVATION", 4, "Resource starvation", "Implement fair scheduling")
_contention.add_error("PRIORITY_INVERSION", 4, "Priority inversion", "Implement priority inheritance")
_contention.add_error("THRASHING", 4, "Resource thrashing", "Implement throttling")
_contention.add_error("OVERFLOW", 3, "Resource pool overflow", "Implement pool limits")

_quota = RESOURCES.add_category("QUOTA", "Resource quota failures")
_quota.add_error("EXCEEDED", 3, "Quota exceeded", "Implement quota enforcement")
_quota.add_error("ALLOCATION_FAILED", 4, "Quota allocation failed", "Handle allocation failure")
_quota.add_error("UNFAIR_DISTRIBUTION", 3, "Unfair quota distribution", "Implement fair distribution")
_quota.add_error("LEAK", 4, "Quota leak detected", "Implement quota accounting")
_quota.add_error("STALE", 2, "Quota information is stale", "Refresh quota regularly")


# =============================================================================
# Module Registry
# =============================================================================

ALL_MODULES = [
    PERCEPTION,
    REASONING,
    TOOL,
    MEMORY,
    OUTPUT,
    COORDINATION,
    COMMUNICATION,
    ORCHESTRATION,
    CONSENSUS,
    RESOURCES,
]

_MODULE_MAP = {m.name: m for m in ALL_MODULES}


def get_module(name: str) -> Optional[TaxonomyModule]:
    """Get a taxonomy module by name."""
    return _MODULE_MAP.get(name.upper())


def get_category(module_name: str, category_name: str) -> Optional[ErrorCategory]:
    """Get an error category by module and category name."""
    module = get_module(module_name)
    if module:
        return module.get_category(category_name.upper())
    return None


def get_error_code(code: str) -> Optional[ErrorCode]:
    """Get an error code by its full code string."""
    return _ERROR_CODE_REGISTRY.get(code)


def classify_error(
    error: Exception,
    context: Optional[Dict[str, Any]] = None,
) -> Tuple[Optional[ErrorCode], float]:
    """
    Classify an error using the taxonomy.

    This is a simple rule-based classifier. The full diagnosis engine
    uses LLM-based classification for better accuracy.

    Args:
        error: The exception to classify.
        context: Additional context for classification.

    Returns:
        Tuple of (error_code, confidence). Error code may be None if
        classification fails.
    """
    error_msg = str(error).lower()

    # Simple keyword-based classification
    classifications = [
        # PERCEPTION
        (r"json", "PERCEPTION.PARSING.JSON_INVALID", 0.7),
        (r"encoding", "PERCEPTION.INPUT.ENCODING", 0.7),
        (r"injection", "PERCEPTION.INPUT.INJECTION", 0.9),
        (r"malformed", "PERCEPTION.INPUT.MALFORMED", 0.7),

        # REASONING
        (r"hallucin", "REASONING.HALLUCINATION.FACTUAL", 0.6),
        (r"contradict", "REASONING.LOGIC.CONTRADICTION", 0.7),

        # TOOL
        (r"timeout", "TOOL.EXECUTION.TIMEOUT", 0.8),
        (r"rate.?limit", "TOOL.EXECUTION.RATE_LIMITED", 0.9),
        (r"permission", "TOOL.INVOCATION.PERMISSION_DENIED", 0.8),

        # MEMORY
        (r"context.+overflow", "MEMORY.CONTEXT_WINDOW.EXCEEDED", 0.8),
        (r"state.+corrupt", "MEMORY.STATE.CORRUPTED", 0.8),

        # OUTPUT
        (r"pii", "OUTPUT.SAFETY.PII_LEAK", 0.9),

        # COORDINATION
        (r"deadlock", "COORDINATION.WORKFLOW.DEADLOCK", 0.9),

        # COMMUNICATION
        (r"undeliverable", "COMMUNICATION.DELIVERY.UNDELIVERABLE", 0.8),

        # ORCHESTRATION
        (r"crash", "ORCHESTRATION.LIFECYCLE.CRASHED", 0.8),

        # CONSENSUS
        (r"quorum", "CONSENSUS.AGREEMENT.QUORUM_FAILED", 0.9),

        # RESOURCES
        (r"quota.+exceed", "RESOURCES.QUOTA.EXCEEDED", 0.9),
    ]

    for pattern, code_str, confidence in classifications:
        if re.search(pattern, error_msg):
            code = get_error_code(code_str)
            if code:
                return (code, confidence)

    return (None, 0.0)


# =============================================================================
# Exports
# =============================================================================

__all__ = [
    # Types
    "ErrorCode",
    "ErrorCategory",
    "TaxonomyModule",
    # Modules
    "PERCEPTION",
    "REASONING",
    "TOOL",
    "MEMORY",
    "OUTPUT",
    "COORDINATION",
    "COMMUNICATION",
    "ORCHESTRATION",
    "CONSENSUS",
    "RESOURCES",
    "ALL_MODULES",
    # Functions
    "get_module",
    "get_category",
    "get_error_code",
    "classify_error",
]
