# Mit Mysql mehrere Kerne nutzen



## BugsBastard (4. Mai 2010)

Hallo zusammen,

ich habe mal ein interessantes Mysql-Problem (zumindest für mich interessant).

Wir haben ein Intranet, welches wir mit PHP und Mysql programmieren. Außerdem hängen noch einige andere Programme über diverse Schnittstellen in dem System, welche die Daten mit der Mysql-Datenbank abgleichen. Mysql selber läuft auf einem eigenen Server (mit Windows), welcher 4 Prozessorkerne hat.

Nun haben wir oft das Problem, daß der Mysql-Server durch bestimmte (nicht optimierbare) Mysql-Abfragen komplett ausgelastet ist, bzw. andere Benutzer keinen Zugriff mehr auf den mysql-Server haben. Wenn wir uns den Server anschauen, dann läuft er im Task-manager auf 25%. Da er 4 Kerne hat, gehen wir davon aus, daß nur ein Kern wirklich ausgelastet ist, die anderen gar nicht benutzt werden.

Für unser Intranet benutzen wir für den Zugriff jeweils nur einen Benutzer. Wenn ich nun, während der Server ausgelastet ist, mit einem Mysql-Administrator unter einem anderen Benutzer auf den Server zugreife, dann kann ich verschiedene Abfragen ausführen, ohne Probleme. Die Auslastung des mysql-Servers geht in diesem Fall auch über 25%, ich kann auch keinen großen Geschwindigkeitsverlust beim ausführen der Abfragen feststellen. Wenn ich allerdings auf der PHP-Seite, welche die Monsterabfragen erstellt, einen anderen Mysql-Benutzer einstelle, so wird der Mysql-Server trotzdem für die anderen PHP-Seiten (mit dem Haupt-Benutzer) geblockt. 

1. Ist es richtig, daß Mysql seine Abfragen von verschiedenen Benutzern auf verschieden Kerne verteilt, oder ist das nur ein komisches (aber replizierbares) Phänomen bei uns?
2. Wie kann ich es einstellen, daß PHP unterschiedliche Mysql-User benutzt, normalerweise sollte ich das doch in der Connection direkt einstellen, richtig?
3. Kann es sein, daß PHP wenn ich die Connection wechsel, weiterhin auf die Alte Connection zugreift nur mit einem anderen Benutzer?

Gruss und danke,

Bugs


----------



## gorefest (4. Mai 2010)

Hi,

schau doch mal in die Datenbank. Nutzt Ihr ISAM Tabellen?


----------



## BugsBastard (4. Mai 2010)

Hi,

wir nutzen myisam-Tabellen,

Gruss,

Bugs


----------



## gorefest (4. Mai 2010)

ein lang laufender Schreibzugriff auf eine myIsam tabelle macht für die Dauer des Zugriffs ein table-lock, welches auch SELECTs hemmt.

es lohnt sich auch, mal zu checken, ob irgendjemand LOCK TABLE absetzt.

[edit] 
ausserdem lohnt es sich, mal die Apache-PHP Config zu prüfen, ob da Connectionpooling verwendet werden kann.
[/edit]

Grüße
gore


btw, nicht optimierbare Statements gibts net ;-)


----------



## BugsBastard (4. Mai 2010)

Hi,

längere Schreibzugriffe haben wir in diesem Fall nich, es geht rein um lesende Zugriffe. Mit dem nicht optimierbar meinte ich übrigens nicht, daß wir die Abfrage nicht noch optimieren können (durch indizies), sondern daß wir in dieser Tabelle keine Indizies mehr verwenden dürfen. Die Tabelle wird aus einem externen System jede Nacht erstellt, die vorhandenen Indizies erstellen dauert bereits 1,5 Stunden, das Eintragen der Daten ca. 3 Stunden. Da wir nur ein Zeitfenster von ca. 6 Stunden nachts haben (wir arbeiten mit Firmen in anderen Zeitzonen zusammen), und noch einige andere Operationen nachts durchgeführt werden, können wir keine weiteren Indizies erstellen. 

Warum wir so eine "kranke" Sache machen möchte ich nicht kommentieren, leider ist das abhängig von dem System mit dem wir da zusammenarbeiten (haben selber oft genug darüber geflucht).

Gruss,

Bugs


----------



## gorefest (4. Mai 2010)

Hi, es geht nicht um längere Schreibzugriffe, sondern generell um Schreibzugriffe auf irgendwelche Tabellen.

Schreibzugriffe auf myIsam blocken alle SELECTs auf eine Relation. Gutes antipattern ist da beispielsweise ein Log-Tabelle, in die reingeloggt wird, während andere darauf selektieren. Hierbei solltet Ihr mal das Augenmerk auf INNODB stellen, welches ROW LEVEL LOCKs unterstützt.

Über welche Volumina sprechen wir hier? Sonst hätte ich Euch vorgeschlagen, die Indizes vor dem Ladeprozess zu droppen und danach neu aufzubauen.

Bei INNODB kann man im übrigen durch Erhöhung des BUFFER POOL attributs in der Konfig einen Geschwindigkeitszuwachs erreichen. Persönlich kann ich nur dazu sagen, dass ich myISAM generell nicht mehr einsetze, weil es aufgrund des kaputten Tabellensperrverhaltens immer wieder mal Probleme gibt, insbesondere wenn man etwas Last auf den Server bekommt.

Ihr solltet im PHP auf jeden Fall sicherstellen, dass Ihr mit pconnect arbeitet und evtl. im Apache das Connectionpooling aktivieren. Kannst Du im laufenden Betrieb mehr als eine Connection auf der Datenbank sehen?

Grüße
gore


----------



## BugsBastard (4. Mai 2010)

Hi,

Schreibzugriffe haben wir in dieser Zeit nicht, da kein Benutzer arbeiten kann während die Abfrage (es gibt mehrere Abfragen, aber kann halt nur immer eine zur Zeit laufen da der Server komplett alles andere blockiert) läuft. 

Zitat: 
Über welche Volumina sprechen wir hier? Sonst hätte ich Euch vorgeschlagen, die Indizes vor dem Ladeprozess zu droppen und danach neu aufzubauen.

Genau das machen wir schon, trotzdem dauert es so lange. Wir reden über mehr als 1,5 Millionen Datensätze mit 70 Feldern, sowie eine andere Tabelle mit 100000 Datensätzen und 110 Feldern. Die beiden Tabellen müssen für diverse Abfragen über 5 bestimmte Felder verknüpft werden. 

INNODB wurde absichtlich nicht eingesetzt, da diese zu Geschwindigkeitseinbußen führen soll (ich muß gestehen daß ich da keine Erfahrung mit habe)

Würde bei pconnect (PHP) nicht genau das gleiche passieren, bzw. alle Benutzer immer über die gleiche, nicht schließbare connection gelotst? (so habe ichs zumindest verstanden). Würde das das ganze nicht erst recht langsam machen?
Ich kann sehen, daß mehrere Benutzer auf die Datenbank zugreifen, aber greifen die halt alle auf den gleichen Kern zu.

Gruss,

Bugs


----------



## gorefest (4. Mai 2010)

zunächst



> Wozu dienen persistente Verbindungen, wenn sie keine zusätzliche Funktionalität bieten?
> 
> Die Antwort ist außerordentlich einfach: Effizienz. Persistente Verbindungen sind nützlich, wenn der Aufwand für das Herstellen einer Verbindung zu einem SQL-Server hoch ist. Ob dies der Fall ist oder nicht, hängt von vielen Faktoren ab - zum Beispiel, um welche Datenbank es sich handelt, ob sie auf dem gleichen Rechner wie der Webserver läuft oder welche Last die SQL-Maschine zu bewältigen hat usw. Grundsätzlich gilt, dass, wenn viele Verbindungen hergestellt werden müssen, persistente Verbindungen außerordentlich hilfreich sind. Sie veranlassen den untergeordneten Prozess, sich während seiner gesamten Lebensdauer lediglich einmal mit dem SQL-Server zu verbinden, anstatt bei jedem Aufruf einer Seite, die eine Verbindung benötigt. Das heißt, dass jeder untergeordnete Prozess, der eine persistente Verbindung öffnet, seine eigene dauerhafte Verbindung zum Server hat. Bei 20 untergeordneten Prozessen, die ein Skript ausführen, das eine persistente Verbindung zum SQL-Server herstellt, hat man beispielsweise 20 verschiedene Verbindungen zum SQL-Server - eine für jeden untergeordneten Prozess.
> 
> Beachten Sie jedoch, dass dies auch ein paar Nachteile haben kann, wenn Sie eine Datenbank mit limitierten Verbindungen benutzen, welche durch persistente Verbindungen überschritten werden. Wenn Ihre Datenbank ein Limit von 16 gleichzeitigen Verbindungen hat, und aufgrund einer stark ausgelasteten Server-Session 17 Kind-Prozesse versuchen, eine Verbindung herzustellen, wird es einem nicht gelingen. Sollten in Ihren Skripten Fehler bestehen, welche das Schließen der Verbindungen nicht erlauben (wie z.B. Endlosschleifen), kann das eine Datenbank mit mit nur 16 Verbindungen sehr schnell überschwemmen. Konsultieren Sie die Dokumentation Ihrer Datenbank bezüglich der Behandlung von aufgegebenen Verbindungen oder Verbindungen im Leerlauf.



Des Weiteren :

Ist der Server ein eigenes Kompilat? Oder nutzt Ihr einen Installer?

Noch ein Hinweis : Bei diesen Volumina solltet Ihr über einen Einsatz von Partitionen nachdenken. Wie bereits erwähnt, lehne ich persönlich myISAM aus diversen Gründen ab. Ein geeigneter Partitionsschlüssel ist meistens schnell gefunden und kann das Suchen in den Daten erheblich beschleunigen.

Grüße


----------



## gorefest (4. Mai 2010)

btw, 

das performanceblog hat auch eine meinung dazu

http://www.mysqlperformanceblog.com/2006/06/17/using-myisam-in-production/

grüße


----------



## TheSilent (7. Mai 2010)

Da die Antworten von deiner Originalfrage ein wenig abweichen hier noch ein Kommentar von mir.

Es ist richtig, dass jede Connection zu MySQL Server als ein Thread läuft und daher nicht mehrere CPUs nutzen kann. Abfragen über diese Connection laufen in diesem Thread. Daher sollte immer versucht werden, mit Connection-Pools, also mit mehreren Connections auf MySQL Server zu arbeiten. Nur so können alle Kerne optimal genutzt werden.


----------

