Brief IA

RAGAS, DeepEval, and Promptfoo: Key Tools for Evaluating LLMs

💻 Code & Dev·Tom Levy·

RAGAS, DeepEval, and Promptfoo: Key Tools for Evaluating LLMs

RAGAS, DeepEval, and Promptfoo: Key Tools for Evaluating LLMs
Key Takeaways
1RAGAS, DeepEval, and Promptfoo are open-source frameworks for evaluating language models, each with distinct objectives.
2Evaluating LLMs requires distinguishing between benchmarking, application evaluation, and production monitoring.
3Position bias, personal preference bias, and verbosity are challenges to overcome when evaluating LLMs.
💡Why it mattersChoosing the right evaluation framework is crucial to ensure the performance and reliability of language models in production.
Le brief IA que lisent les pros

Le brief IA que les pros lisent chaque soir

Les 7 actus IA du jour, décryptées en 5 min. Gratuit.

Inclus dès l'inscription : notre sélection des meilleurs guides & comparatifs IA.

Choisis ton rythme

Gratuit · Pas de spam · Désabonnement en 1 clic

📄
Full Analysis

Introduction to LLM Evaluation Frameworks

Evaluating large language models (LLMs) is a complex task that requires suitable tools to effectively measure their performance. Among the main open-source frameworks available, RAGAS, DeepEval, and Promptfoo stand out with their unique approaches. These tools rely on the LLM-as-a-judge mechanism, which presents measurable biases that are crucial to consider when designing LLM-based systems.

Objectives of the Evaluation Frameworks

The RAGAS, DeepEval, and Promptfoo frameworks primarily differ in their objectives and the situations in which they are most useful. It is essential to understand when to use each of them, as well as the combinations recommended by experienced teams.

  • RAGAS: This framework is research-based, with an academic-quality methodology behind metrics such as fidelity, accuracy, and context recall. It focuses on evaluating the fidelity and accuracy of responses generated by LLMs based on retrieved data. It is particularly suited for information retrieval-focused architectures. However, it is limited to evaluating retrieval and generation, without production monitoring or integrated collaboration layers.

  • DeepEval: Integrated with Python and based on pytest, DeepEval offers over 14 metrics to evaluate hallucinations, bias, toxicity, and other RAG-specific aspects. It is explicitly designed to function as a CI/CD quality gate that can block a deployment if necessary, ensuring seamless integration into existing testing suites.

  • Promptfoo: This framework is command-line oriented and uses YAML configuration. It excels in comparing multi-model prompts and red-teaming, with a security testing suite that includes over 500 attack vectors.

Understanding LLM Evaluation

Before diving into the specifics of each framework, it is important to distinguish between the different categories of LLM evaluation. This distinction helps avoid common mistakes when selecting an evaluation framework.

  • Model Benchmarking: This category assesses the raw capabilities of models on standardized academic tasks such as MMLU, GSM8K, and HumanEval. The lm-evaluation-harness tool is often used for these academic benchmarks.

  • Application Evaluation: This focuses on the performance of specific applications, such as RAG pipelines, chatbots, or agents, by checking whether the outputs are correct, grounded, and safe.

  • Production Monitoring: This category tracks live traffic after deployment to detect regressions and drifts not anticipated by offline testing. Tools like LangSmith, Braintrust, and Arize Phoenix are used in this context.

Biases in LLM Evaluation

When evaluating LLMs, it is crucial to consider positional, personal preference, and verbosity biases. These biases can significantly influence the results. Positional biases refer to a model's tendency to favor certain positions in a text sequence. Personal preference biases concern subjective inclinations that can affect judgments. Finally, verbosity biases manifest when longer responses are favored, regardless of their relevance or accuracy.

To detect these biases, rigorous auditing is necessary. This involves systematically testing the model's responses in various scenarios to identify undesirable trends. Once detected, these biases can be mitigated by adjusting model parameters or modifying training data to balance preferences.

Essential Metrics of the Frameworks

To understand the differences between RAGAS, DeepEval, and Promptfoo, it is crucial to know the metrics they use. Each tool implements a version of a few key metrics. The true differentiating factor between these frameworks is not the novelty of the metrics, as they primarily implement the same ideas. Rather, it is the suitability of the workflow: how the metric is triggered, where the result goes, and whether it blocks a deployment or simply generates a report.

  • Fidelity: This metric checks whether a response contains only claims supported by the retrieved context, which is essential for detecting RAG hallucinations.

  • Accuracy and Context Recall: These metrics verify whether the retrieval has extracted the correct documents before generating responses.

  • Response Relevance: This assesses whether the response actually addresses the question posed, regardless of its factual grounding.

  • G-Eval: Introduced by Liu et al., this mechanism uses chain-of-thought prompting to guide an LLM judge through an explicit process, aligning evaluations more closely with human preferences.

Direct Comparison: RAGAS, DeepEval, and Promptfoo

Each of these frameworks has its strengths and weaknesses, and their choice depends on the specific needs of the evaluation. Notably, DeepEval and RAGAS are not really competitors. DeepEval covers broad LLM application testing, while RAGAS specializes specifically in RAG. A significant portion of production teams uses both together — with RAGAS noting retrieval-specific dimensions and DeepEval managing everything else in the same CI pipeline.

  • RAGAS: Ideal for retrieval-focused architectures, with metrics supported by academic research.

  • DeepEval: Designed to integrate into CI/CD testing suites, with broad metric coverage.

  • Promptfoo: Perfect for multi-model prompt engineering and security testing.

Code Review: Detecting Hallucinations

A simple code example demonstrates the fidelity checking mechanism used by RAGAS. This code breaks down a response into atomic claims and checks each claim against the retrieved context. A claim without support in the context is considered a hallucination.

# Example code to check fidelity
import re

def decompose_claims(answer: str) -> list[str]:
    """Divides an answer into atomic statements."""
    sentences = re.split(r'(?<=[.!?])\s+', answer.strip())
    return [s.strip() for s in sentences if s.strip()]

def claim_supported_by_context(claim: str, context: str) -> bool:
    """
    Checks if a claim is supported by the retrieved context.
    """
    claim_words = set(re.findall(r'\b[a-zA-Z]{4,}\b', claim.lower()))
    context_words = set(re.findall(r'\b[a-zA-Z]{4,}\b', context.lower()))
    if not claim_words:
        return True
    overlap = len(claim_words & context_words) / len(claim_words)
    return overlap >= 0.5

def compute_faithfulness(answer: str, context: str) -> dict:
    """
    Calculates the fidelity score.
    """
    claims = decompose_claims(answer)
    supported = [c for c in claims if claim_supported_by_context(c, context)]
    unsupported = [c for c in claims if c not in supported]
    score = len(supported) / len(claims) if claims else 1.0
    return {
        "score": round(score, 3),
        "total_claims": len(claims),
        "unsupported_claims": unsupported,
    }

if __name__ == "__main__":
    context = "Abuja became the capital of Nigeria in 1991, replacing Lagos."
    grounded_answer = "The capital of Nigeria is Abuja. It became the capital in 1991."
    result_1 = compute_faithfulness(grounded_answer, context)
    print("Grounded answer:")
    print(f"  Fidelity score: {result_1['score']}")
    print(f"  Unsupported claims: {result_1['unsupported_claims']}\n")
    
    hallucinated_answer = (
        "The capital of Nigeria is Abuja. It became the capital in 1991. "
        "The city has a population of over 3 million inhabitants."
    )
    result_2 = compute_faithfulness(hallucinated_answer, context)
    print("Answer with a hallucinated detail:")
    print(f"  Fidelity score: {result_2['score']}")
    print(f"  Unsupported claims: {result_2['unsupported_claims']}")

This code illustrates how an unsupported claim in the context can be identified as a hallucination, highlighting the importance of fidelity checking in LLM evaluation.

Brief IA — L'actualité IA en français

L'essentiel de l'actualité de l'intelligence artificielle, décrypté et expliqué chaque jour.