"""UKO Layer 3: Python-specific vocabulary (``uko-py:``).

Extends the Layer 2 Object-Oriented paradigm (``uko-oo:``) with
Python-specific semantic refinements:

Classes:
- ``PythonModule``    -- Python module (extends ``uko-code:Module``)
- ``PythonClass``     -- Python class (extends ``uko-oo:Class``)
- ``PythonFunction``  -- Python function/method (extends ``uko-oo:Method``)
- ``PythonDecorator`` -- Decorator chain entry
- ``PythonTypeStub``  -- ``.pyi`` stub type annotation

DetailLevelMap insertions (spec lines 25006-25026):
- ``DECORATED_SIGNATURES`` at depth 7 (between SIGNATURES_WITH_DOCS
  and VISIBILITY_ANNOTATED)
- ``TYPE_STUBS`` at depth 11 (between KEY_LOGIC and NEAR_COMPLETE)
- ``WITH_TESTS`` at depth 14 (beyond FULL_SOURCE)

Based on ``docs/specification.md`` ~lines 44405-44420 and 25006-25026.
"""

from __future__ import annotations

from cleveragents.acms.uko.vocabulary import (
    OO_EFFECTIVE_LEVELS,
    UKO_CODE_IRI,
    UKO_OO_IRI,
    Layer2Dependency,
    UKOClass,
    UKOProperty,
    UKOVocabulary,
    build_detail_level_map,
)

__all__: list[str] = [
    "PYTHON_DETAIL_LEVELS",
    "PYTHON_VOCABULARY",
    "PythonClass",
    "PythonDecorator",
    "PythonFunction",
    "PythonModule",
    "PythonTypeStub",
]

# ---------------------------------------------------------------------------
# Namespace constants
# ---------------------------------------------------------------------------

UKO_PY_IRI = "https://cleveragents.ai/ontology/uko/py#"
UKO_PY_PREFIX = "uko-py:"


# ---------------------------------------------------------------------------
# OWL Class definitions
# ---------------------------------------------------------------------------

PythonModule = UKOClass(
    uri=f"{UKO_PY_IRI}PythonModule",
    label="PythonModule",
    comment="A Python module (.py file) — extends uko-code:Module.",
    subclass_of=(f"{UKO_CODE_IRI}Module",),
)

PythonClass = UKOClass(
    uri=f"{UKO_PY_IRI}PythonClass",
    label="PythonClass",
    comment="A Python class definition — extends uko-oo:Class.",
    subclass_of=(f"{UKO_OO_IRI}Class",),
)

PythonFunction = UKOClass(
    uri=f"{UKO_PY_IRI}PythonFunction",
    label="PythonFunction",
    comment=(
        "A Python function or method — extends uko-oo:Method. "
        "Includes decorators and type annotations."
    ),
    subclass_of=(f"{UKO_OO_IRI}Method",),
)

# Intentionally parallel to JavaAnnotation; pending
# uko-code:Annotation base (see #576 review).
PythonDecorator = UKOClass(
    uri=f"{UKO_PY_IRI}PythonDecorator",
    label="PythonDecorator",
    comment=(
        "A decorator chain entry (@property, @staticmethod, "
        "@classmethod, custom decorators)."
    ),
    subclass_of=(f"{UKO_CODE_IRI}TypeDefinition",),
)

PythonTypeStub = UKOClass(
    uri=f"{UKO_PY_IRI}PythonTypeStub",
    label="PythonTypeStub",
    comment=("Type annotations from .pyi stub files or inline typing module usage."),
    subclass_of=(f"{UKO_CODE_IRI}TypeDefinition",),
)


# ---------------------------------------------------------------------------
# OWL Property definitions
# ---------------------------------------------------------------------------

_py_has_decorator = UKOProperty(
    uri=f"{UKO_PY_IRI}hasDecorator",
    label="hasDecorator",
    comment="Links a function/class to its decorator chain entries.",
    domain=(f"{UKO_PY_IRI}PythonFunction", f"{UKO_PY_IRI}PythonClass"),
    range_uri=f"{UKO_PY_IRI}PythonDecorator",
    is_object_property=True,
)

_py_has_type_stub = UKOProperty(
    uri=f"{UKO_PY_IRI}hasTypeStub",
    label="hasTypeStub",
    comment="Links a module/class/function to its .pyi type stub.",
    domain=(
        f"{UKO_PY_IRI}PythonModule",
        f"{UKO_PY_IRI}PythonClass",
        f"{UKO_PY_IRI}PythonFunction",
    ),
    range_uri=f"{UKO_PY_IRI}PythonTypeStub",
    is_object_property=True,
)

_py_has_test = UKOProperty(
    uri=f"{UKO_PY_IRI}hasTest",
    label="hasTest",
    comment=(
        "Links a callable to its associated test cases (for WITH_TESTS depth level)."
    ),
    domain=(f"{UKO_PY_IRI}PythonFunction", f"{UKO_PY_IRI}PythonClass"),
    range_uri=f"{UKO_PY_IRI}PythonFunction",
    is_object_property=True,
)

_py_decorator_name = UKOProperty(
    uri=f"{UKO_PY_IRI}decoratorName",
    label="decoratorName",
    comment="The string name of a decorator (e.g. 'property', 'staticmethod').",
    domain=(f"{UKO_PY_IRI}PythonDecorator",),
    range_uri="xsd:string",
    is_object_property=False,
)

_py_stub_annotation = UKOProperty(
    uri=f"{UKO_PY_IRI}stubAnnotation",
    label="stubAnnotation",
    comment="Type annotation string from a .pyi stub file.",
    domain=(f"{UKO_PY_IRI}PythonTypeStub",),
    range_uri="xsd:string",
    is_object_property=False,
)


# ---------------------------------------------------------------------------
# Layer 2 dependencies
# ---------------------------------------------------------------------------

_PY_LAYER2_DEPS = (
    Layer2Dependency(
        uri=f"{UKO_OO_IRI}Class",
        prefix="uko-oo:",
        description="OO class (PythonClass extends this).",
    ),
    Layer2Dependency(
        uri=f"{UKO_OO_IRI}Method",
        prefix="uko-oo:",
        description="OO method (PythonFunction extends this).",
    ),
    # Conceptual reference — no Layer 3 class directly extends this.
    Layer2Dependency(
        uri=f"{UKO_OO_IRI}Interface",
        prefix="uko-oo:",
        description="OO interface (referenced for protocol support).",
    ),
    # Conceptual reference — no Layer 3 class directly extends this.
    Layer2Dependency(
        uri=f"{UKO_OO_IRI}Attribute",
        prefix="uko-oo:",
        description="OO attribute (referenced for member listings).",
    ),
    Layer2Dependency(
        uri=f"{UKO_CODE_IRI}Module",
        prefix="uko-code:",
        layer=1,
        description="General code module (PythonModule extends this).",
    ),
    Layer2Dependency(
        uri=f"{UKO_CODE_IRI}TypeDefinition",
        prefix="uko-code:",
        layer=1,
        description="General type definition (PythonTypeStub extends this).",
    ),
)


# ---------------------------------------------------------------------------
# DetailLevelMap: uko-oo: effective map (parent) then uko-py: insertions
# ---------------------------------------------------------------------------

# Python-specific insertions (spec lines 25006-25026)
_PY_INSERTIONS: tuple[tuple[str, int], ...] = (
    # DECORATED_SIGNATURES: between SIGNATURES_WITH_DOCS(6) and
    # VISIBILITY_ANNOTATED(7) — use 6 so it sorts after depth-6 parent
    ("DECORATED_SIGNATURES", 6),
    # TYPE_STUBS: between KEY_LOGIC(9) and NEAR_COMPLETE(10)
    ("TYPE_STUBS", 9),
    # WITH_TESTS: beyond FULL_SOURCE(11)
    ("WITH_TESTS", 12),
)

# Build the full Python effective map
PYTHON_DETAIL_LEVELS: tuple[tuple[str, int], ...] = build_detail_level_map(
    OO_EFFECTIVE_LEVELS, _PY_INSERTIONS
)


# ---------------------------------------------------------------------------
# Vocabulary definition
# ---------------------------------------------------------------------------

PYTHON_VOCABULARY = UKOVocabulary(
    namespace=UKO_PY_IRI,
    prefix=UKO_PY_PREFIX,
    layer=3,
    label="Python Technology Vocabulary",
    comment=(
        "Layer 3 technology-specific vocabulary for Python. "
        "Extends uko-oo: with decorator chains, .pyi stub type "
        "annotations, and associated test cases."
    ),
    parent_prefixes=("uko-oo:",),
    classes=(
        PythonModule,
        PythonClass,
        PythonFunction,
        PythonDecorator,
        PythonTypeStub,
    ),
    properties=(
        _py_has_decorator,
        _py_has_type_stub,
        _py_has_test,
        _py_decorator_name,
        _py_stub_annotation,
    ),
    layer2_dependencies=_PY_LAYER2_DEPS,
    inserted_levels=(
        (
            "DECORATED_SIGNATURES",
            "@property, @staticmethod, @classmethod, custom decorator chains.",
        ),
        (
            "TYPE_STUBS",
            "Type annotations from .pyi stub files, typing module usage.",
        ),
        (
            "WITH_TESTS",
            "Full source + associated test cases for each callable.",
        ),
    ),
)
