CI/CD
.yml
GitLab · CI/CD · Magento Cache · Deployment
Cache Flush vs. Cache Clean
was wann in Deployments wirklich gebraucht wird

Wer nach jedem Deployment reflexartig cache:flush ausführt, löscht mehr als nötig und erhöht die Last durch unnötige Cache-Regenerierung. Die präzise Cache-Invalidierung nach einem Release ist eine technische Entscheidung – keine Gewohnheitssache.

10 Min. Lesezeit cache:flush · cache:clean · Redis · Cache-Typen · Deployment Magento 2 · GitLab CI · Performance

1. Magento Cache-Typen und was sie speichern

Magento verwaltet einen Satz von benannten Cache-Typen, die jeweils unterschiedliche Kategorien von Daten zwischenspeichern. Der config-Cache enthält zusammengeführte Konfigurationsdaten aus allen XML-Dateien. Der layout-Cache speichert Layout-Update-Handles. Der block_html-Cache enthält gerenderte Block-HTML-Ausgaben. Der full_page-Cache (FPC) speichert vollständige Seiten-Responses. Daneben gibt es collections, db_ddl, compiled_config, reflection, eav, customer_notification, target_rule und weitere.

Das zentrale Missverständnis: Nicht alle Cache-Typen werden durch ein Code-Deployment ungültig. Ein neues Theme-Release ändert block_html und full_page, aber nicht notwendigerweise db_ddl oder eav. Eine Konfigurationsänderung invalidiert config und compiled_config, aber nicht full_page. Wer nach jedem Deployment blind cache:flush ausführt, löscht auch Caches, die intakt und performanceoptimierend weiter genutzt werden könnten – um den Preis hoher Last beim ersten Warmup nach dem Release.

Die Liste der Magento-Cache-Typen ist nicht statisch: Drittanbieter-Module können eigene Cache-Typen registrieren. bin/magento cache:status zeigt die vollständige Liste aller registrierten Cache-Typen mit ihrem aktuellen Status. Es lohnt sich, nach der Installation neuer Module diese Liste zu prüfen und zu verstehen, welche neuen Cache-Typen hinzugekommen sind und durch welche Deployments sie invalidiert werden müssen. Undokumentierte Drittanbieter-Caches sind häufig die Quelle von Inkonsistenz-Problemen nach Deployments.

2. cache:flush vs. cache:clean: der technische Unterschied

bin/magento cache:flush löscht den gesamten Cache-Storage – bei Redis bedeutet das ein FLUSHDB auf der konfigurierten Redis-Datenbank. Es werden alle Daten gelöscht, egal welchem Cache-Typ sie gehören. Das ist ein radikaler Schritt, der sicherstellt, dass absolut keine veralteten Daten mehr vorhanden sind. Es ist auch der Schritt mit der höchsten Performance-Konsequenz: Nach einem Flush muss Magento alle Cache-Typen von Grund auf neu aufbauen.

bin/magento cache:clean hingegen invalidiert nur die Magento-eigenen Cache-Einträge, aber lässt Drittanbieter-Daten im selben Storage intakt. Es respektiert Cache-Tags und kann auf bestimmte Cache-Typen beschränkt werden: bin/magento cache:clean config block_html invalidiert nur diese beiden Typen. Für die meisten Deployments ist cache:clean mit den tatsächlich betroffenen Cache-Typen die präzisere und performantere Wahl.

deploy:production:
  stage: deploy
  script:
    - ssh "${DEPLOY_USER}@${DEPLOY_HOST}" bash -s << 'DEPLOY'
        set -euo pipefail
        cd "${DEPLOY_PATH}/current"

        # Step 1: Flush config-related caches BEFORE symlink switch
        # These must be cleared because the new code may rely on new config
        php bin/magento cache:clean config compiled_config

        # Step 2: Static content deploy (generates new assets)
        php bin/magento setup:static-content:deploy de_DE -f -j 4

        # Step 3: After symlink switch — clean layout and HTML caches
        # New templates and blocks need fresh rendering
        php bin/magento cache:clean layout block_html full_page

        # Step 4: Only use cache:flush when storage backend must be reset
        # e.g., after changing Redis database or prefix — NOT routine deployment
        # php bin/magento cache:flush  # Use sparingly!
      DEPLOY

3. Wann cache:flush wirklich nötig ist

cache:flush ist in wenigen, klar definierten Situationen die richtige Wahl. Erstens: wenn der Cache-Storage selbst gewechselt wird – zum Beispiel eine neue Redis-Instanz oder eine geänderte Datenbankpräfix-Konfiguration. In diesem Fall enthält der neue Storage keine alten Daten, und flush ist ohnehin leer oder notwendig. Zweitens: wenn ein schwerwiegender Fehler im Cache-Backend vermutet wird, der zu inkonsistenten Daten geführt hat. Drittens: nach dem ersten Aufsetzen des Systems, wenn der Cache noch keine sinnvollen Daten enthält.

In einem normalen Magento-Release-Deployment ist cache:flush fast nie die richtige Wahl. Es ist die Lösung für Ausnahmesituationen, nicht für den Standardprozess. Teams, die es routinemäßig nach jedem Deployment ausführen, tun es meist aus Unsicherheit – "dann kann auf jeden Fall nichts mehr aus dem alten Cache kommen" – bezahlen aber mit einer deutlich erhöhten Last und verlängerten Response-Zeiten in den Minuten nach dem Deployment, bis der Cache wieder warm ist.

4. Wann cache:clean die bessere Wahl ist

Für die meisten Magento-Deployments ist cache:clean mit explizit angegebenen Cache-Typen die richtige Wahl. Bei einem reinen PHP-Code-Deployment ohne Konfigurationsänderungen müssen mindestens config, compiled_config, block_html und full_page geleert werden. Bei einem Frontend-Release, das nur Templates und CSS ändert, reichen layout, block_html und full_page. Bei einer Konfigurationsänderung in XML-Dateien sind config und compiled_config relevant.

Die Analyse, welche Cache-Typen durch ein spezifisches Release betroffen sind, lässt sich im Deployment-Prozess automatisieren: Das CI-System kann anhand der geänderten Dateien bestimmen, welche Cache-Typen invalidiert werden müssen. Wenn sich ausschließlich Dateien in app/design/ geändert haben, brauchen db_ddl, eav und collections nicht geleert zu werden. Diese präzise Invalidierung ist der Unterschied zwischen einem Deployment mit kurzer Cache-Aufwärmzeit und einem, das die Server für Minuten unter hohe Last setzt.

5. Die richtige Cache-Sequenz im Deployment

Die Reihenfolge der Cache-Befehle im Deployment ist so wichtig wie die Befehle selbst. Vor dem Symlink-Wechsel sollten config und compiled_config geleert werden, damit die neue Konfiguration beim ersten Request des neuen Releases sofort geladen wird. setup:static-content:deploy läuft danach und generiert neue statische Dateien. Der Symlink-Wechsel erfolgt erst, wenn das neue Release-Verzeichnis vollständig vorbereitet ist.

Nach dem Symlink-Wechsel werden layout, block_html und full_page geleert. Diese Caches können erst geleert werden, wenn der Webserver bereits auf das neue Release zeigt, weil sie beim nächsten Request mit dem neuen Template-Output neu befüllt werden. Wenn diese Sequenz vertauscht wird – erst full_page leeren, dann Symlink wechseln – lädt Magento kurzzeitig den alten Code und generiert neuen Full-Page-Cache damit, der dann vom neuen Release sofort wieder invalidiert werden müsste.

6. Cache-Befehle in GitLab CI korrekt platzieren

In einer GitLab-Pipeline sollten Cache-Operationen im Deploy-Job stehen, nicht in einem separaten post-deploy-Job. Der Grund: Wenn der Deploy-Job fehlschlägt und der Cache bereits geleert wurde, steht die Production ohne Cache-Daten da, obwohl kein neues Release aktiv ist. Die Cache-Bereinigung muss Teil der atomaren Deployment-Sequenz sein – zusammen mit dem Symlink-Wechsel, nicht als nachgelagerter Schritt.

Ein Verify-Job nach dem Deploy kann cache:status aufrufen, um zu prüfen, ob alle Cache-Typen aktiviert und erreichbar sind. Das ist keine Cache-Invalierung, sondern eine Zustandsprüfung – und ein wichtiges Signal, dass das Cache-Backend korrekt konfiguriert ist. Wenn cache:status meldet, dass ein Cache-Typ fehlt oder deaktiviert ist, deutet das auf ein Konfigurationsproblem hin, das vor dem nächsten Deployment behoben werden muss.

7. Redis-Cache: Besonderheiten beim Flush

Bei Redis als Cache-Backend hat cache:flush eine besonders weitreichende Wirkung, weil es ein FLUSHDB auf der konfigurierten Datenbank ausführt. Wenn mehrere Magento-Instanzen oder andere Anwendungen dieselbe Redis-Datenbank nutzen – was nicht empfohlen wird, aber vorkommt – löscht cache:flush auch deren Daten. Deshalb muss jede Magento-Instanz eine eigene Redis-Datenbank (oder eigene Redis-Instanz) nutzen, wenn cache:flush auch nur gelegentlich verwendet wird.

Ein weiterer Redis-Aspekt: Wenn Magento mit cache:clean oder cache:flush arbeitet, während der Redis-Server unter hoher Last steht, kann der Befehl blockieren. In Produktionsumgebungen empfiehlt sich daher ein kurzes Monitoring-Fenster nach dem Cache-Befehl: Wenn Redis-CPU oder -Memory unerwartet ansteigen, kann das auf einen zu früh ausgelösten Regenerierungseffekt hinweisen. Das passiert typischerweise, wenn viele Requests gleichzeitig denselben Cache-Eintrag generieren wollen – das klassische Cache-Stampede-Problem nach einem Flush.

verify:cache:
  stage: verify
  script:
    - ssh "${DEPLOY_USER}@${DEPLOY_HOST}" bash -s << 'VERIFY'
        set -euo pipefail
        cd "${DEPLOY_PATH}/current"

        # Verify all expected cache types are enabled
        php bin/magento cache:status

        # Confirm Redis is reachable and responding
        php -r "
          \$redis = new Redis();
          \$redis->connect('${REDIS_HOST}', ${REDIS_PORT});
          echo 'Redis PING: ' . \$redis->ping() . PHP_EOL;
          echo 'Redis DB keys: ' . \$redis->dbSize() . PHP_EOL;
        "
      VERIFY
  when: on_success
  dependencies:
    - deploy:production

7b. Opcache und Cache-Befehle im Zusammenspiel

Ein oft vergessener Cache-Layer neben dem Magento-eigenen Cache ist der PHP-Opcache. Der Opcache speichert kompilierte PHP-Bytecode-Versionen und beschleunigt die Ausführung erheblich. Nach einem Deployment, bei dem sich PHP-Dateien geändert haben, muss auch der Opcache geleert werden – sonst läuft Magento unter Umständen noch mit der alten PHP-Code-Version, auch wenn die Dateien auf dem Server bereits aktualisiert sind. Das passiert besonders häufig bei Symlink-basierten Deployments, wenn Nginx den neuen Symlink-Pfad erkennt, aber der PHP-Opcache noch die alten Dateien aus dem Inode-Cache hält.

Der korrekte Ablauf: Nach dem Symlink-Wechsel wird der Opcache über php -r 'opcache_reset();' auf der CLI geleert. Alternativ kann PHP-FPM mit einem reload-Signal (nicht restart) dazu gebracht werden, seine Worker nacheinander zu ersetzen und dabei den Opcache zu leeren. Bei Docker-basierten Setups empfiehlt sich ein expliziter php-fpm reload nach dem Symlink-Wechsel. Das Zusammenspiel von Magento-Cache-Befehlen und PHP-Opcache-Reset ist ein häufig übersehener Grund für unerklärliche Verhaltensänderungen direkt nach Deployments.

Ein diagnostisches Hilfsmittel für Opcache-Probleme: php -r 'var_dump(opcache_get_status(true));' zeigt den aktuellen Zustand des Opcache und ob der Invalidierungsschritt tatsächlich wirksam war. Wenn nach einem Opcache-Reset noch Einträge mit alten Zeitstempeln vorhanden sind, deutet das auf ein Konfigurationsproblem mit opcache.validate_timestamps hin. In Produktionsumgebungen wird validate_timestamps oft deaktiviert (auf 0 gesetzt), um Opcache-Overheads zu vermeiden – dann muss der Reset explizit ausgeführt werden, da der Opcache Dateiänderungen sonst nicht bemerkt.

Fazit für den Deployment-Ablauf: Magento-Cache-Befehle (cache:clean) und PHP-Opcache-Reset sind zwei unabhängige Schichten, die beide zur vollständigen Cache-Invalidierung nach einem Deployment benötigt werden. Wer nur eine der beiden Schichten bedenkt, wird nach bestimmten Deployments unerklärliche, inkonsistente Verhaltensänderungen beobachten, die schwer zu reproduzieren und zu debuggen sind.

8. Cache-Strategie beim Rollback

Ein Rollback kehrt den Code zum vorherigen Release zurück, aber der Cache enthält möglicherweise bereits Daten aus dem neuen Release. Das kann zu Inkonsistenzen führen, wenn das neue Release neue Cache-Strukturen oder -Formate eingeführt hat. Die sichere Rollback-Cache-Strategie lautet daher: Nach dem Symlink-Wechsel zum alten Release immer cache:clean config compiled_config block_html full_page layout ausführen, um sicherzustellen, dass der Cache mit dem zurückgerollten Code konsistent ist.

Im Gegensatz zum Deployment-Fall empfiehlt sich beim Rollback ein etwas aggressiverer Cache-Clean, weil der Rollback selbst schon eine Ausnahmesituation ist. Der Performance-Verlust durch das Warmup ist in diesem Fall akzeptabel – es ist wichtiger, dass das zurückgerollte Release korrekt funktioniert, als dass der Cache optimal gefüllt ist. Ein cache:flush beim Rollback ist in vielen Fällen die sicherere Wahl, auch wenn es die Server kurz unter Last setzt.

9. Vergleich: reflexartig vs. gezielt invalidieren

Situation Empfohlener Befehl Begründung Performance-Effekt
Code-Deployment cache:clean config block_html full_page Nur betroffene Typen leeren Minimale Warmup-Last
Rollback cache:flush Ausnahmesituation, Konsistenz wichtiger Erhöhte Last, akzeptabel
Redis-Backend-Wechsel cache:flush Neuer Storage, alte Daten obsolet Einmalig, geplant
Nur Frontend-Änderung cache:clean layout block_html full_page Kein Konfigurationseinfluss Sehr geringe Warmup-Last
Routine nach Deploy cache:flush (falsch!) Löscht unnötig alle Cache-Typen Hohe Last, verlängerte TTFB

Die Tabelle macht deutlich: cache:flush ist kein Standard-Deployment-Befehl, sondern ein Notfallinstrument. Wer gezielt invalidiert, reduziert die Server-Last nach dem Release und verkürzt die Zeit, bis der Shop wieder volle Performance liefert. Das ist besonders bei Deployments in Stoßzeiten relevant.

10. Zusammenfassung

Der Unterschied zwischen cache:flush und cache:clean ist keine akademische Feinheit – er hat direkte Auswirkungen auf die Performance des Shops in den Minuten nach einem Deployment. cache:flush löscht alles und erzeugt maximale Regenerierungslast. cache:clean mit expliziten Cache-Typen ist präziser, schont nicht betroffene Caches und reduziert die Warmup-Last. Für Rollbacks ist cache:flush wegen der Ausnahmesituation akzeptabel; für reguläre Deployments ist gezieltes cache:clean die richtige Wahl.

Die Reihenfolge der Cache-Befehle ist dabei genauso wichtig wie die Wahl des Befehls: config und compiled_config vor dem Symlink-Wechsel, block_html, layout und full_page nach dem Symlink-Wechsel. Diese Sequenz stellt sicher, dass der Cache in jedem Schritt des Deployments konsistent mit dem aktiven Code ist.

Wer diese Regeln in der GitLab-Pipeline einmal explizit als kommentierte Deployment-Sequenz dokumentiert, verhindert, dass zukünftige Team-Mitglieder oder KI-gestützte Code-Änderungen reflexartig cache:flush einbauen. Die beste Pipeline-Dokumentation ist die, die direkt im YAML-Code als Kommentar erklärt, warum welcher Befehl in welcher Reihenfolge verwendet wird – und warum cache:flush explizit vermieden wird.

Eine abschließende Faustregel: Wenn die Entscheidung zwischen cache:flush und cache:clean unklar ist, ist cache:clean mit einer breiten Liste von Cache-Typen fast immer die sichere Wahl. Im schlimmsten Fall wird ein Cache-Eintrag nicht geleert und muss manuell nachgelöscht werden. Das ist viel weniger problematisch als ein überflüssiger Flush, der den Shop für mehrere Minuten unter Hochlast setzt. Performance-Probleme nach Deployments, die durch Cache-Stampede entstehen, sind oft schwerer zu diagnostizieren als ein einzelner veralteter Cache-Eintrag.

Cache Flush vs. Cache Clean — Das Wichtigste auf einen Blick

cache:clean für Deployments

cache:clean config compiled_config block_html full_page – gezielt die betroffenen Typen leeren, nicht alles.

cache:flush für Ausnahmefälle

Nur bei Rollback, Backend-Wechsel oder Inkonsistenz-Verdacht. Nicht als Standard-Deployment-Schritt.

Reihenfolge entscheidend

config/compiled_config VOR dem Symlink-Wechsel. block_html/layout/full_page NACH dem Symlink-Wechsel.

Redis-Stampede vermeiden

Cache-Warmup nach Flush erzeugt hohe Last. Cache-Clean mit gezielten Typen minimiert diesen Effekt.

11. FAQ: Cache Flush vs. Cache Clean für Magento

1Unterschied cache:flush vs. cache:clean?
Flush löscht den gesamten Storage (FLUSHDB bei Redis). Clean invalidiert nur Magento-eigene Einträge, kann auf Typen beschränkt werden.
2Welche Cache-Typen nach Code-Deployment?
Mindestens: config, compiled_config, block_html, full_page, layout. Bei reinen Frontend-Änderungen können config und compiled_config entfallen.
3Wann cache:flush statt cache:clean?
Rollback, Backend-Wechsel, Cache-Korruption, erster Systemaufbau. Nicht für reguläre Deployments.
4Was ist ein Cache-Stampede?
Viele Requests regenerieren gleichzeitig denselben leeren Cache. Nach cache:flush entsteht das für alle Typen. cache:clean minimiert den Effekt.
5Warum nicht nach jedem Deployment cache:flush?
Löscht nicht betroffene Caches und erhöht unnötig die Regenerierungslast. cache:clean mit betroffenen Typen hat dieselbe Wirkung bei weniger Nebenwirkungen.
6Löscht cache:clean Drittanbieter-Daten in Redis?
Nein. cache:clean respektiert Cache-Tags und löscht nur Magento-eigene Einträge. cache:flush führt FLUSHDB aus und löscht alles.
7Reihenfolge der Cache-Befehle im Deployment?
config/compiled_config VOR Symlink-Wechsel. block_html/layout/full_page NACH Symlink-Wechsel.
8Was macht cache:status?
Zeigt aktivierte Cache-Typen und Erreichbarkeit. Invalidiert nichts. Nützlich im Verify-Job nach dem Deployment.
9Wie lange dauert Cache-Warmup nach Flush?
Abhängig von Traffic und Seitenanzahl – Minuten bei full_page. Cache-Warmup-Skripte (automatisiertes URL-Aufrufen) verkürzen diese Zeit.
10Cache vor oder nach setup:upgrade leeren?
setup:upgrade führt selbst ein Cache-Flush aus. Nach setup:upgrade ist cache:flush ausnahmsweise angebracht, weil DB-Schema und DI-Container sich geändert haben können.

Die wichtigste Praxis-Regel: lieber einmal mehr flushen als einen inkonsistenten Cache-Zustand in Production zu haben — aber lieber gezielte Tags cleanen als unnötig alle Caches zu invalidieren und Warmup-Zeit zu verschwenden.

Ein klar dokumentiertes Cache-Konzept im Deployment-Playbook erspart stundenlange Fehlersuche nach dem Release und schützt vor klassischen Pitfalls wie veralteten Layout-Caches oder nicht aktualisierten Konfigurationswerten.