"""
HeadingStack — tracks section hierarchy during streaming element emission.

section_path_tier is a DETECTION QUALITY indicator (1-4), NOT a depth indicator:
  1 = native semantic markup (PDF tags, DOCX heading styles, HTML h1-h6)
  2 = font heuristic (font size + bold detection)
  3 = keyword heuristic (ALL CAPS patterns, numbered headings)
  4 = positional fallback (no heading signals found)
"""

from __future__ import annotations

from dataclasses import dataclass, field


@dataclass
class HeadingFrame:
    level: int  # 1-6 relative heading depth
    text: str  # heading text
    detection_tier: int  # quality tier at which this heading was detected (1-4)


@dataclass
class HeadingStack:
    """Maintains the current section_path during streaming document parsing."""

    detection_tier: int = 1  # document-level baseline, set by classifier
    frames: list[HeadingFrame] = field(default_factory=list)

    def push(self, level: int, text: str, detection_tier: int | None = None) -> None:
        """Push a new heading, popping any same-or-deeper levels first."""
        tier = detection_tier if detection_tier is not None else self.detection_tier
        # Pop frames at same or deeper level
        self.frames = [f for f in self.frames if f.level < level]
        self.frames.append(HeadingFrame(level=level, text=text, detection_tier=tier))

    def current_section_path(self) -> list[str]:
        """Return the current section path as an ordered list of heading texts."""
        return [f.text for f in self.frames]

    def current_section_path_tier(self) -> int:
        """
        Return the detection quality tier for the current section path.
        Uses the most recently pushed frame's tier, or document baseline.
        """
        if self.frames:
            return self.frames[-1].detection_tier
        return self.detection_tier

    def reset(self) -> None:
        """Clear all frames (e.g., at document start)."""
        self.frames.clear()

    def depth(self) -> int:
        """Return current nesting depth (NOT the same as tier)."""
        return len(self.frames)
