ScrapeGraphAI/Scrapegraph-ai · error · InvalidStateError

comparison_result missing 'differences' key

Error message

comparison_result missing 'differences' key

What it means

semantic_focused_analysis requires the comparison_result dict to contain a 'differences' key; this InvalidStateError is thrown upfront when it is absent. comparison_result is expected to come from a prior semantic comparison step (LLM answer compare).

Source

Thrown at scrapegraphai/utils/code_error_analysis.py:312

        >>> state = {
            'generated_code': 'def add(a, b): return a + b'
        }
        >>> comparison_result = {
            'differences': ['Missing docstring', 'No type hints'],
            'explanation': 'The code is missing documentation'
        }
        >>> analysis = semantic_focused_analysis(state, comparison_result, mock_llm)
    """
    try:
        # Validate state using Pydantic model
        validated_state = CodeAnalysisState(
            generated_code=state.get("generated_code", ""),
            errors=state.get("errors", {}),
        )

        # Validate comparison_result
        if "differences" not in comparison_result:
            raise InvalidStateError("comparison_result missing 'differences' key")
        if "explanation" not in comparison_result:
            raise InvalidStateError("comparison_result missing 'explanation' key")

        # Create prompt template and chain
        prompt = PromptTemplate(
            template=get_optimal_analysis_template("semantic"),
            input_variables=["generated_code", "differences", "explanation"],
        )
        chain = prompt | llm_model | StrOutputParser()

        # Execute chain with validated inputs
        return chain.invoke(
            {
                "generated_code": validated_state.generated_code,
                "differences": json.dumps(comparison_result["differences"], indent=2),
                "explanation": comparison_result["explanation"],
            }
        )

View on GitHub (pinned to 532dfffbf6)

Solutions

  1. Ensure comparison_result is a dict with both 'differences' and 'explanation' keys before calling
  2. If it comes from an LLM comparison step, parse/normalize its output (e.g. json.loads + key check) first
  3. Upgrade both producer and consumer together so the key contract stays in sync

Example fix

# before
semantic_focused_analysis(state, llm_comparison_output, llm)
# after
comparison = {"differences": llm_comparison_output.get("differences", []), "explanation": llm_comparison_output.get("explanation", "")}
semantic_focused_analysis(state, comparison, llm)
Defensive patterns

Strategy: type-guard

Validate before calling

if not isinstance(comparison_result, dict) or "differences" not in comparison_result:
    comparison_result = {"differences": [], "explanation": str(comparison_result)}

Type guard

def is_valid_comparison(cr) -> bool:
    return isinstance(cr, dict) and "differences" in cr and "explanation" in cr

Try / catch

from scrapegraphai.utils.code_error_analysis import InvalidStateError
try:
    semantic_focused_analysis(state, comparison_result, llm_model)
except InvalidStateError as e:
    if "differences" in str(e):
        comparison_result.setdefault("differences", [])
    raise

Prevention

When it happens

Trigger: Calling semantic_comparison_loop / semantic_focused_analysis(state, comparison_result, llm_model) where comparison_result was built by hand or by a comparison step that did not include 'differences' (e.g. LLM output parsing dropped it).

Common situations: Passing the raw output of an LLM comparison without parsing it into {differences, explanation}; a comparison node returning a different key layout after a version change; empty dict passed while testing.

Related errors


AI-assisted analysis of ScrapeGraphAI/Scrapegraph-ai@532dfffbf6 (2026-08-28). Data as JSON: /api/errors/643b5e9180755d1a. Report an issue: GitHub.