Debugging von Agent-Runs

Debugging von Runs hilft zu verstehen, warum ein Agent eine bestimmte Entscheidung getroffen hat.
Auf dieser Seite
  1. Idee in 30 Sekunden
  2. Das Hauptproblem
  3. So funktioniert es
  4. Typische Production-Signale fĂŒr debugging runs
  5. Wie man den Debugging-Layer liest
  6. Wann verwenden
  7. Implementierungsbeispiel
  8. Investigation
  9. Typische Fehler
  10. Analyse beginnt bei irgendeinem Log-Fehler
  11. Keine Korrelation von trace + logs + metrics
  12. repeated calls und stop_reason werden ignoriert
  13. Kein Vergleich mit vorherigem Release
  14. Incident wird ohne replay und Verifikation geschlossen
  15. Selbst-Check
  16. FAQ
  17. Verwandte Seiten

Idee in 30 Sekunden

Debugging von Agent-Runs hilft, vom Symptom zur Ursache zu kommen: was genau kaputt ist, in welchem Schritt, und warum.

DafĂŒr mĂŒssen Tracing, Logs und Metriken eines problematischen Runs zusammengefĂŒhrt werden.

Ohne das sieht das Team oft nur den finalen Fehler, aber nicht den gesamten Weg dorthin.

Das Hauptproblem

In Agent-Systemen hat ein Incident selten nur eine offensichtliche Ursache.

Der finale Fehler kann nur eine Folge sein: Das eigentliche Problem kann frĂŒher begonnen haben, zum Beispiel durch einen langsamen tool call, ein fehlerhaftes retry oder eine Regression nach dem Release. Ohne systematisches debugging ist das schwer schnell zu lokalisieren.

Als NĂ€chstes schauen wir, wie man diese Signale liest und stabil root cause findet.

In Production sieht das oft so aus:

  • in Logs gibt es viele Events, aber keine klare Reihenfolge;
  • die Ursache vermischt sich mit Begleitfehlern;
  • der Incident wurde "gefixt", kommt aber nach dem Release zurĂŒck;
  • MTTR steigt, weil das Team den Incident-Kontext jedes Mal neu aufbauen muss.

Genau deshalb sollte debugging eines Runs ein eigener operativer Prozess sein und keine manuelle Suche nach dem "ersten error".

So funktioniert es

Ein praktischer debugging run besteht meist aus drei Ebenen:

  • Run-Kontext (run_id, trace_id, release, workflow);
  • Evidence -> Analyse (spans, logs, metrics, stop_reason);
  • Entscheidung (Hypothese -> Fix -> Verifikation via replay und Tests).

Diese Ebenen beantworten: wo das Problem liegt, warum es entstanden ist und ob der Fix es wirklich entfernt. Tracing zeigt den Pfad, Logs zeigen Ereignisse, und Metriken zeigen Ausmaß und Trend.

Viele Logs != schnelles debugging. Geschwindigkeit entsteht nicht aus Datenmenge, sondern aus Korrelation rund um einen Run.

Typische Production-Signale fĂŒr debugging runs

SignalWo prĂŒfenWarum es wichtig ist
first_error_spanTracingPunkt finden, an dem der Fehler zuerst erschien
slowest_spanTracing + MetrikenBottleneck-Kandidat (muss verifiziert werden)
stop_reasonLog run_finishedverstehen, wie der Run beendet wurde
error_classtool_result / llm_result LogsTimeout von Logikfehler trennen
repeated_tool_callstool_call Logs + tool metricswiederholte Aufrufe erkennen (loops, retries, tool spam)
run_latency_p95MetrikenprĂŒfen, ob Incident bereits systemisch ist
release_diffRelease-VergleichsdashboardRegression nach Änderungen erkennen
synthetic_run_statushealth checksAuswirkung auf kritischen workflow prĂŒfen

Damit debugging stabil bleibt, werden diese Signale typischerweise nach release, workflow, model und tool segmentiert.

Wichtig: keine high-cardinality Labels (run_id, request_id, user_id) in Metriken aufnehmen. DafĂŒr sind Logs und Tracing besser geeignet.

Wie man den Debugging-Layer liest

Welcher Run ist fehlgeschlagen -> in welchem Schritt -> warum genau. Diese drei Ebenen sollte man immer gemeinsam betrachten.

Wichtig ist, auf Trends und Release-Deltas zu schauen, nicht nur auf ein einzelnes Notfall-Event.

Typische Signalkombinationen:

  • first_error_span=tool_call + tool_error_rate ↑ -> Problem in einem konkreten tool-layer;
  • run_latency_p95 ↑ + tool_latency_p95 stabil -> wahrscheinlich Problem in LLM oder runtime-Logik;
  • repeated_tool_calls ↑ + stop_reason=max_steps -> Agent steckt in einer Schleife;
  • error_rate ↑ nach Release + positives release_diff -> Änderungsregression, kein einmaliger Incident;
  • synthetic_run_status=fail + health_score ↓ -> Problem beeinflusst bereits kritischen workflow.

Wann verwenden

Ein formaler debugging-flow ist nicht immer nötig.

FĂŒr ein einfaches single-shot Szenario ohne tools reichen manchmal Basis-Logging und manuelle FehlerprĂŒfung.

Ein systematischer debugging-Ansatz wird aber kritisch, wenn:

  • Runs mehrere reasoning-Schritte und tool calls enthalten;
  • Incidents Latenz, Kosten oder SLO beeinflussen;
  • Releases hĂ€ufig kommen und Regressionen frĂŒh erkannt werden mĂŒssen;
  • es einen on-call Prozess gibt und ein planbares MTTR nötig ist.

Implementierungsbeispiel

Unten ist eine vereinfachte Funktion, die Evidence fĂŒr einen Run sammelt und eine Basis-Hypothese bildet. Das ersetzt kein vollstĂ€ndiges incident tooling, zeigt aber einen praktischen debugging-Prozess.

PYTHON
from collections import Counter


def debug_run(run_id, trace_events, log_events, debug_metrics_snapshot):
    run_spans = sorted(
        [s for s in trace_events if s.get("run_id") == run_id],
        key=lambda s: s.get("started_at_ms", 0),
    )
    run_logs = [e for e in log_events if e.get("run_id") == run_id]

    first_error_span = next((s for s in run_spans if s.get("status") == "error"), None)
    # slowest_span kann None sein, wenn der Run keine spans enthÀlt
    slowest_span = max(run_spans, key=lambda s: s.get("latency_ms", 0), default=None)

    stop_reason = "unknown"
    for event in reversed(run_logs):
        if event.get("event") == "run_finished":
            stop_reason = event.get("stop_reason", "unknown")
            break

    seen_signatures = set()
    repeated_tools = Counter()
    for event in run_logs:
        if event.get("event") != "tool_call":
            continue
        signature = (event.get("tool"), event.get("args_hash"))
        if signature in seen_signatures:
            repeated_tools[event.get("tool")] += 1
        else:
            seen_signatures.add(signature)

    hypotheses = []
    if first_error_span and first_error_span.get("step_type") == "tool_call":
        hypotheses.append("Wahrscheinlicher Ausfall im tool-layer: Tool-VerfĂŒgbarkeit und timeout policy prĂŒfen.")

    if repeated_tools:
        hypotheses.append("Wiederholte tool calls erkannt: dedupe/cache und stop conditions prĂŒfen.")

    if slowest_span and debug_metrics_snapshot.get("run_latency_p95_ms", 0) > debug_metrics_snapshot.get("slo_latency_ms", 2500):
        hypotheses.append("p95 latency liegt ĂŒber SLO: Bottleneck ĂŒber slowest_span lokalisieren.")

    if debug_metrics_snapshot.get("release_error_rate_delta", 0) > 0:
        hypotheses.append("error_rate ist nach Release gestiegen: Änderungen in prompt/runtime/tool routing prĂŒfen.")

    return {
        "run_id": run_id,
        "first_error_span": first_error_span,
        "slowest_span": slowest_span,
        "stop_reason": stop_reason,
        "repeated_tools": dict(repeated_tools),
        "hypotheses": hypotheses,
    }

Debugging gilt erst als abgeschlossen, wenn das Problem reproduzierbar ist (replay) und bestÀtigt ist, dass der Fix es stabil entfernt. Wenn sich das Problem nicht reproduzieren lÀsst, wechselt debugging in den Modus von Hypothesen statt Beweisen.

Insight

Replay != optional.

Ohne replay ist es eine Annahme.
Mit replay ist es ein Beweis.

So kann ein kurzer debugging snapshot aussehen:

Runfirst_error_spanslowest_spanstop_reasonFazit
run_9fd2tool_call: search_docstool_call: search_docs (1.8s)tool_errortool degradiert + retries
run_a113llm_generatellm_generate (2.4s)step_errorModellfehler nach Release
run_d77c—reasoning (3.1s)max_stepsLoop ohne expliziten Fehler

Investigation

Wenn ein Incident-Signal auslöst:

  1. run_id, trace_id, release und betroffenen workflow festhalten;
  2. im Tracing first_error_span und slowest_span finden;
  3. in Logs stop_reason, error_class, repeated_tool_calls prĂŒfen;
  4. in Metriken Ausmaß bestĂ€tigen (Spike oder Trend) und Release-Deltas vergleichen.

Typische Fehler

Auch mit observability scheitert debugging oft an typischen Fehlern.

Analyse beginnt bei irgendeinem Log-Fehler

Ohne Bindung an eine konkrete run_id mischt das Team Symptome aus verschiedenen Incidents. So wird es schwer, lokales Problem von kaskadierendem Ausfall zu trennen.

Keine Korrelation von trace + logs + metrics

Wenn Tracing, Logs und Metriken getrennt betrachtet werden, widersprechen sich Hypothesen oft. Dadurch steigt MTTR selbst bei einfachen Tool-AusfÀllen.

repeated calls und stop_reason werden ignoriert

Ohne diese Signale ĂŒbersieht man leicht loops und retry storms. Das verdeckt oft die frĂŒhe Phase von Tool-Spam.

Kein Vergleich mit vorherigem Release

Ohne release_diff sieht das Team nicht, ob das Problem nach Änderungen aufgetreten ist. Dadurch bleibt Regression lĂ€nger in Production.

Incident wird ohne replay und Verifikation geschlossen

Ein Fix kann nur das Symptom entfernen, nicht die Ursache. Das erhöht das Risiko einer wiederholten teilweisen Störung.

Selbst-Check

Unten ist eine kurze Baseline-Checkliste fĂŒr debugging-flow vor dem Release.

Fortschritt: 0/9

⚠ Grundlegende Observability fehlt

Das System wird in production schwer zu debuggen sein. Starten Sie mit run_id, structured logs und tracing von tool calls.

FAQ

Q: Womit beginnt debugging eines problematischen Runs?
A: Starte mit run_id und trace_id: finde first_error_span, prĂŒfe stop_reason und bestĂ€tige dann das Ausmaß in den Metriken. first_error_span ist der schnellste Weg zum Fehlerpunkt.

Q: Was ist wichtiger fĂŒr debugging: Tracing oder Logs?
A: Beides zusammen: Tracing zeigt den Schrittpfad, Logs liefern Event-Details (error_class, args_hash, policy decision).

Q: Wie erkenne ich Release-Regression statt einmaligem Ausfall?
A: Vergleiche error_rate, latency_p95, repeated_tool_calls zwischen Releases. Wenn das Signal nach dem Release stabil schlechter ist, ist es Regression.

Q: Was ist das Minimum an Daten fĂŒr Debugging in 10-15 Minuten?
A: Minimum: run_id, trace_id, first_error_span, stop_reason, error_class, latency_p95 und Release-Kontext.

Verwandte Seiten

Weiter zum Thema:

⏱ 7 Min. Lesezeit ‱ Aktualisiert 23. MĂ€rz 2026Schwierigkeit: ★★★
Integriert: Production ControlOnceOnly
Guardrails fĂŒr Tool-Calling-Agents
Shippe dieses Pattern mit Governance:
  • Budgets (Steps / Spend Caps)
  • Tool-Permissions (Allowlist / Blocklist)
  • Kill switch & Incident Stop
  • Idempotenz & Dedupe
  • Audit logs & Nachvollziehbarkeit
Integrierter Hinweis: OnceOnly ist eine Control-Layer fĂŒr Production-Agent-Systeme.

Autor

Nick — Engineer, der Infrastruktur fĂŒr KI-Agenten in Produktion aufbaut.

Fokus: Agent-Patterns, Failure-Modes, Runtime-Steuerung und SystemzuverlÀssigkeit.

🔗 GitHub: https://github.com/mykolademyanov


Redaktioneller Hinweis

Diese Dokumentation ist KI-gestĂŒtzt, mit menschlicher redaktioneller Verantwortung fĂŒr Genauigkeit, Klarheit und Produktionsrelevanz.

Der Inhalt basiert auf realen AusfÀllen, Post-Mortems und operativen VorfÀllen in produktiv eingesetzten KI-Agenten-Systemen.