"""Tests for neonlink.dlq."""

from datetime import datetime, timezone

from neonlink.dlq import _classify_reason, route_to_dlq
from neonlink.mock import MockProducer
from neonlink.record import HEADER_RETRY_COUNT, Record


class TestClassifyReason:
    def test_with_retry_count(self):
        rec = Record(topic="t", headers={HEADER_RETRY_COUNT: "5"})
        assert _classify_reason(rec) == "MAX_RETRIES_EXCEEDED(retry_count=5)"

    def test_without_retry_count(self):
        rec = Record(topic="t", headers={})
        assert _classify_reason(rec) == "NON_RETRIABLE_ERROR"

    def test_zero_retry_count(self):
        rec = Record(topic="t", headers={HEADER_RETRY_COUNT: "0"})
        assert _classify_reason(rec) == "NON_RETRIABLE_ERROR"

    def test_invalid_retry_count(self):
        rec = Record(topic="t", headers={HEADER_RETRY_COUNT: "bad"})
        assert _classify_reason(rec) == "NON_RETRIABLE_ERROR"


class TestRouteToDLQTimestamp:
    """R-01: DLQ timestamp must have real sub-second precision."""

    def test_timestamp_has_subsecond_precision(self):
        mp = MockProducer()
        rec = Record(topic="src", key=b"k", value=b"v", partition=1, offset=42)
        route_to_dlq(mp, "dlq-topic", rec, ValueError("boom"))

        assert len(mp.records) == 1
        ts = mp.records[0].headers["dlq_timestamp"]
        if isinstance(ts, bytes):
            ts = ts.decode("utf-8")
        # Must parse as a valid ISO timestamp.
        parsed = datetime.fromisoformat(ts)
        assert parsed.tzinfo is not None  # Must be timezone-aware.

    def test_timestamp_not_hardcoded_zeros(self):
        mp = MockProducer()
        rec = Record(topic="src", key=b"k", value=b"v")
        route_to_dlq(mp, "dlq-topic", rec, RuntimeError("fail"))

        ts = mp.records[0].headers["dlq_timestamp"]
        if isinstance(ts, bytes):
            ts = ts.decode("utf-8")
        # Old bug: always ended with ".000Z". New format uses isoformat
        # which produces microseconds (e.g., "+00:00" suffix).
        assert ".000Z" not in ts or "+" in ts
