Skip to main content

Diagnose von CI-Testfehlern

Wird Copilot CLI verwendet, um CI-Protokolle abzurufen, Fehler mit lokalem Code zu korrelieren und Probleme zu beheben, ohne das Terminal zu verlassen.

Copilot CLI wird mit dem GitHub MCP-Server ausgeliefert. Dadurch erhalten Sie direkten Zugriff auf Ihre GitHub Actions Workflowausführungen, Auftragsprotokolle und Überprüfungsstatus. In Kombination mit dem Zugriff auf Ihre lokalen Dateien können CI-Fehlerdetails abgerufen, mit Ihrem Code korreliert und Korrekturen vom Terminal vorgeschlagen werden.

Beispielszenario 1: Tests laufen lokal erfolgreich durch, schlagen jedoch in CI fehl

Sie haben einen Test, der auf Ihrem lokalen Rechner erfolgreich läuft, aber in CI fehlschlägt. Sie können Copilot CLI bitten, diesen Testfehler direkt zu untersuchen.

In diesem Beispiel definiert der getestete Code einen einfachen Bestelldienst (order.py), und es gibt einen entsprechenden Test, der überprüft, ob heute eine Bestellung erstellt wurde (test_order_service.py).

Beispielaufforderung

Copilot prompt
My CI is failing on this branch. Can you pull the latest workflow run 
logs, figure out what is failing, and help me fix it? The relevant files 
are @order.py and @test_order_service.py

Beispielantwort

Hinweis

Die folgende Antwort ist ein Beispiel. Da die Copilot-Chat-Antworten nicht deterministisch sind, erhältst du möglicherweise eine andere Antwort als die hier beschriebene.

Copilot CLI verwendet den GitHub MCP-Server, um Ihre neuesten Workflow-Ausführungen im aktuellen Branch abzurufen, den fehlgeschlagenen Job zu identifizieren und dessen Protokolle abzurufen. Es erkennt den folgenden Fehler:

___ TestOrderService.test_order_created_today ___
>       assert order["created_date"] == date.today()
E       AssertionError: assert datetime.date(2024, 1, 15) == datetime.date(2024, 1, 16)

test_order_service.py:45: AssertionError

Nachdem Copilot CLI beide lokalen Dateien gelesen hat, stellt es fest, dass die Daten genau einen Tag auseinanderliegen, und identifiziert dies als Problem mit der Zeitzonengrenze. Der CI-Läufer verwendet UTC, während ihr lokaler Computer eine andere Zeitzone verwendet. Wenn der Test nahe Mitternacht ausgeführt wird, date.today() werden in jeder Umgebung unterschiedliche Datumsangaben zurückgegeben.

Copilot CLI schlägt vor, zu standardisieren, wie today berechnet wird, indem eine Clock-Abhängigkeit injiziert oder die Zeitzone festgelegt wird:

from datetime import timezone, datetime

def get_today():
    return datetime.now(timezone.utc).date()

Es wendet den Fix auf beide order.py und test_order_service.py an und aktualisiert alle Verweise, sodass sie die neue get_today()-Hilfsfunktion verwenden.

Nach dem Fix können Sie die Änderungen überprüfen und die Tests lokal ausführen:

  1. Führen Sie den Befehl aus /diff , um genau zu überprüfen, was Copilot CLI sich geändert hat.
  2. Führen Sie !pytest test_order_service.py aus, um zu bestätigen, dass die Tests lokal erfolgreich durchlaufen.
  3. Pushen Sie den Fix, und lassen Sie CI erneut ausführen.

Beispielszenario 2: Zeitweilige Testfehler mit Rennbedingungen

Ein Test besteht manchmal und schlägt manchmal auf demselben Computer fehl. Sie möchten Copilot CLI Protokolle erfolgreicher und fehlerhafter Ausführungen vergleichen, um die Ursache zu ermitteln.

In diesem Beispiel verwendet der zu testende Code einen Hintergrundauftrag in order_service.py, um den Status einer Bestellung asynchron zu aktualisieren, und eine Überprüfung in test_order_service.py bestätigt, dass der endgültige Status "processed" ist.

Beispielaufforderung für Rennbedingungen

Copilot prompt
This test passes sometimes and fails sometimes. Can you pull the logs 
from the last passing and failing CI runs for test_order_processed 
on this branch, compare them, and figure out what is going wrong? 
Relevant files: @order_service.py @test_order_service.py

Beispielantwort für Rennbedingungen

Hinweis

Die folgende Antwort ist ein Beispiel. Da die Copilot-Chat-Antworten nicht deterministisch sind, erhältst du möglicherweise eine andere Antwort als die hier beschriebene.

Copilot CLI verwendet den GitHub-MCP-Server, um die neuesten Workflow-Ausführungen auf dem aktuellen Branch aufzulisten, identifiziert eine erfolgreiche und eine fehlgeschlagene Ausführung und ruft die Protokolle für beide ab. Es vergleicht sie:

Erfolgreicher Durchlauf:

[DEBUG] Created order #1234
[DEBUG] Background job started for order #1234
[DEBUG] Background job completed (52ms)
[DEBUG] Checking order status
[DEBUG] Order #1234 status: processed

Fehler beim Ausführen:

[DEBUG] Created order #1234
[DEBUG] Background job started for order #1234
[DEBUG] Checking order status
[DEBUG] Order #1234 status: pending

Copilot CLI stellt fest, dass im erfolgreichen Durchlauf der Hintergrundauftrag vor der Statusüberprüfung beendet wurde, während im fehlgeschlagenen Durchlauf der Status überprüft wurde, als der Auftrag noch lief. Dies wird als Rennbedingung identifiziert, da der Test nicht auf den Abschluss des Hintergrundauftrags wartet.

Copilot CLI empfiehlt, vor der Prüfung einen expliziten Wartemechanismus hinzuzufügen, und schlägt eine Lösung mithilfe eines Polling-Helfers vor:

import time

def wait_for_status(order_id, expected, timeout=5):
    start = time.time()
    while time.time() - start < timeout:
        order = get_order(order_id)
        if order.status == expected:
            return order
        time.sleep(0.1)
    raise TimeoutError(
        f"Order {order_id} did not reach '{expected}' within {timeout}s"
    )

Weiterführende Lektüre

GitHub Copilot-CLI