"""
Regulation & Requirement models — extracted from compliance/db/models.py.

The foundational compliance aggregate: regulations (GDPR, AI Act, CRA, ...) and
the individual requirements they contain. Re-exported from
``compliance.db.models`` for backwards compatibility.

DO NOT change __tablename__, column names, or relationship strings.
"""

import uuid
import enum
from datetime import datetime, timezone

from sqlalchemy import (
    Column, String, Text, Integer, Boolean, DateTime, Date,
    ForeignKey, Enum, JSON, Index,
)
from sqlalchemy.orm import relationship

from classroom_engine.database import Base


# ============================================================================
# ENUMS
# ============================================================================

class RegulationTypeEnum(str, enum.Enum):
    """Type of regulation/standard."""
    EU_REGULATION = "eu_regulation"      # Directly applicable EU law
    EU_DIRECTIVE = "eu_directive"        # Requires national implementation
    DE_LAW = "de_law"                    # German national law
    BSI_STANDARD = "bsi_standard"        # BSI technical guidelines
    INDUSTRY_STANDARD = "industry_standard"  # ISO, OWASP, etc.


# ============================================================================
# MODELS
# ============================================================================

class RegulationDB(Base):
    """
    Represents a regulation, directive, or standard.

    Examples: GDPR, AI Act, CRA, BSI-TR-03161
    """
    __tablename__ = 'compliance_regulations'

    id = Column(String(36), primary_key=True, default=lambda: str(uuid.uuid4()))
    code = Column(String(20), unique=True, nullable=False, index=True)  # e.g., "GDPR", "AIACT"
    name = Column(String(200), nullable=False)                           # Short name
    full_name = Column(Text)                                             # Full official name
    regulation_type = Column(Enum(RegulationTypeEnum), nullable=False)
    source_url = Column(String(500))                                     # EUR-Lex URL or similar
    local_pdf_path = Column(String(500))                                 # Local PDF if available
    effective_date = Column(Date)                                        # When it came into force
    description = Column(Text)                                           # Brief description
    is_active = Column(Boolean, default=True)

    # Timestamps
    created_at = Column(DateTime, default=lambda: datetime.now(timezone.utc))
    updated_at = Column(DateTime, default=lambda: datetime.now(timezone.utc), onupdate=lambda: datetime.now(timezone.utc))

    # Relationships
    requirements = relationship("RequirementDB", back_populates="regulation", cascade="all, delete-orphan")

    def __repr__(self):
        return f"<Regulation {self.code}: {self.name}>"


class RequirementDB(Base):
    """
    Individual requirement from a regulation.

    Examples: GDPR Art. 32(1)(a), AI Act Art. 9, BSI-TR O.Auth_1
    """
    __tablename__ = 'compliance_requirements'

    id = Column(String(36), primary_key=True, default=lambda: str(uuid.uuid4()))
    regulation_id = Column(String(36), ForeignKey('compliance_regulations.id'), nullable=False, index=True)

    # Requirement identification
    article = Column(String(50), nullable=False)                         # e.g., "Art. 32", "O.Auth_1"
    paragraph = Column(String(20))                                       # e.g., "(1)(a)"
    requirement_id_external = Column(String(50))                         # External ID (e.g., BSI ID)
    title = Column(String(300), nullable=False)                          # Requirement title
    description = Column(Text)                                           # Brief description
    requirement_text = Column(Text)                                      # Original text from regulation

    # Breakpilot-specific interpretation and implementation
    breakpilot_interpretation = Column(Text)                             # How Breakpilot interprets this
    implementation_status = Column(String(30), default="not_started")    # not_started, in_progress, implemented, verified
    implementation_details = Column(Text)                                # How we implemented it
    code_references = Column(JSON)                                       # List of {"file": "...", "line": ..., "description": "..."}
    documentation_links = Column(JSON)                                   # List of internal doc links

    # Evidence for auditors
    evidence_description = Column(Text)                                  # What evidence proves compliance
    evidence_artifacts = Column(JSON)                                    # List of {"type": "...", "path": "...", "description": "..."}

    # Audit-specific fields
    auditor_notes = Column(Text)                                         # Notes from auditor review
    audit_status = Column(String(30), default="pending")                 # pending, in_review, approved, rejected
    last_audit_date = Column(DateTime)
    last_auditor = Column(String(100))

    is_applicable = Column(Boolean, default=True)                        # Applicable to Breakpilot?
    applicability_reason = Column(Text)                                  # Why/why not applicable

    priority = Column(Integer, default=2)                                # 1=Critical, 2=High, 3=Medium

    # Source document reference
    source_page = Column(Integer)                                        # Page number in source document
    source_section = Column(String(100))                                 # Section in source document

    # Timestamps
    created_at = Column(DateTime, default=lambda: datetime.now(timezone.utc))
    updated_at = Column(DateTime, default=lambda: datetime.now(timezone.utc), onupdate=lambda: datetime.now(timezone.utc))

    # Relationships
    regulation = relationship("RegulationDB", back_populates="requirements")
    control_mappings = relationship("ControlMappingDB", back_populates="requirement", cascade="all, delete-orphan")

    __table_args__ = (
        Index('ix_requirement_regulation_article', 'regulation_id', 'article'),
        Index('ix_requirement_audit_status', 'audit_status'),
        Index('ix_requirement_impl_status', 'implementation_status'),
    )

    def __repr__(self):
        return f"<Requirement {self.article} {self.paragraph or ''}>"


__all__ = ["RegulationTypeEnum", "RegulationDB", "RequirementDB"]
