Ich arbeite derzeit an einer MySQL-Datenbank, in der eine große Anzahl von Ungültigkeitserklärungen aus dem Abfrage-Cache angezeigt wird, hauptsächlich wegen der hohen Anzahl von INSERT-, DELETE- und UPDATE-Anweisungen, die für viele der Tabellen ausgeführt werden.
Ich versuche festzustellen, ob es überhaupt einen Vorteil gibt, wenn der Abfragecache für SELECT-Anweisungen verwendet wird, die für diese Tabellen ausgeführt werden. Da sie so schnell ungültig werden, scheint es mir das Beste zu sein, SQL_NO_CACHE nur für SELECT-Anweisungen mit diesen Tabellen zu verwenden.
Lohnt sich der Aufwand für häufige Invalidierung jemals?
Bearbeiten: Auf Wunsch des Benutzers @RolandoMySQLDBA unten finden Sie hier die Informationen zu MyISAM und INNODB.
InnoDB
- Datengröße: 177,414 GB
- Indexgröße: 114,792 GB
- Tabellengröße: 292,205 GB
MyISAM
- Datengröße: 379,762 GB
- Indexgröße: 80,681 GB
- Tabellengröße: 460,443 GB
Zusätzliche Information:
- Version: 5.0.85
- query_cache_limit: 1048576
- query_cache_min_res_unit: 4096
- query_cache_size: 104857600
- query_cache_type: ON
- query_cache_wlock_invalidate: OFF
- innodb_buffer_pool_size: 8841592832
- 24 GB RAM
Antworten:
Sie sollten den Abfrage-Cache einfach mit deaktivieren
und starten Sie mysql neu. Warum sollte ich das vorschlagen ???
Der Abfrage-Cache wird immer mit InnoDB zusammenarbeiten. Es wäre schön, wenn das MVCC von InnoDB die Abfragen aus dem Abfrage-Cache bedienen würde, wenn Änderungen keine Auswirkungen auf wiederholbare Lesevorgänge für andere Transaktionen haben. InnoDB macht das leider nicht. Anscheinend haben Sie viele Anfragen, die ziemlich schnell ungültig werden und wahrscheinlich nicht wiederverwendet werden.
Für InnoDB unter MySQL 4.0 wurde der Abfrage-Cache für Transaktionen deaktiviert. Ab MySQL 4.1 spielt InnoDB Traffic Cop, wenn der Zugriff auf den Abfrage-Cache tabellenweise gewährt wird.
Aus der Perspektive Ihrer Frage würde ich sagen, dass die Rechtfertigung für das Entfernen des Abfragecaches nicht so sehr der Overhead ist, sondern wie InnoDB ihn verwaltet.
Weitere Informationen zur Interaktion von InnoDB mit dem Abfragecache finden Sie auf den Seiten 213-215 des Buches "High Performance MySQL (Second Edition)" .
Wenn alle oder ein Großteil Ihrer Daten MyISAM sind, können Sie mit Ihrer ursprünglichen Idee, SQL_NO_CACHE zu verwenden, fortfahren.
Wenn Sie eine Mischung aus InnoDB und MyISAM haben, müssen Sie das richtige Gleichgewicht für Ihre Anwendung finden, basierend auf der Höhe Ihrer Cache-Fehler. Tatsächlich verweisen die Seiten 209-210 desselben Buches auf Gründe für Cache-Fehler:
und die Hauptursachen für hohe Cache-Fehler mit wenigen nicht zwischenspeicherbaren Abfragen können sein:
UPDATE 06.09.2012 10:10 EDT
Wenn Sie Ihre letzten aktualisierten Informationen anzeigen, haben Sie
query_cache_limit
1048576 (1M) festgelegt. Dies begrenzt jede Ergebnismenge auf 1 Million. Wenn Sie etwas größeres abrufen, wird es einfach nicht zwischengespeichert. Während Siequery_cache_size
104857600 (100M) festgelegt haben, sind in einer perfekten Welt nur 100 zwischengespeicherte Ergebnisse zulässig. Wenn Sie Hunderte von Abfragen durchführen, kommt es relativ schnell zu einer Fragmentierung. Sie haben auch 4096 (4 KB) als Ergebnismenge für die Mindestgröße. Leider verfügt mysql über keinen internen Mechanismus zum Defragmentieren des Abfragecaches.Wenn Sie den Abfrage-Cache haben müssen und über so viel RAM verfügen, können Sie Folgendes ausführen:
um den Abfrage-Cache zu leeren. Sie verlieren alle zwischengespeicherten Ergebnisse. Führen Sie diese Zeilen daher außerhalb der Spitzenzeiten aus.
Ich würde auch folgendes vergeben:
Damit verbleiben 23G RAM. Ich würde folgendes ansprechen:
Das lässt 7G. Dies sollte für Betriebssystem- und DB-Verbindungen ausreichend sein.
Beachten Sie, dass der Schlüsselpuffer nur MyISAM-Indexseiten zwischenspeichert, während der InnoDB-Pufferpool Daten und Indizes zwischenspeichert.
Eine weitere Empfehlung: Aktualisieren Sie auf MySQL 5.5, damit Sie InnoDB für mehrere CPUs und mehrere Threads für Lese- / Schreib-E / A konfigurieren können.
Siehe meine früheren Beiträge zur Verwendung von MySQL 5.5 in Verbindung mit dem Zugriff auf mehrere CPUs für InnoDB
Nov 24, 2011
: Warum ist mysql 5.5 langsamer als 5.1 (Linux, mit mysqlslap)Oct 05, 2011
: Die Abfrage wird in einigen neueren MySQL-Versionen sehr lange ausgeführtSep 20, 2011
: Multi-Cores und MySQL-PerformanceJun 19, 2011
: Wie führe ich ein MySQL-Bake-Off richtig durch?UPDATE 2012-09-06 14:56 EDT
Meine Methode zum Leeren des Abfragecaches ist ziemlich extrem, da sie zwischengespeicherte Daten überflutet und ein völlig anderes RAM-Segment bildet. Wie Sie in Ihrem Kommentar ausgeführt haben
FLUSH QUERY CACHE
(wie Sie vorgeschlagen haben) oder sogarRESET QUERY CACHE
besser wären. Zur Verdeutlichung, als ich "kein interner Mechanismus" sagte, meinte ich genau das. Die Defragmentierung ist erforderlich und muss manuell durchgeführt werden. Es müsste crontab'd werden .Wenn Sie DML (INSERTs, UPDATEs, DELETEs) in InnoDB häufiger ausführen als in MyISAM, würde ich sagen, dass Sie den Abfrage-Cache insgesamt entfernen, was ich am Anfang gesagt habe.
quelle
FLUSH QUERY CACHE
zum Defragmentieren nicht ausführen ? Siehe: dev.mysql.com/doc/refman/5.0/en/flush.htmlBAD: query_cache_size = 1G
Warum? Wie lange dauert ein Flush? Das heißt, wenn einige Schreibvorgänge ausgeführt werden, werden alle 1 GB nach Verweisen auf die geänderte Tabelle durchsucht. Je größer die QC, desto langsamer ist diese. Ich empfehle eine Größe von nicht mehr als 50 MB, es sei denn, Ihre Daten ändern sich selten.
Die Qualitätskontrolle ist sowohl für MyISAM als auch für InnoDB mit einem Mehraufwand verbunden. Es nimmt einen globalen Mutex heraus und nimmt ihn zu früh heraus. Dieser Mutex ist ein Grund, warum MySQL nicht mehr als 8 Kerne effektiv nutzen kann.
SQL_NO_CACHE wird erst nach dem Sperren des Mutex bemerkt ! Die einzige Verwendung für dieses Flag ist das Benchmarking.
Häufig ist es besser, den RAM einem anderen Cache zuzuweisen.
quelle
Ich kann mir einen perfekten Fall dafür vorstellen, und wir haben ihn gründlich getestet und in der Produktion ausgeführt ... Ich nenne ihn die "Überholspur" -Clustering-Strategie:
Wenn Sie mit einem Proxy wie MaxScale eine Lese- / Schreibaufteilung durchführen oder Ihre Anwendung dazu in der Lage ist, können Sie einige der Lesevorgänge für diese selten ungültig gemachten Tabellen nur an Slaves senden, bei denen der Abfragecache aktiviert ist, und den Rest an andere Slaves ausgeschaltet.
Dies tun wir und bearbeiten als Ergebnis 4 Millionen Anrufe pro Minute an den Cluster während unserer Auslastungstests (kein Benchmark ... der eigentliche Deal). Die App wartet in master_pos_wait () auf einige Dinge, sodass sie vom Replikationsthread gedrosselt wird. Obwohl der Status "Warten auf Qcache-Invalidierung bei sehr hohem Durchsatz" angezeigt wird, sind diese Durchsatzraten höher als der gerade Wert des Clusters fähig ohne Qcache.
Dies funktioniert, weil in dem winzigen Abfragecache auf diesen Computern selten etwas Relevantes zum Ungültigmachen vorhanden ist (diese Abfragen sind nur für selten aktualisierte Tabellen relevant). Diese Boxen sind unsere "Überholspur". Für den Rest der Abfragen, die die Anwendung ausführt, müssen sie sich nicht mit Qcache herumschlagen, da sie zu Boxen wechseln, ohne dass diese aktiviert sind.
quelle