Wenn "läuft bei mir" keine Option mehr ist
Ein Bug, der sich lokal partout nicht reproduzieren lässt, aber in Produktion regelmäßig auftritt, ist eines der frustrierendsten Probleme im Magento-Alltag. Mit systematischer Eingrenzung, sicherem Remote-Debugging und strukturiertem Logging wird auch der hartnäckigste Produktions-Only-Bug greifbar.
Inhaltsverzeichnis
- 1. Warum manche Bugs nur in Produktion auftreten
- 2. Umgebungsunterschiede systematisch eingrenzen
- 3. Remote-Debugging mit Xdebug ohne Produktionsausfall
- 4. Strukturiertes Logging und Korrelations-IDs
- 5. Feature Flags zur gezielten Reproduktion
- 6. Anonymisierte Produktionsdaten fürs Staging
- 7. Profiling mit Blackfire in Produktion
- 8. Canary Deployments zur Bug-Isolierung
- 9. Debugging-Techniken im Vergleich
- 10. Zusammenfassung
- 11. FAQ
1. Warum manche Bugs nur in Produktion auftreten
Produktions-Only-Bugs entstehen fast immer durch eine Kombination von Faktoren, die lokal schlicht nicht vorhanden sind: reale Lastmuster, produktionsgroße Datenmengen, Race Conditions bei paralleler Nutzung, oder Konfigurationswerte, die sich zwischen Umgebungen unterscheiden. Ein Bug, der nur bei tausend gleichzeitigen Sessions auftritt, lässt sich auf einer lokalen Single-User-Instanz naturgemäß nicht auslösen, egal wie oft der Code gelesen wird.
Der erste Schritt im Umgang mit Produktions-Only-Bugs ist die Akzeptanz, dass klassisches lokales Debugging mit Breakpoints hier an seine Grenzen stößt. Stattdessen braucht es eine Kombination aus Observability-Werkzeugen, die im laufenden Betrieb Daten sammeln, ohne den Betrieb zu stören, und einer systematischen Methode, um Umgebungsunterschiede einzugrenzen, statt wild zu raten.
Dieser Artikel zeigt einen strukturierten Ansatz für Produktions-Only-Bugs in Magento 2, von der systematischen Eingrenzung über sicheres Remote-Debugging bis zu Techniken wie Canary Deployments, die einen Bug gezielt auf einen kleinen Nutzerkreis isolieren, bevor er das gesamte System betrifft.
2. Umgebungsunterschiede systematisch eingrenzen
Bevor überhaupt ein Debugger angesetzt wird, lohnt sich eine systematische Gegenüberstellung von Produktion und lokaler Umgebung: PHP-Version, installierte Extensions, php.ini-Werte wie memory_limit und max_execution_time, Redis- und Datenbank-Version, sowie aktivierte Module und deren Versionen. Produktions-Only-Bugs entstehen überraschend oft durch eine einzelne abweichende PHP-Extension oder eine andere OPcache-Konfiguration, die lokal nie auffällt.
Ein einfaches, aber wirkungsvolles Werkzeug: bin/magento sys:info beziehungsweise ein eigenes Diagnose-Skript, das die relevanten Umgebungsdaten in strukturierter Form ausgibt, sowohl lokal als auch per SSH in Produktion, und die beiden Ausgaben automatisiert diffen. Wer diesen Diff bei jedem Produktions-Only-Bug zuerst prüft, findet überraschend häufig schon hier den entscheidenden Hinweis, bevor überhaupt Code-Level-Debugging beginnt.
#!/usr/bin/env bash
# env-diff.sh — compare local and production environment fingerprints
set -euo pipefail
collect_fingerprint() {
echo "PHP: $(php -v | head -n1)"
echo "Extensions: $(php -m | sort | tr '\n' ',')"
echo "memory_limit: $(php -i | grep '^memory_limit')"
echo "opcache.enable: $(php -i | grep '^opcache.enable ')"
bin/magento module:status | sort
}
echo "=== Local fingerprint ==="
collect_fingerprint > /tmp/local_fingerprint.txt
cat /tmp/local_fingerprint.txt
echo "=== Production fingerprint (via SSH) ==="
ssh deploy@production "cd /var/www/html && $(declare -f collect_fingerprint); collect_fingerprint" \
> /tmp/prod_fingerprint.txt
diff /tmp/local_fingerprint.txt /tmp/prod_fingerprint.txt || echo "[INFO] Differences found above"
3. Remote-Debugging mit Xdebug ohne Produktionsausfall
Xdebug dauerhaft in Produktion zu aktivieren, ist wegen des Performance-Overheads keine Option, aber ein gezielt getriggertes Remote-Debugging für eine einzelne Anfrage ist es durchaus. Über den XDEBUG_TRIGGER-Cookie oder -Query-Parameter lässt sich Xdebug so konfigurieren, dass es nur für Anfragen mit diesem speziellen Trigger aktiv wird, während alle anderen Requests unbeeinflusst und mit voller Performance laufen.
Für Produktions-Only-Bugs, die sich auf eine bestimmte Kombination aus Nutzer, Session und Request-Parametern zurückführen lassen, ist dieser gezielte Trigger-Ansatz der sicherste Weg, echten Step-Debugging-Zugriff zu bekommen, ohne die restliche Produktionsumgebung zu belasten. Wichtig: Der Trigger-Wert sollte niemals ein einfaches, erratbares Geheimnis sein, sondern ein zufällig generierter Wert, der nur temporär für die Dauer der Fehlersuche gesetzt und danach sofort wieder entfernt wird.
#!/usr/bin/env bash
# Trigger a single, targeted Xdebug session on production
# without enabling Xdebug globally (avoids performance overhead)
set -euo pipefail
XDEBUG_SECRET="$(openssl rand -hex 16)"
echo "[INFO] Set this cookie in your browser DevTools for the debugging session:"
echo "XDEBUG_TRIGGER=${XDEBUG_SECRET}"
echo "XDEBUG_SESSION_START=${XDEBUG_SECRET}"
echo "[INFO] Ensure xdebug.mode=debug and xdebug.discover_client_host=1"
echo "[INFO] Point xdebug.client_host to your local IDE listener"
echo "[INFO] Remove the cookie and rotate the secret once debugging is complete"
4. Strukturiertes Logging und Korrelations-IDs
Ohne Korrelations-ID lässt sich ein einzelner Request in Produktion praktisch nicht durch alle beteiligten Log-Dateien verfolgen, besonders wenn asynchrone Message-Queue-Consumer oder mehrere PHP-FPM-Worker gleichzeitig beteiligt sind. Eine eindeutige Request-ID, die beim Eingang jeder Anfrage generiert und in jeden Log-Eintrag, jede Exception und jede an Message Queues gesendete Nachricht eingebettet wird, macht Produktions-Only-Bugs über verteilte Systemgrenzen hinweg nachvollziehbar.
Magentos Monolog-Integration erlaubt genau diese Anreicherung über einen eigenen Logger-Processor, der die Korrelations-ID automatisch jedem Log-Eintrag hinzufügt, ohne dass jeder einzelne $this->logger->info()-Aufruf im Code manuell angepasst werden muss. Sobald ein Produktions-Only-Bug gemeldet wird, reicht ein Filter nach der Korrelations-ID aus dem Support-Ticket, um die vollständige Kette aller beteiligten Log-Zeilen zu rekonstruieren.
<?php
declare(strict_types=1);
namespace Vendor\Module\Logger;
use Monolog\Processor\ProcessorInterface;
use Monolog\LogRecord;
/**
* Adds a request-scoped correlation ID to every log record,
* so a single request can be traced across all log files and queues.
*/
class CorrelationIdProcessor implements ProcessorInterface
{
private string $correlationId;
/**
* Generates the correlation ID once per request lifecycle.
*/
public function __construct()
{
$this->correlationId = bin2hex(random_bytes(8));
}
/**
* Injects the correlation ID into the log record's extra context.
*
* @param LogRecord $record Log record being processed
* @return LogRecord
*/
public function __invoke(LogRecord $record): LogRecord
{
$record->extra['correlation_id'] = $this->correlationId;
return $record;
}
}
5. Feature Flags zur gezielten Reproduktion
Manche Produktions-Only-Bugs lassen sich am effizientesten eingrenzen, indem verdächtiger Code hinter einem Feature Flag gezielt für einzelne Kundengruppen, Store Views oder sogar einzelne Nutzer deaktiviert wird, während der Rest des Systems unverändert weiterläuft. Tritt der Bug bei deaktiviertem Flag nicht mehr auf, ist die Ursache eingegrenzt, ohne einen kompletten Rollback des Deployments zu benötigen.
Feature Flags eignen sich außerdem hervorragend, um einen vermuteten Fix schrittweise auszurollen und dabei live zu beobachten, ob der Produktions-Only-Bug tatsächlich verschwindet. Statt einen Fix sofort für alle Nutzer scharfzuschalten, aktiviert man ihn zunächst für ein kleines Prozent-Segment und vergleicht die Fehlerrate zwischen Flag-aktiv- und Flag-inaktiv-Gruppe, bevor der vollständige Rollout erfolgt.
# feature-flags.yaml — scoped flag for isolating a suspected bug source
flags:
new_checkout_totals_calculation:
enabled: false
rollout:
strategy: "percentage"
percentage: 5
sticky_by: "customer_id"
scopes:
- store_view: "store_de"
- customer_group: "wholesale"
description: >
Suspected source of incorrect tax totals reported only in production.
Enabled for 5 percent of German store customers to compare error rates.
6. Anonymisierte Produktionsdaten fürs Staging
Ein häufiger Grund, warum Produktions-Only-Bugs im Staging nicht reproduzierbar sind: Die Testdaten sind zu klein, zu sauber oder zu homogen im Vergleich zur echten Produktionsdatenbank. Ein Kunde mit einer außergewöhnlich langen Bestellhistorie, ein Produkt mit besonders vielen Varianten oder eine Adresse mit ungewöhnlichen Sonderzeichen können Edge Cases auslösen, die in synthetischen Testdaten schlicht nicht vorkommen.
Ein regelmäßig aktualisiertes, anonymisiertes Abbild der Produktionsdatenbank im Staging, kombiniert mit einer Read-Replica für lastintensive Analysen ohne Produktionsrisiko, schließt diese Lücke. Wichtig dabei bleibt die konsequente Anonymisierung personenbezogener Daten vor dem Import ins Staging, damit reale Datenmengen für Reproduktionszwecke zur Verfügung stehen, ohne DSGVO-Risiken einzugehen.
7. Profiling mit Blackfire in Produktion
Wenn ein Produktions-Only-Bug tatsächlich ein Performance-Problem ist, etwa eine Anfrage, die unter bestimmter Last zeitweise in einen Timeout läuft, liefert Blackfires produktionstaugliches Profiling detaillierte Call-Graphen, ohne den Request spürbar zu verlangsamen. Im Gegensatz zu Xdebug ist Blackfires Profiler für den Dauerbetrieb in Produktion konzipiert und lässt sich gezielt für einzelne Requests über einen HTTP-Header aktivieren.
Für Produktions-Only-Bugs, die nur unter realer Last auftreten, lässt sich Blackfire zusätzlich mit synthetischem Last-Testing kombinieren: Ein Lasttest, der die Produktionslast nachbildet, während gleichzeitig ein Blackfire-Profil der betroffenen Anfrage erstellt wird, zeigt oft genau die Stelle, an der die Ausführungszeit unter Last exponentiell statt linear ansteigt.
#!/usr/bin/env bash
# Trigger a single-request Blackfire profile in production
set -euo pipefail
curl -sS \
-H "X-Blackfire-Query: signature=abc123&flags=samples=10" \
-H "Cookie: PHPSESSID=${SESSION_ID}" \
"https://shop.example.com/checkout/cart/index" \
-o /dev/null
echo "[INFO] Profile submitted — review the call graph in the Blackfire dashboard"
8. Canary Deployments zur Bug-Isolierung
Ein Canary Deployment rollt eine neue Version nur an einen kleinen Prozentsatz des Produktionstraffics aus, während der Großteil der Nutzer weiterhin auf der stabilen Version bleibt. Für die Suche nach Produktions-Only-Bugs lässt sich dieses Muster umkehren: Ein verdächtiger Codepfad wird gezielt nur für den Canary-Traffic mit zusätzlichem, ausführlichem Debug-Logging instrumentiert, während der restliche Traffic unverändert und mit normalem Log-Level läuft.
Dieser Ansatz begrenzt sowohl das Risiko als auch das Log-Volumen: Statt ausführliches Debug-Logging für den gesamten Produktionstraffic zu aktivieren, was schnell zu einer Log-Flut und zusätzlicher I/O-Last führt, konzentriert sich das detaillierte Logging auf den kleinen Canary-Anteil, in dem der Produktions-Only-Bug vermutet wird. Sobald genug Daten gesammelt wurden, wird der Canary-Traffic-Anteil wieder auf null gesetzt.
9. Debugging-Techniken im Vergleich
Die folgende Tabelle ordnet die vorgestellten Techniken nach Einsatzszenario für Produktions-Only-Bugs ein.
| Technik | Einsatzszenario | Produktionsrisiko |
|---|---|---|
| Umgebungsdiff | Konfigurations- oder Versionsunterschiede vermutet | Keines |
| Getriggertes Xdebug | Bug an bestimmte Session/Request gebunden | Gering, nur getriggerte Requests |
| Korrelations-IDs | Verteilte Systeme, asynchrone Verarbeitung | Keines |
| Feature Flags | Verdächtiger Code identifizierbar | Gering, kontrolliert |
| Blackfire-Profiling | Performance-/Timeout-Probleme unter Last | Gering, produktionstauglich |
| Canary Deployment | Neue Codeänderung als Bug-Kandidat | Kontrolliert, begrenzter Traffic |
In der Praxis werden mehrere dieser Techniken kombiniert: Ein Umgebungsdiff zur ersten Eingrenzung, Korrelations-IDs zur Nachverfolgung des betroffenen Requests, und je nach Befund entweder getriggertes Xdebug für Logikfehler oder Blackfire für Performance-Probleme. Kein einzelnes Werkzeug löst Produktions-Only-Bugs allein, aber die richtige Kombination macht sie systematisch statt zufällig auffindbar.
Mironsoft
Magento-2-Entwicklung, Observability und Performance-Debugging
Bugs, die sich der Reproduktion widersetzen, endlich greifbar machen?
Wir bauen Observability-Infrastruktur für eure Magento-Shops auf, mit Korrelations-IDs, sicherem Remote-Debugging und Blackfire-Profiling, damit Produktions-Only-Bugs systematisch statt zufällig gefunden werden.
Observability-Audit
Logging, Korrelations-IDs und Monitoring-Lücken identifizieren
Sicheres Remote-Debugging
Getriggertes Xdebug und Blackfire-Profiling einrichten
Bugfix-Support
Akute Produktions-Only-Bugs gemeinsam eingrenzen und beheben
10. Zusammenfassung
Produktions-Only-Bugs entstehen durch Faktoren, die lokal fehlen: reale Last, produktionsgroße Daten, Race Conditions und Umgebungsunterschiede. Die systematische Lösung beginnt mit einem Diff zwischen lokaler und Produktionsumgebung, gefolgt von gezieltem, getriggertem Xdebug für einzelne Requests, Korrelations-IDs für verteilte Nachverfolgung und Feature Flags zur kontrollierten Isolierung verdächtigen Codes.
Für Performance-bedingte Produktions-Only-Bugs liefert Blackfire produktionstaugliches Profiling ohne spürbaren Overhead, während Canary Deployments neue Codeänderungen kontrolliert auf einen kleinen Traffic-Anteil begrenzen. Keine einzelne Technik löst jeden Fall, aber die Kombination aus Observability, gezieltem Debugging und kontrollierter Traffic-Isolierung macht auch die hartnäckigsten Bugs systematisch auffindbar statt dem Zufall überlassen.
Debugging von Produktions-Only-Bugs — Das Wichtigste auf einen Blick
Umgebungsdiff
PHP-Version, Extensions und Konfiguration zwischen lokal und Produktion zuerst vergleichen.
Getriggertes Xdebug
Nur für einzelne markierte Requests aktivieren, nie dauerhaft in Produktion.
Korrelations-IDs
Ein Request muss über alle Logs und Queues hinweg nachverfolgbar sein.
Kontrollierte Isolierung
Feature Flags und Canary Deployments begrenzen Risiko und Log-Volumen bei der Bug-Suche.