"""
Implementation of the ScorerData class.

ScorerData holds the information related to a single, completed Scorer evaluation run.
"""

from __future__ import annotations

from judgeval.data.judgment_types import ScorerData as JudgmentScorerData
from judgeval.scorers import BaseScorer
from typing import List


class ScorerData(JudgmentScorerData):
    """
    ScorerData holds the information related to a single, completed Scorer evaluation run.

    For example, if running the Judgment Faithfulness scorer on an example, the ScorerData
    object will contain whether the example passed its threshold expectation, as well as more detailed
    information surrounding the evaluation run such as the claims and verdicts generated by the
    judge model(s).
    """

    def to_dict(self) -> dict:
        """Convert the ScorerData instance to a JSON-serializable dictionary."""
        return {
            "name": self.name,
            "threshold": self.threshold,
            "success": self.success,
            "score": self.score,
            "reason": self.reason,
            "strict_mode": self.strict_mode,
            "evaluation_model": self.evaluation_model,
            "error": self.error,
            "additional_metadata": self.additional_metadata,
        }


def create_scorer_data(scorer: BaseScorer) -> List[ScorerData]:
    """
    After a `scorer` is run, it contains information about the example that was evaluated
    using the scorer. For example, after computing Faithfulness, the `scorer` object will contain
    whether the example passed its threshold, the score, the reason for score, etc.

    This function takes an executed `scorer` object and produces a ScorerData object that
    contains the output of the scorer run that can be exported to be logged as a part of
    the ScorerResult.
    """
    scorers_result = list()

    scorers_result.append(
        ScorerData(
            name=scorer.name,
            threshold=scorer.threshold,
            score=scorer.score,
            reason=scorer.reason,
            success=scorer.success,
            strict_mode=scorer.strict_mode,
            evaluation_model=scorer.model,
            error=scorer.error,
            additional_metadata=scorer.additional_metadata,
        )
    )
    if hasattr(scorer, "internal_scorer") and scorer.internal_scorer is not None:
        scorers_result.append(
            ScorerData(
                name=scorer.internal_scorer.name,
                score=scorer.internal_scorer.score,
                threshold=scorer.internal_scorer.threshold,
                reason=scorer.internal_scorer.reason,
                success=scorer.internal_scorer.success,
                strict_mode=scorer.internal_scorer.strict_mode,
                evaluation_model=scorer.internal_scorer.model,
                error=scorer.internal_scorer.error,
                additional_metadata=scorer.internal_scorer.additional_metadata,
            )
        )
    return scorers_result
