Inhaltsverzeichnis
Access denied
-FehlerMySQL server has gone away
-FehlerCan't connect to [local] MySQL server
-FehlerHost '...' is blocked
-FehlerToo many connections
-FehlerSome non-transactional changed tables couldn't be rolled back
-FehlerNo free memory
-FehlerPacket too large
-FehlerThe table is full
-FehlerCan't create/write to file
-FehlerCommand out of sync
-Fehler in ClientUser ignored
-FehlerTable 'xxx' doesn't exist
-FehlerCan't initialize charset xxx
-Fehler.Dieses Kapitel listet einige gebräuchliche Probleme und Fehlermeldungen auf, denen Benutzer in die Arme laufen. Sie lernen herauszufinden, was das Problem ist und wie Sie es lösen. Hier finden sich auch korrekte Lösungen einiger häufiger Probleme.
Wenn Sie Probleme bekommen, sollten Sie als erstes herausfinden, welches Programm oder Hardware-Teil die Probleme verursacht:
Wenn Sie eins der folgenden Symptome beobachten, gibt es wahrscheinlich ein Hardware- (Speicher, Hauptplatine, Prozessor oder Festplatte) oder Kernel-Problem:
Die Tastatur funktioniert nicht. Normalerweise können Sie das durch Drücken der Feststelltaste (Caps Lock) überprüfen. Wenn sich die Anzeigeleuchte beim Drücken nicht an- und ausschaltet, müssen Sie Ihre Tastatur ersetzen. (Bevor Sie das tun, sollten Sie Ihren Computer neu starten und alle Kabelverbindungen zur Tastatur überprüfen.)
Der Mauszeiger bewegt sich nicht.
Die Maschine antwortet auf entfernte Ping-Versuche nicht.
Andere Programme, die mit MySQL nichts zu tun haben, funktionieren nicht korrekt.
Wenn Ihr System unerwartet neu startet (ein fehlerhaftes Programm auf Benutzerebene sollte NIE in der Lage sein, Ihr System zum Absturz zu bringen).
In solchen Fällen sollten Sie zunächst alle Kabel überprüfen und Diagnoseprogramme laufen lassen, um Ihre Hardware zu untersuchen! Sie sollten auch prüfen, ob Patches, Aktualisierungen oder Service-Packs für Ihre Betriebssystem verfügbar sind, die Ihre Probleme möglicherweise lösen. Prüfen Sie auch, ob Ihre Bibliotheken (wie glibc) aktuell sind.
Es ist immer eine gute Idee, eine Maschine mit ECC-Speicher zu benutzen, um Speicherprobleme frühzeitig zu erkennen!
Wenn Ihre Tastatur gesperrt ist, können Sie das eventuell
beheben, indem Sie sich von einer anderen Maschine aus
verbinden und kbd_mode -a
ausführen.
Untersuchen Sie Ihre System-Log-Datei (/var/log/messages oder ähnliches) nach Gründen für Ihre Probleme. Wenn Sie glauben, dass das Problem an MySQL liegt, sollten Sie auch die Log-Dateien von MySQL überprüfen. See Abschnitt 5.9.3, „Die Update-Log-Datei“.
Wenn Sie nicht glauben, ein Hardware-Problem zu haben, sollten Sie herausfinden, welches Programm die Probleme verursacht.
Probieren Sie top
, ps
,
taskmanager
oder ein ähnliches Programm,
um zu prüfen, welches Programm die gesamte Prozessorzeit
konsumiert oder die Maschine blockiert.
Prüfen Sie mit top
, df
oder einem ähnlichen Programm, wenn Sie keinen freien
Arbeitsspeicher, Festplattenspeicher, verfügbare
Datei-Handler oder eine andere kritische Ressource mehr haben.
Wenn das Problem an einem aus dem Ruder gelaufenen Prozess liegt, können Sie versuchen, diesen zu killen. Wenn er nicht sterben will, gibt es wahrscheinlich einen Bug im Betriebssystem.
Wenn Sie alle anderen Möglichkeiten untersucht und ausgeschlossen haben und zur Schlussfolgerung gekommen sind, dass die Probleme durch den MySQL-Server oder ein MySQL-Client-Programm verursacht werden, ist es an der Zeit, einen Bug-Bericht für die Mailing-Liste oder unser Support-Team zu schreiben. Machen Sie im Bug-Bericht eine sehr detaillierte Beschreibung, wie sich Ihr System verhält und was Sie vermuten, was passiert. Sie sollten auch angeben, warum Sie denken, dass MySQL die Probleme verursacht. Ziehen Sie alle Situationen in diesem Kapitel in Betracht. Geben Sie genau an, welche Probleme wie auftauchen, wenn Sie Ihr System untersuchen. Benutzen Sie Kopieren und Einfügen, wenn Sie Ausgaben und / oder Fehlermeldungen von Programmen oder aus Log-Dateien beifügen!
Versuchen Sie detailliert zu beschreiben, welches Programm nicht funktioniert, und alle Symptome, die Sie sehen! In der Vergangenheit haben wir viele Bug-Berichte erhalten, in denen schlicht steht, dass "das System nicht funktioniert". Daraus können wir natürlich keinerlei Informationen ziehen, wie das Problem gelöst werden könnte.
Wenn ein Programm fehlschlägt, ist es immer nützlich, folgendes zu wissen:
Hat das fragliche Programm einen Segmentation-Fehler verursacht (Core Dump)?
Nimmt das Programm sich die gesamte Prozessorleistung?
Überprüfen Sie das mit top
. Lassen Sie
das Programm eine Weile laufen, denn vielleicht evaluiert es
gerade nur etwas Schwieriges.
Wenn der mysqld
-Server Probleme verursacht,
können Sie dann mysqladmin -u root ping
oder mysqladmin -u root processlist
ausführen?
Was sagt ein Client-Programm (zum Beispiel
mysql
), wenn Sie versuchen, sich mit dem
MySQL-Server zu verbinden? Bricht der Client zusammen?
Erhalten Sie von diesem Programm irgend welche Ausgaben?
Wenn Sie einen Bug-Bericht senden, sollten Sie immer den Angaben folgen, die in diesem Handbuch beschrieben sind. See Abschnitt 2.6.2.2, „Wie man Fragen stellt oder Bugs berichtet“.
Access denied
-FehlerMySQL server has gone away
-FehlerCan't connect to [local] MySQL server
-FehlerHost '...' is blocked
-FehlerToo many connections
-FehlerSome non-transactional changed tables couldn't be rolled back
-FehlerNo free memory
-FehlerPacket too large
-FehlerThe table is full
-FehlerCan't create/write to file
-FehlerCommand out of sync
-Fehler in ClientUser ignored
-FehlerTable 'xxx' doesn't exist
-FehlerCan't initialize charset xxx
-Fehler.Dieser Abschnitt listet einige Fehler auf, die Benutzer häufig erhalten. Hier finden Sie Beschreibungen dieser Fehler und wie man die Probleme löst.
See Abschnitt 5.2.5, „Wie das Berechtigungssystem funktioniert“, insbesondere See
Abschnitt 5.2.10, „Gründe für Access denied
-Fehler“.
Dieser Abschnitt behandelt auch den verwandten Lost
connection to server during query
-Fehler.
Der häufigste Grund für den MySQL server has gone
away
-Fehler ist eine Zeitüberschreitung, nach der der
Server die Verbindung schloss. Vorgabemäßig schließt der
Server die Verbindung nach 8 Stunden, wenn nichts passiert ist.
Sie können diesen Wert mit der
wait_timeout
-Variablen ändern, die beim
Start von mysqld
gesetzt wird.
Ein weiterer häufiger Grund für den MySQL server has
gone away
-Fehler ist das Absetzen eines ``close'' auf
Ihre MySQL-Verbindung mit dem anschließenden Versuch, auf der
geschlossenen Verbindung eine Anfrage abzusetzen.
Sie können überprüfen, ob der MySQL-Server gestorben ist,
indem Sie mysqladmin version
ausführen und
die Uptime untersuchen.
Wenn Sie ein Skript haben, müssen Sie die Anfrage lediglich noch einmal für den Client absetzen, um eine automatische Neuverbindung zu machen.
Normalerweise können Sie folgende Fehler-Codes für diesen Fall abfragen (die Betriebssystem-abhängig sind):
CR_SERVER_GONE_ERROR | Der Client konnte keine Anfrage an den Server schicken. |
CR_SERVER_LOST | Der Client erhielt beim Schreiben zum Server keinen Fehler, bekam aber keine vollständige (oder überhaupt keine) Antwort. |
Sie erhalten diese Fehler auch, wenn Sie eine Anfrage zum Server
schicken, die falsch oder zu Groß ist. Wenn
mysqld
ein Paket erhält, das zu Groß oder
nicht in Ordnung ist, nimmt er hat, dass etwas mit dem Client
schief ging und schließt die Verbindung. Wenn Sie große
Anfragen brauchen (beispielsweise wenn Sie mit
BLOB
-Spalten arbeiten), können Sie die
Anfragebeschränkung erhöhen, indem Sie
mysqld
mit der -O
max_allowed_packet=#
-Option starten (Vorgabe 1 MB).
Der zusätzliche Speicher wird bei Bedarf zugewiesen, daher
benutzt mysqld
nur dann mehr Speicher, wenn
Sie eine große Anfrage ausführen oder wenn
mysqld
ein großes Ergebnis zurückgeben
muss!
Ein MySQL-Client unter Unix kann sich auf zwei unterschiedliche
Arten mit dem mysqld
-Server verbinden:
Unix-Sockets, die sich durch eine Datei im Dateisystem verbinden
(Vorgabe /tmp/mysqld.sock
) oder über
TCP/IP, was sich über eine Portnummer verbindet. Unix-Sockets
sind schneller als TCP/IP, können aber nur benutzt werden, wenn
man sich zu einem Server auf demselben Computer verbindet.
Unix-Sockets werden benutzt, wenn Sie keinen Hostnamen oder den
speziellen Hostnamen localhost
angeben.
Unter Windows können Sie sich nur mit TCP/IP verbinden, wenn
der mysqld
-Server unter Windows 95 / 98
läuft. Wenn er unter Windows NT läuft, können Sie sich auch
mit Named Pipes verbinden. Der Name der Named Pipe ist MySQL.
Wenn Sie bei der Verbindung zu mysqld
keinen
Hostnamen angeben, versucht ein MySQL-Client zuerst, sich über
die Named Pipe zu verbinden. Erst wenn das fehlschlägt,
versucht er, sich über den TCP/IP-Port zu verbinden. Sie
können die Benutzung von Named Pipes unter Windows erzwingen,
indem Sie .
als Hostnamen benutzen.
Der Fehler (2002) Can't connect to ...
bedeutet normalerweise, dass auf dem System kein MySQL-Server
läuft oder dass Sie eine falsche Socket-Datei oder einen
falschen TCP/IP-Port bei der Verbindung mit dem
mysqld
-Server benutzen.
Prüfen Sie zuerst mit ps
oder dem
Task-Manager unter Windows, ob es einen laufenden Prozess namens
mysqld
auf Ihrem Server gibt! Wenn es keinen
mysqld
-Prozess gibt, sollten Sie einen
starten. See Abschnitt 3.4.2, „Probleme mit dem Start des MySQL-Servers“.
Wenn ein mysqld
-Prozess läuft, können Sie
den Server mit diesen unterschiedlichen Verbindungen
überprüfen (die Portnummer und Socket-Pfadnamen können auf
Ihrem System natürlich anders sein):
shell>mysqladmin version
shell>mysqladmin variables
shell>mysqladmin -h `hostname` version variables
shell>mysqladmin -h `hostname` --port=3306 version
shell>mysqladmin -h 'ip_ihres_hosts' version
shell>mysqladmin --socket=/tmp/mysql.sock version
Beachten Sie die Benutzung umgedrehter Anführungszeichen statt
normaler Anführungszeichen beim
hostname
-Befehl. Diese verursachen, dass die
Ausgabe durch hostname
(das heißt des
aktuellen Hostnamens) im mysqladmin
-Befehl
ersetzt wird.
Hier sind einige Gründe für das Auftreten des Can't
connect to local MySQL server
-Fehlers:
mysqld
läuft nicht.
Sie fahren auf einem System, das MIT-pThread verwendet. Wenn
Sie auf einem System fahren, das keine nativen Threads hat,
benutzt mysqld
das MIT-pThread-Paket. See
Abschnitt 3.2.2, „Betriebssysteme, die von MySQL unterstützt werden“. Nicht alle MIT-pThread-Versionen
unterstützen jedoch Unix-Sockets. Auf einem System ohne
Socket-Unterstützung müssen Sie den Hostnamen immer
explizit angeben, wenn Sie sich mit dem Server verbinden.
Benutzen Sie diesen Befehl, um die Verbindung zum Server zu
überprüfen:
shell> mysqladmin -h `hostname` version
Jemand hat den Unix-Socket entfernt, den
mysqld
benutzt (Vorgabe
/tmp/mysqld.sock
). Vielleicht gibt es
einen cron
-Job, der den MySQL-Socket
entfernt (beispielsweise ein Job, der alte Dateien aus dem
/tmp
-Verzeichnis entfernt). Sie können
mysqladmin version
laufen lassen und
überprüfen, dass der Socket, den
mysqladmin
versucht zu benutzen,
tatsächlich existiert. Die Problemlösung besteht in diesem
Fall darin, den cron
-Job so zu ändern,
dass er nicht mysqld.sock
entfernt oder
den Socket an andere Stelle zu platzieren. See
Abschnitt A.4.5, „Wie Sie die MySQL-Socket-Datei /tmp/mysql.sock
schützen oder ändern“.
Sie haben den mysqld
-Server mit der
--socket=/pfad/zu/socket
-Option gestartet.
Wenn Sie den Socket-Pfadnamen zum Server ändern, müssen
Sie auch die MySQL-Clients darüber unterrichten. Das
können Sie tun, indem Sie den Socket-Pfad als Argument an
den Client übergeben. See
Abschnitt A.4.5, „Wie Sie die MySQL-Socket-Datei /tmp/mysql.sock
schützen oder ändern“.
Sie benutzen Linux und ein Thread ist gestorben (Core Dump).
In diesem Fall müssen Sie den anderen
mysqld
-Thread killen (beispielsweise mit
dem mysql_zap
-Skript), bevor Sie einen
neuen MySQL-Server starten können. See
Abschnitt A.4.1, „Was zu tun ist, wenn MySQL andauernd abstürzt“.
Eventuell haben Sie keine Lese- und Schreibberechtigungen
entweder für das Verzeichnis, in dem die Socket-Datei
liegt, oder keine Berechtigung für die Socket-Datei selbst.
In diesem Fall können Sie entweder die Berechtigung für
die Datei und / oder das Verzeichnis ändern oder
mysqld
neu starten, so dass er ein
Verzeichnis benutzt, auf das Sie Zugriff haben.
Wenn Sie die Fehlermeldung Can't connect to MySQL
server on ein_hostname
erhalten, können Sie folgendes
probieren, um den Grund des Problems herauszufinden:
Überprüfen Sie, ob der Server hochgefahren ist, indem Sie
telnet ihr_hostname tcp-ip-port-nummer
ausführen und einige Male die Eingabetaste
(RETURN
) drücken. Wenn es auf diesem
Port einen laufenden MySQL-Server gibt, sollten Sie eine
Antwort erhalten, die die Versionsnummer des Server
enthält. Wenn Sie einen Fehler wie telnet: Unable
to connect to remote host: Connection refused
erhalten, gibt es auf diesem Port keinen laufenden Server.
Versuchen Sie, sich mit dem mysqld
-Daemon
auf der lokalen Maschine zu verbinden und prüfen Sie den
TCP/IP-Port, den mysqld
laut
Konfiguration benutzen soll (Variable
port
), mit mysqladmin
variables
.
Prüfen Sie, ob Ihr mysqld
-Server nicht
gestartet wurde, indem Sie die
--skip-networking
-Option verwenden.
Wenn Sie einen Fehler wie folgt erhalten:
Host 'hostname' is blocked because of too many connection errors. Unblock with 'mysqladmin flush-hosts'
Bedeutet das, dass mysqld
zu viele
(max_connect_errors
) Verbindungsanforderungen
vom Host 'hostname'
erhalten hat, die
mittendrin unterbrochen wurden. Nach
max_connect_errors
fehlgeschlagenen Anfragen
nimmt mysqld
an, dass etwas nicht stimmt (wie
ein Angriff eines Crackers) und blockiert weitere
Verbindungsanforderungen von der Site, bis jemand
mysqladmin flush-hosts
ausführt.
Vorgabemäßig blockiert mysqld
einen Host
nach 10 Verbindungsfehlern. Das können Sie leicht durch Starten
des Servers wie folgt ändern:
shell> safe_mysqld -O max_connect_errors=10000 &
Beachten Sie, dass Sie bei dieser Fehlermeldung für einen
gegebenen Host zunächst prüfen sollten, ob etwas mit den
TCP/IP-Verbindungen von diesem Host aus nicht stimmt. Wenn Ihre
TCP/IP-Verbindungen nicht funktionieren, nützt es Ihnen nichts,
den Wert der max_connect_errors
-Variablen
heraufzusetzen!
Wenn Sie beim Verbindungsversuch den Fehler Too many
connections
erhalten, heißt das, dass es bereits
max_connections
Clients gibt, die mit dem
mysqld
-Server verbunden sind.
Wenn Sie mehr Verbindungen als die Vorgabe (100) benötigen,
können Sie mysqld
mit einem größeren Wert
für die max_connections
-Variable neu
starten.
Beachten Sie, dass mysqld
tatsächlich
(max_connections
+1) Clients für Verbindungen
zuläßt. Die letzte Verbindung wird für einen Benutzer mit der
process-Berechtigung
reserviert. Wenn Sie keinem normalen Benutzer diese Berechtigung
geben (diese sollte sie nie benötigen), kann sich ein
Administrator mit dieser Berechtigung einloggen und
SHOW PROCESSLIST
benutzen, um herauszufinden,
was schief geht. See Abschnitt 5.5.5, „SHOW
-Syntax“.
Die maximale Anzahl von Verbindungen ist davon abhängig, wie gut die Thread-Bibliothek auf der Plattform ist. Linux oder Solaris sollten in der Lage sein, 500 bis 1000 gleichzeitige Verbindungen zu unterstützen, abhängig davon, wie viel Arbeitsspeicher Sie haben und was Ihre Clients ausführen.
Wenn Sie den Fehler Warning: Some non-transactional
changed tables couldn't be rolled back
erhalten, wenn
Sie ein ROLLBACK
versuchen, bedeutet das,
dass einige der bei der Transaktion benutzten Tabellen keine
Transaktionen unterstützen. Diese nicht transkationalen
Tabellen werden vom ROLLBACK
-Statement nicht
betroffen.
Der typischste Fall, bei dem dieser Fehler auftritt, ist, wenn
Sie versucht haben, eine Tabelle von einem Typ zu erzeugen, der
von Ihrer mysqld
-Binärdatei nicht
unterstützt wird. Wenn mysqld
einen
Tabellentyp nicht unterstützt (oder wenn der Tabellentyp durch
die Startoption ausgeschaltet ist), wird statt dessen ein
Tabellentyp erzeugt, der dem angeforderten am nächsten
entspricht (wahrscheinlich MyISAM
.
Sie können den Tabellentyp für eine Tabelle wie folgt überprüfen:
SHOW TABLE STATUS LIKE 'tabelle'
. See
Abschnitt 5.5.5.2, „SHOW TABLE STATUS
“.
Sie können die Erweiterungen, die Ihre
mysqld
-Binärdatei unterstützt, wie folgt
überprüfen:
show variables like 'have_%'
. See
Abschnitt 5.5.5.4, „SHOW VARIABLES
“.
Wenn Sie eine Anfrage ausführen und etwas wie folgenden Fehler erhalten:
mysql: No free memory at line 42, 'malloc.c' mysql: needed 8136 byte (8k), memory in use: 12481367 Bytes (12189k) ERROR 2008: MySQL client ran No free memory
Beachten Sie, dass sich dieser Fehler auf den MySQL-Client
mysql
bezieht. Der Grund für diesen Fehler
ist einfach, dass der Client nicht genug freien Speicher hat, um
das gesamte Ergebnis zu speichern.
Um das Problem zu beheben, prüfen Sie zunächst, ob Ihre
Anfrage korrekt ist. Sollte sie vernünftigerweise so viele
Zeilen zurückgeben? Wenn das der Fall ist, können Sie
mysql --quick
benutzen, was
mysql_use_result()
benutzt, um die
Ergebnismenge abzurufen. Hierdurch wird Last vom Client auf den
Server verlagert.
Wenn ein MySQL-Client oder der mysqld
-Server
ein Paket erhält, das größer als
max_allowed_packet
Bytes ist, gibt er einen
Packet too large
-Fehler aus und schließt die
Verbindung.
Wenn Sie den mysql
-Client benutzen, müssen
Sie einen größeren Puffer angeben, indem Sie den Client mit
mysql --set-variable=max_allowed_packet=8M
starten.
Wenn Sie andere Clients benutzen, die die Angabe der maximalen
Paketgröße nicht zulassen (wie DBI
),
müssen Sie die Paketgröße beim Start des Servers setzen. Sie
können eine Kommandozeilenoption für mysqld
benutzen, um max_allowed_packet
auf eine
höhere Größe zu setzen. Wenn Sie zum Beispiel beabsichtigen,
die volle Länge eines BLOB
in eine Tabelle
zu speichern, müssen Sie den Server mit der
--set-variable=max_allowed_packet=16M
-Option
starten.
Sie können merkwürdige Probleme mit großen Paketen erhalten,
wenn Sie große Blobs benutzen, aber mysqld
keinen Zugriff auf genug Speicher gegeben haben, um die Anfrage
zu handhaben. Wenn Sie vermuten, dass das der Fall ist,
versuchen Sie, am Anfang des
safe_mysqld
-Skripts ulimit -d
256000
hinzuzufügen, und starten Sie
mysqld
neu.
Ab MySQL 3.23.40
erhalten Sie den
Aborted connection
-Fehler nur dann, wenn Sie
mysqld
mit --warnings
starten.
Wenn Sie Fehler wie den folgenden in Ihrer Fehler-Log-Datei entdecken:
010301 14:38:23 Aborted connection 854 to db: 'Benutzer' user: 'josh'
See Abschnitt 5.9.1, „Die Fehler-Log-Datei“.
Bedeutet das, dass eins der folgenden Dinge passiert ist:
Das Client-Programm rief vor dem Beenden nicht
mysql_close()
auf.
Der Client schlief länger als
wait_timeout
oder
interactive_timeout
, ohne Anfragen
auszuführen.
Das Client-Programm wurde abrupt während einer Übertragung beendet.
Wenn das oben Genannte passiert, wird die Servervariable
Aborted_clients
heraufgezählt.
Die Servervariable Aborted_connects
wird in
folgenden Fällen heraufgezählt:
Wenn ein Verbindungspaket nicht die richtigen Informationen enthält.
Wenn der Benutzer keine Berechtigung hat, sich mit einer Datenbank zu verbinden.
Wenn ein Benutzer ein falsches Passwort angegeben hat.
Wenn es länger als connect_timeout
Sekunden dauert, um ein Verbindungspaket zu erhalten.
Beachten Sie, dass obiges auch anzeigen könnte, dass jemand versucht, in Ihre Datenbank einzubrechen!
See Abschnitt 5.5.5.4, „SHOW VARIABLES
“.
Andere Gründe für Probleme mit abgebrochenen Clients / abgebrochenen Verbindungen:
Benutzung des Duplex-Ethernet-Protokolls, sowohl Halb- als auch Voll-Duplex, unter Linux. Viele Linux-Ethernet-Treiber haben diesen Bug. Sie können auf diesen Bug überprüfen, indem Sie eine sehr große Datei via FTP zwischen diesen beiden Maschinen übertragen. Wenn ein Transfer nach dem Schema schnelle Übertragung - Pause - schnelle Übertragung - Pause läuft, haben Sie ein Linux-Duplex-Syndrom. Die einzige Lösung besteht darin, Halb- und Vollduplex auf Hubs und Switches auszuschalten.
Probleme mit der Thread-Bibliothek, was Unterbrechungen bei Lesevorgängen verursacht.
Schlecht konfiguriertes TCP/IP.
Fehlerhafte Ethernets, Hubs, Switches, Kabel usw. Das kann nur durch Austausch von Hardware sauber diagnostiziert werden.
max_allowed_packet
ist zu klein oder
Anfragen erfordern mehr Speicher, als Sie für
mysqld
zugewiesen haben.
Der Fehler tritt in älteren MySQL-Versionen auf, wenn eine
Hauptspeicher-basierende temporäre Tabelle größer als
tmp_table_size
Bytes wird. Um dieses Problem
zu vermeiden, können Sie die -O
tmp_table_size=#
-Option für mysqld
benutzen, um die Größe der temporären Tabelle zu erhöhen,
oder die SQL-Option SQL_BIG_TABLES
verwenden,
bevor Sie die problematische Anfrage abschicken. See
Abschnitt 6.5.6, „SET
-Syntax“.
Sie können auch mysqld
mit der
--big-tables
-Option starten. Das ist genau
dasselbe, wie SQL_BIG_TABLES
für alle
Anfragen zu benutzen.
In MySQL-Version 3.23 werden Hauptspeicher-basierende temporäre
Tabellen automatisch in Festplatten-basierende
MyISAM
-Tabellen umgewandelt, wenn die Tabelle
größer als tmp_table_size
wird.
Wenn Sie für einige Anfragen Fehler folgenden Typs erhalten:
Can't create/write to file '\\sqla3fe_0.ism'.
Bedeutet das, dass MySQL keine temporäre Datei für die
Ergebnismenge im angegebenen temporären Verzeichnis erzeugen
kann. (Der obige Fehler ist eine typische Fehlermeldung unter
Windows; die Unix-Fehlermeldung ist ähnlich.) Das Problem
läßt sich beheben, indem Sie mysqld
mit
--tmpdir=pfad
starten oder folgendes in Ihrer
Optionsdatei ergänzen:
[mysqld] tmpdir=C:/temp
Unter der Annahme, dass das
c:\\temp
-Verzeichnis existiert. See
Abschnitt 5.1.2, „my.cnf-Optionsdateien“.
Überprüfen Sie auch den Fehler-Code, den Sie bei
perror
erhalten. Ein Grund kann ein Fehler
wegen fehlenden Festplattenspeichers sein:
shell> perror 28
Error code 28: No space left on device
Wenn Sie den Fehler command out of sync; You can't run
this command now
in Ihrem Client-Code erhalten, rufen
Sie Client-Funktionen in der falschen Reihenfolge auf!
Das kann zum Beispiel passieren, wenn Sie
mysql_use_result()
benutzen und versuchen,
eine neue Anfrage auszuführen, bevor Sie
mysql_free_result()
aufgerufen haben. Der
Fehler passiert ebenfalls, wenn Sie versuchen, zwei Anfragen
auszuführen, die Daten zurückgeben, ohne zwischendrin
mysql_use_result()
oder
mysql_store_result()
aufzurufen.
Wenn Sie folgenden Fehler erhalten:
Found wrong password for user: 'benutzer@ein_host';
User ignored
Bedeutet das, dass mysqld
beim Start oder
nach dem Neuladen der Berechtigungstabellen einen Eintrag in der
user
-Tabelle mit einem ungültigen Passwort
gefunden hat. Als Ergebnis wird der Eintrag vom
Berechtigungssystem einfach ignoriert.
Mögliche Gründe und Problembehebung:
Sie lassen eine neue Version von mysqld
mit einer alten user
-Tabelle laufen. Das
können Sie prüfen, indem Sie mysqlshow mysql
user
eingeben, um zu sehen, ob das Passwortfeld
kürzer als 16 Zeichen ist. Wenn das der Fall ist, können
Sie diesen Zustand beheben, indem Sie das
scripts/add_long_password
-Skript laufen
lassen.
Der Benutzer hat ein altes Passwort (8 Zeichen lang) und Sie
haben mysqld
nicht mit der
--old-protocol
-Option gestartet.
Sie haben in der user
-Tabelle ein
Passwort eingegeben, ohne die
PASSWORD()
-Funktion zu benutzen. Benutzen
Sie mysql
, um den Benutzer in der
user
-Tabelle mit einem neuen Passwort zu
aktualisieren. Stellen Sie sicher, dass Sie die
PASSWORD()
-Funktion benutzen:
mysql> update user set password=PASSWORD('ihr_passwort')
where user='XXX';
Wenn Sie den Fehler Table 'xxx' doesn't exist
oder Can't find file: 'xxx' (errno: 2)
erhalten, bedeutet das, dass in der aktuellen Datenbank keine
Tabelle mit dem Namen xxx
existiert.
Beachten Sie, dass Datenbank- und Tabellennamen abhängig von der verwendeten Groß-/Kleinschreibung sind, weil MySQL Verzeichnisse und Dateien benutzt, um Datenbanken und Tabellen zu speichern! (Unter Windows sind Datenbank- und Tabellennamen unabhängig von der Schreibweise, aber alle Verweise auf eine gegebene Tabelle innerhalb einer Anfrage müssen dieselbe Schreibweise benutzen!)
Sie finden heraus, welche Tabellen sich in der aktuellen
Datenbank befinden, indem Sie SHOW TABLES
eingeben. See Abschnitt 5.5.5, „SHOW
-Syntax“.
Wenn Sie folgenden Fehler erhalten:
MySQL Connection Failed: Can't initialize charset xxx
Bedeutet das eins der folgenden Dinge:
Der Zeichensatz ist ein Multi-Byte-Zeichensatz und Ihr Client unterstützt diesen Zeichensatz nicht.
In diesem Fall müssen Sie Ihren Client neu kompilieren und
die --with-charset=xxx
- oder die
--with-extra-charsets=xxx
-Option angeben.
See Abschnitt 3.3.3, „Typische configure
-Optionen“.
Alle Standard-MySQL-Binärdistributionen werden mit
--with-extra-character-sets=complex
kompiliert, was die Unterstützung für alle
Multi-Byte-Zeichensätze aktiviert. See
Abschnitt 5.6.1, „Der für Daten und Sortieren benutzte Zeichensatz“.
Der Zeichensatz ist ein einfacher Zeichensatz, der nicht in
mysqld
kompiliert wurde, und die
Zeichensatz-Definitionsdateien sind nicht an der Stelle, an
der der Client sie erwartet.
In diesem Fall müssen Sie:
Den Client mit Unterstützung für den Zeichensatz neu
kompilieren. See Abschnitt 3.3.3, „Typische configure
-Optionen“.
Dem Client angeben, wo die
Zeichensatz-Definitionsdateien sind. Bei vielen Clients
können Sie das mit der
--character-sets-dir=pfad-to-charset-dir
-Option
machen.
Die Zeichensatz-Definitionsdatei in den Pfad kopieren, wo der Client sie zu finden erwartet.
Wenn Sie den Fehler ERROR '...' not found (errno:
23)
, Can't open file: ... (errno:
24)
oder irgend einen anderen Fehler mit
errno 23
oder errno 24
erhalten, bedeutet das, dass Sie MySQL nicht genug
Datei-Deskriptoren zugewiesen haben. Sie können das
perror
-Dienstprogramm benutzen, um eine
Beschreibung dessen zu erhalten, was die Fehlernummer bedeutet:
shell>perror 23
File table overflow shell>perror 24
Too many open files shell>perror 11
Resource temporarily unavailable
Das Problem hierbei ist, dass mysqld
versucht, zu viele Dateien gleichzeitig offen zu halten. Sie
können entweder mysqld
veranlassen, nicht so
viele Dateien auf einmal zu öffnen, oder die Anzahl von
Datei-Deskriptoren heraufsetzen, über die
mysqld
verfügen kann.
Um mysqld
anzuweisen, weniger Dateien
zugleich offen zu halten, können Sie den Tabellen-Cache kleiner
machen, indem Sie die -O
table_cache=32
-Option für
safe_mysqld
benutzen (der Vorgabewert ist
64). Wenn Sie den Wert von max_connections
verringern, reduziert auch das die Anzahl offener Dateien (der
Vorgabewert ist 90).
Um die Anzahl von Datei-Deskriptoren, die
mysqld
zur Verfügung stehen, zu ändern,
können Sie die --open-files-limit=#
-Option
für safe_mysqld
oder die -O
open-files-limit=#
-Option für
mysqld
benutzen. See
Abschnitt 5.5.5.4, „SHOW VARIABLES
“. Die einfachste Art, das zu
tun, besteht darin, eine Option zu Ihrer Optionsdatei
hinzuzufügen. See Abschnitt 5.1.2, „my.cnf-Optionsdateien“. Wenn Sie eine
alte mysqld
-Version haben, die das nicht
unterstützt, können Sie das
safe_mysqld
-Skript editieren. Es gibt dort
eine auskommentierte Zeile ulimit -n 256
.
Entfernen Sie das '#'
-Zeichen, um diese Zeile
zu aktivieren, und ändern Sie die Anzahl 256, um die Anzahl
verfügbarer Datei-Deskriptoren zu beeinflussen.
Mit ulimit
(und
open-files-limit
) kann man die Anzahl von
Datei-Deskriptoren heraufsetzen, aber nur bis zu der Grenze, die
das Betriebssystem vorgibt. Darüber hinaus gibt es eine 'harte'
Grenze, die nur überschrieben werden kann, wenn Sie
safe_mysqld
oder mysqld
als Root starten (denken Sie daran, dass Sie in diesem Fall auch
die --user=..
-Option benutzen müssen). Wenn
Sie die Betriebssystem-Grenze hinsichtlich der Anzahl von
Datei-Deskriptoren, die für jeden Prozess verfügbar sind,
heraufsetzen müssen, schauen Sie in der Dokumentation Ihres
Betriebssystems nach.
Beachten Sie, dass ulimit
nicht funktioniert,
wenn Sie die tcsh
-Shell laufen lassen!
tcsh
berichtet auch nicht korrekte Werte,
wenn Sie die aktuellen Grenzen abfragen! In diesem Fall sollten
Sie safe_mysqld
mit sh
starten!
Wenn Sie Ihr Programm linken und Fehler für unreferenzierte
Symbole erhalten, die mit mysql_
beginnen,
wie folgende:
/tmp/ccFKsdPa.o: In function `main': /tmp/ccFKsdPa.o(.text+0xb): undefined reference to `mysql_init' /tmp/ccFKsdPa.o(.text+0x31): undefined reference to `mysql_real_connect' /tmp/ccFKsdPa.o(.text+0x57): undefined reference to `mysql_real_connect' /tmp/ccFKsdPa.o(.text+0x69): undefined reference to `mysql_error' /tmp/ccFKsdPa.o(.text+0x9a): undefined reference to `mysql_close'
Sollten Sie das durch Hinzufügen von
-Lpath-to-the-mysql-library-lmysqlclient
als
LETZTES in Ihrer Link-Zeile
beheben können.
Wenn Sie undefined reference
-Fehler bei der
uncompress
- oder
compress
-Funktion erhalten, fügen Sie
-lz
als
LETZTES zu Ihrer Link-Zeile
hinzu und versuchen Sie es noch einmal!
Wenn Sie undefined reference
-Fehler bei
Funktionen erhalten, die es auf Ihrem System geben sollte, wie
connect
, sehen Sie in der Handbuch-Seite
(ManPage) für die fragliche Funktion nach, welche Bibliotheken
Sie zur Link-Zeile hinzufügen sollten!
Wenn Sie undefined reference
-Fehler bei
Funktionen erhalten, die es auf Ihrem System nicht gibt, wie
folgenden:
mf_format.o(.text+0x201): undefined reference to `__lxstat'
Heißt das üblicherweise, dass Ihre Bibliothek auf einem System kompiliert wurde, das nicht 100% kompatibel zu Ihrem System ist. In diesem Fall sollten Sie die letzte MySQL-Quelldistribution herunter laden und sie selbst kompilieren. See Abschnitt 3.3, „Installation der Quelldistribution“.
Wenn Sie versuchen, ein Programm laufen zu lassen und Fehler
für unreferenzierte Symbole erhalten, die mit
mysql_
anfangen, oder den Fehler, dass die
mysqlclient
-Bibliothek nicht gefunden werden
kann, heißt das, dass Ihr System die gemeinsam genutzte
libmysqlclient.so
-Bibliothek nicht findet.
Das Problem beheben Sie, indem Sie Ihr System anweisen, dort nach gemeinsam genutzten Bibliotheken zu suchen, wo sich die Bibliothek befindet, mit einer der folgenden Methoden:
Fügen Sie den Pfad zum Verzeichnis, in dem Sie
libmysqlclient.so
haben, der
LD_LIBRARY_PATH
-Umgebungsvariablen hinzu.
Fügen Sie den Pfad zum Verzeichnis, in dem Sie
libmysqlclient.so
haben, der
LD_LIBRARY
-Umgebungsvariablen hinzu.
Kopieren Sie libmysqlclient.so
an eine
Stelle, die von Ihrem System durchsucht wird, wie
/lib
, und aktualisieren Sie die
Informationen über gemeinsam genutzte Bibliotheken, indem
Sie ldconfig
ausführen.
Eine weitere Möglichkeit, dieses Problem zu lösen, besteht
darin, Ihr Programm statisch mit -static
zu
linken oder die dynamischen MySQL-Bibliotheken zu entfernen,
bevor Sie Ihren Code linken. Im letzteren Fall sollten Sie
sicherstellen, dass keine anderen Programme die dynamischen
Bibliotheken benutzen!
Der MySQL-Server mysqld
kann von jedem
beliebigen Benutzer gestartet werden und unter diesem laufen.
Damit mysqld
als Unix-Benutzer
benutzername
läuft, müssen Sie folgendes
tun:
Halten Sie den Server an, falls er läuft (benutzen Sie
mysqladmin shutdown
).
Ändern Sie die Datenbankverzeichnisse und Dateien so, dass
benutzername
die Berechtigungen zum Lesen
und Schreiben von Dateien darin hat (das müssen Sie
eventuell als Unix-root
-Benutzer machen):
shell> chown -R benutzername /pfad/zu/mysql/datadir
Wenn Verzeichnisse oder Dateien im MySQL-Daten-Verzeichnis
symbolische Links sind, müssen Sie auch diesen
Verknüpfungen folgen und die Verzeichnisse und Dateien, auf
die sie zeigen, ändern. chown -R
kann
SymLinks für Sie folgen.
Starten Sie den Server als Benutzer
benutzername
oder, wenn Sie MySQL-Version
3.22 oder später benutzen, starten Sie
mysqld
als
Unix-root
-Benutzer und benutzen Sie die
--user=benutzername
-Option.
mysqld
schaltet um und läuft dann unter
Unix-Benutzer benutzername
, bevor er
irgend welche Verbindungen annimmt.
Um den Server automatisch beim Hochfahren des Systems unter
dem angegebenen Benutzernamen zu starten, fügen Sie zur
[mysqld]
-Gruppe der
/etc/my.cnf
-Optionendatei oder der
my.cnf
-Optionendatei im
Datenverzeichnis des Servers eine
user
-Zeile hinzu, die den Benutzernamen
angibt. Beispiel:
[mysqld] user=benutzername
Nunmehr sollte Ihr mysqld
-Prozess korrekt
unter dem Unix-Benutzer benutzername
laufen.
Dennoch hat sich eins nicht geändert: Die Inhalte der
Berechtigungstabellen. Vorgabemäßig (direkt nach dem
Laufenlassen des Skripts mysql_install_db
,
das die Berechtigungstabellen installiert), ist der
MySQL-Benutzer root
der einzige Benutzer mit
Zugriffsrechten auf die mysql
-Datenbank. Er
ist auch der einzige, der Datenbanken erzeugen und löschen
kann. Wenn Sie diese Berechtigungen nicht geändert haben, sind
sie noch gültig. Das sollte Sie nicht davon abhalten, auf MySQL
als der MySQL-root
-Benutzer zuzugreifen, wenn
Sie als ein anderer Unix-Benutzer als root
eingeloggt sind. Geben Sie einfach für Client-Programme die
-u root
-Option an.
Beachten Sie, dass der Zugriff auf MySQL als
root
(indem Sie -u root
auf der Kommandozeile eingeben) nichts
damit zu tun hat, dass Sie MySQL als
Unix-root
-Benutzer laufen lassen oder als
irgend ein anderer Unix-Benutzer. Die Zugriffsberechtigungen und
Benutzernamen von MySQL sind komplett unterschiedlich von den
Unix-Benutzernamen. Die einzige Verbindung mit
Unix-Benutzernamen besteht darin, dass ein Client versuchen
wird, sich mit Ihrem Unix-Login-Namen als MySQL-Benutzernamen zu
verbinden, wenn Sie beim Aufruf eines Client-Programms keine
-u
-Option angeben.
Wenn Ihre Unix-Box selbst nicht abgesichert ist, sollten Sie
zumindest ein Passwort für den
MySQL-root
-Benutzer in den
Berechtigungstabellen angeben. Ansonsten kann jeder beliebige
Benutzer mit einem Konto auf der Maschine mysql -u root
datenbank
eingeben und tun, was er will.
Wenn Sie Probleme mit Dateirechten haben, wenn
mysql
zum Beispiel folgende Fehlermeldung
beim Erzeugen einer Tabelle ausgibt:
Error: Can't find file: 'pfad/mit/dateiname.frm' (Errcode: 13)
Kann es sein, dass die Umgebungsvariable
UMASK
falsch gesetzt ist, wenn
mysqld
startet. Der vorgabemäßige
umask-Wert ist 0660
. Sie können dieses
Verhalten ändern, indem Sie safe_mysqld
wie
folgt starten:
shell>UMASK=384 # = 600 in oktal
shell>export UMASK
shell>/pfad/zu/safe_mysqld &
Vorgabemäßig erzeugt MySQL Datenbank- und
RAID
-Verzeichnisse mit dem Berechtigungstyp
0700. Dieses Verhalten können Sie durch Setzen der
UMASK_DIR
-Variablen ändern. Wenn Sie diese
setzen, werden neue Verzeichnisse mit kombiniertem
UMASK
und UMASK_DIR
erzeugt. Wenn Sie zum Beispiel Gruppenzugriff auf alle neuen
Verzeichnisse geben wollen, können Sie folgendes tun:
shell>UMASK_DIR=504 # = 770 in oktal
shell>export UMASK_DIR
shell>/pfad/zu/safe_mysqld &
Ab MySQL-Version 3.23.25 nimmt MySQL an, dass die Werte für
UMASK
und UMASK_DIR
in
oktal angegeben sind, wenn sie mit einer 0 anfangen.
Alle MySQL-Versionen werden auf vielen Plattformen getestet, bevor sie herausgegeben werden. Das heißt nicht, dass es keinerlei Bugs in MySQL gibt, aber es heißt, dass, wenn es Bugs gibt, diese sehr wenige und schwer zu finden sind. Wenn Sie ein Problem haben, ist es immer hilfreich herauszufinden, was Ihr System zum Absturz bringt, weil Sie dann viel bessere Chancen haben, es schnell zu beheben.
Zunächst sollten Sie versuchen herauszufinden, ob das Problem
darin besteht, dass Ihr mysqld
-Daemon stirbt,
oder ob Sie ein Problem mit Ihrem Client haben. Sie können
herausfinden, seit wann Ihr mysqld
-Server
hochgefahren ist, indem Sie mysqladmin
version
ausführen. Wenn mysqld
gestorben ist, finden Sie den Grund hierfür womöglich in der
Datei
mysql-daten-verzeichnis/`hostname`.err
. See
Abschnitt 5.9.1, „Die Fehler-Log-Datei“.
Viele Abstürze von MySQL werden durch beschädigte Index- oder
Daten-Dateien verursacht. MySQL aktualisiert die Daten auf
Platte mit dem write()
Systemaufruf, nach
jedem SQL-Statement und bevor der Client über das Ergebnis
unterrichtet wird. (Das gilt nicht, wenn Sie mit
delayed_key_writes
fahren, denn in diesem
Fall werden nur die Daten geschrieben.) Das bedeutet, dass die
Daten sicher sind, selbst wenn mysqld
abstürzt, weil das Betriebssystem sicherstellt, dass die nicht
von MySQL zurückgeschriebenen Daten (flush) auf Platte
zurückgeschrieben werden. Sie können MySQL zwingen, alles nach
jedem SQL-Befehl auf Platte zurückzusynchronisieren, indem Sie
mysqld
mit --flush
starten.
Das Gesagte bedeutet, dass Sie normalerweise keine beschädigten Tabellen erhalten sollten, ausser in folgenden Fällen:
Jemand oder etwas killte mysqld
oder die
Maschine mitten während einer Aktualisierung.
Sie haben einen Bug in mysqld
gefunden,
der dazu führte, dass er mitten während einer
Aktualisierung starb.
Jemand manipuliert die Daten- / Index-Dateien ausserhalb von mysqld, ohne die Tabelle korrekt zu sperren.
Wenn Sie viele mysqld
-Server auf
denselben Daten auf einem System laufen lassen, das
Dateisystem-Sperren nicht gut unterstützt (das wird
normalerweise vom lockd
-Daemon
gehandhabt) oder wenn Sie mehrere Server mit
--skip-locking
fahren.
Wenn Sie eine beschädigte Index- / Daten-Datei haben, die
sehr falsche Daten enthält, die mysqld
durcheinander brachten.
Sie haben einen Bug im Datenspeicher-Code gefunden. Das ist
nicht sehr wahrscheinlich, aber zumindest möglich. In
diesem Fall können Sie versuchen, den Dateityp auf einen
anderen Datenbank-Handler umzustellen, indem Sie
ALTER TABLE
auf eine reparierte Kopie der
Tabelle anwenden!
Weil es sehr schwierig ist herauszufinden, warum etwas abstürzt, versuchen Sie zuerst herauszufinden, ob Dinge, die bei anderen funktionieren, bei Ihnen abstürzen, oder ob das nicht der Fall ist. Versuchen Sie bitte folgendes:
Fahren Sie den mysqld
-Daemon mit
mysqladmin shutdown
herunter und führen
Sie myisamchk --silent --force */*.MYI
auf alle Tabellen aus. Starten Sie den
mysqld
-Daemon erneut. Das stellt sicher,
dass Sie von einem sauberen Ausgangszustand aus fahren. See
Kapitel 5, MySQL-Datenbankadministration.
Benutzen Sie mysqld --log
und versuchen
Sie den Informationen im Log zu entnehmen, ob eine bestimmte
Anfrage den Server killt oder nicht. Etwa 95% aller Bugs
beziehen sich auf eine bestimmte Anfrage! Normalerweise ist
das eine der letzten Anfragen in der Log-Datei, direkt bevor
MySQL neu startete. See Abschnitt 5.9.2, „Die allgemeine Anfragen-Log-Datei“. Wenn
Sie MySQL wiederholt mit einer der Anfragen killen, selbst
wenn Sie alle Tabellen direkt vor der Ausführung der
Anfrage überprüft haben, haben Sie den Bug eingegrenzt und
sollten dafür einen Bug-Bericht schreiben! See
Abschnitt 2.6.2.3, „Wie man Bugs oder Probleme berichtet“.
Versuchen Sie, einen Testfall herzustellen, den wir zur Reproduzierung des Problems verwenden können. See Abschnitt D.1.6, „Einen Testfall herstellen, wenn Sie Tabellenbeschädigung feststellen“.
Versuchen Sie, die beigefügten mysql-test test und
MySQL-Benchmarks laufen zu lassen. See
Abschnitt 10.3.2, „MySQL-Test-Suite“. Sie können MySQL recht
gut prüfen. Sie können den Benchmarks auch selbst Code
hinzufügen, der Ihre Applikation simuliert! Die Benchmarks
finden sich im bench
-Verzeichnis in der
Quelldistribution oder bei einer Binärdistribution im
sql-bench
-Verzeichnis unter Ihrem
MySQL-Installationsverzeichnis.
Probieren Sie fork_test.pl
und
fork2_test.pl
.
Wenn Sie MySQL zum Debuggen konfigurieren, ist es wesentlich
einfacher, Informationen über mögliche Fehler zu erhalten,
wenn etwas schief geht. Konfigurieren Sie MySQL mit der
--with-debug
-Option oder mit der
--with-debug=full
-Option für
configure
neu und kompilieren Sie neu.
See Abschnitt D.1, „Einen MySQL-Server debuggen“.
Wenn MySQL zum Debuggen konfiguriert wird, wird ein sicherer Speicher-Zuweiser (Memory Allocator) hinzugefügt, der einige Fehler finden kann. Ausserdem erfolgen etliche Ausgaben über das, was gerade geschieht.
Haben Sie die neuesten Patches für Ihr Betriebssystem installiert?
Benutzen Sie die --skip-locking
-Option für
mysqld
. Auf manchen Systemen arbeitet der
lockd
-Sperrmanager nicht korrekt. Die
--skip-locking
-Option weist
mysqld
an, keine externen Sperren zu
benutzen. (Das heißt, dass Sie nicht zwei
mysqld
-Server auf denselben Daten laufen
lassen können und dass Sie vorsichtig sein müssen, wenn
Sie myisamchk
benutzen, aber es kann
aufschlussreich sein, die Option testweise zu benutzen.)
Haben Sie mysqladmin -u root processlist
ausprobiert, wenn mysqld
zu laufen
scheint, aber nicht antwortet? Manchmal ist
mysqld
nicht komatös, obwohl es so
aussieht. Das Problem kann darin bestehen, dass alle
Verbindungen in Benutzung sind, oder es kann ein internes
Sperrproblem vorliegen. mysqladmin
processlist
ist üblicherweise in der Lage, in
solchen Fällen eine Verbindung aufzubauen und kann
nützliche Informationen über die momentane Anzahl von
Verbindungen und ihren Status liefern.
Lassen Sie den Befehl mysqladmin -i 5
status
oder mysqladmin -i 5 -r
status
in einem separaten Fenster laufen, um
statistische Informationen auszugeben, während Sie Ihre
anderen Anfragen laufen lassen.
Versuchen Sie folgendes:
Starten Sie mysqld
von
gdb
aus (oder in einem anderen
Debugger). See Abschnitt D.1.3, „mysqld unter gdb debuggen“.
Lassen Sie Ihre Test-Skripts laufen.
Geben Sie die Ablaufverfolgung (Backtrace) und die
lokalen Variablen der untersten 3 Ebenen aus. In gdb
können Sie das mit folgenden Befehle tun, wenn
mysqld
innerhalb von gdb abgestürzt
ist:
backtrace info local up info local up info local
Mit gdb können Sie auch untersuchen, welchen Thread es
gibt (mit info thread
und zu einem
speziellen Thread umschalten (mit thread
#
, wobei #
die
Thread-Kennung ist).
Versuchen Sie, Ihre Applikation mit einem Perl-Skript zu simulieren, um MySQL zu zwingen, abzustürzen oder fehlerhaftes Verhalten an den Tag zu legen.
Senden Sie einen normalen Bug-Bericht. See Abschnitt 2.6.2.3, „Wie man Bugs oder Probleme berichtet“. Geben Sie mehr Details an als üblich. Weil MySQL bei vielen Leuten funktioniert, kann es sein, dass der Absturz das Ergebnis von etwas ist, das nur auf Ihrem Computer existiert (beispielsweise ein Fehler, der aus Ihren besonderen Systembibliotheken resultiert).
Wenn Sie ein Problem mit Tabellen haben, die Zeilen
dynamischer Länge enthalten, und Sie nicht
BLOB/TEXT
-Spalten benutzen (sondern nur
VARCHAR
-Spalten), können Sie versuchen,
alle VARCHAR
- in
CHAR
-Spalten umzuwandeln, indem Sie
ALTER TABLE
verwenden. Das erzwingt, dass
MySQL Zeilen fester Länge verwendet. Zeilen fester Länge
benötigen etwas mehr Platz, sind aber fehlertoleranter
gegenüber Beschädigungen!
Der aktuelle Code mit dynamischen Zeilen ist bei MySQL AB seit mindestens drei Jahren ohne jedes Problem in Benutzung, aber naturgemäß sind Zeilen dynamischer Länge fehleranfälliger. Daher kann es eine gute Idee sein, das oben Gesagte auszuprobieren.
Wenn Sie das root
-Benutzerpasswort für MySQL
vergessen haben, können Sie es mit folgender Prozedur
wiederherstellen:
Fahren Sie den mysqld
-Server durch Senden
von kill
(nicht kill
-9
) an den mysqld
-Server
herunter. Die Prozess-Kennung (PID) wird in einer
.pid
-Datei gespeichert, die sich
normalerweise im MySQL-Datenbank-Verzeichnis befindet:
kill `cat /mysql-daten-verzeichnis/hostname.pid`
Hierfür müssen Sie entweder der
Unix-root
-Benutzer sein oder derselbe
Benutzer, unter dem der Server läuft.
Starten Sie mysqld
mit der
--skip-grant-tables
-Option neu.
Verbinden Sie sich mit dem mysqld
-Server
mit mysql -h hostname mysql
und ändern
Sie das Passwort mit einem GRANT
-Befehl.
See Abschnitt 5.3.1, „GRANT
- und REVOKE
-Syntax“. Sie können dasselbe auch mit
mysqladmin -h hostname -u benutzer password
'neues_passwort'
machen.
Laden Sie die Berechtigungstabellen neu mit
mysqladmin -h hostname flush-privileges
oder mit dem SQL-Befehl FLUSH PRIVILEGES
.
Beachten Sie, dass nach dem Start von mysqld
mit --skip-grant-tables
jede Benutzung von
GRANT
-Befehlen zu einem Unknown
command
-Fehler führt, bis Sie FLUSH
PRIVILEGES
ausgeführt haben.
Wenn etwas hinsichtlich der Festplatte passiert, tut MySQL folgendes:
Er prüft einmal pro Minute, um festzustellen, ob es genug Platz gibt, um die aktuelle Zeile zu schreiben oder nicht. Wenn genug Platz vorhanden ist, wird fortgefahren, als sei nichts geschehen.
Alle 6 Minuten schreibt er einen Eintrag in die Log-Datei mit einer Warnung wegen voller Festplatte.
Um das Problem abzumildern, können Sie folgende Aktionen unternehmen:
Um einfach weiterzumachen, müssen Sie lediglich genug Festplattenplatz freigeben, damit alle Datensätze eingefügt werden können.
Um den Thread abzubrechen, müssen Sie mysqladmin
kill
an den Thread senden. Der Thread wird beim
nächsten Mal, wenn er die Festplatte prüft (in 1 Minute)
abgebrochen.
Beachten Sie, dass eventuell ein anderer Thread auf die Tabelle wartet, die den Zustand ``Platte voll'' verursachte. Wenn Sie mehrere ``gesperrte'' Threads haben, kann es sein, dass Sie einen Thread killen, der wegen ``Platte voll'' wartet, dass dafür aber ein anderer Thread weitermacht.
Ausnahmen zum obigen Verhalten treten bei der Benutzung von
REPAIR
oder OPTIMIZE
auf,
oder wenn die Indexe nach einem LOAD DATA
INFILE
- oder einem ALTER
TABLE
-Statement im Stapel erzeugt werden.
Alle obigen Befehle benutzen eventuell große temporäre
Dateien, die - sich selbst überlassen - für den Rest des
Systems große Probleme verursachen können. Wenn MySQL ein
``Platte voll'' erhält, während irgend eine der obigen
Operationen ausgeführt wird, entfernt er die großen
temporären Dateien und markiert die Tabelle als beschädigt
(ausser bei ALTER TABLE
, wobei die alte
Tabelle unverändert gelassen wird).
MySQL benutzt den Wert der
TMPDIR
-Umgebungsvariablen als Pfadnamen des
Verzeichnisses, in dem temporäre Dateien gespeichert werden.
Wenn Sie TMPDIR
nicht gesetzt haben, benutzt
MySQL die System-Vorgabe, die normalerweise
/tmp
oder /usr/tmp
ist. Wenn das Dateisystem, das Ihr Verzeichnis für temporäre
Dateien enthält, zu klein ist, sollten Sie
safe_mysqld
editieren, um
TMPDIR
so zu setzen, dass sie auf ein
Verzeichnis in einem Dateisystem zeigt, wo Sie genug Platz
haben! Sie können das temporäre Verzeichnis auch mit der
--tmpdir
-Option für mysqld
setzen.
MySQL erzeugt alle temporären Dateien als versteckte Dateien.
Das stellt sicher, dass die temporären Dateien entfernt werden,
wenn mysqld
beendet wird. Der Nachteil
versteckter Dateien ist, dass Sie eine große temporäre Datei
nicht sehen, die das Dateisystem auffüllt, in dem sich das
Verzeichnis für temporäre Dateien befindet.
Zum Sortieren (ORDER BY
oder GROUP
BY
) benutzt MySQL normalerweise ein oder zwei
temporäre Dateien. Der maximal benötigte Speicherplatz ist:
(laenge_dessen_was_sortiert_wird + groesse_von(datenbank_zeiger)) * anzahl_uebereinstimmender_zeilen * 2
groesse_von(datenbank_zeiger)
ist
üblicherweise 4, kann in Zukunft aber für wirklich große
Tabellen anwachsen.
Bei einigen SELECT
-Anfragen erzeugt MySQL
zusätzliche temporäre SQL-Tabellen. Diese sind nicht versteckt
und haben Namen der Form SQL_*
.
ALTER TABLE
erzeugt eine temporäre Tabelle
im selben Verzeichnis, in dem sich die Original-Tabelle
befindet.
Wenn Sie Probleme damit haben, dass jeder beliebige den
MySQL-Kommunikations-Socket /tmp/mysql.sock
löschen kann, können Sie unter den meisten Versionen von Unix
Ihr /tmp
-Dateisystem schützen, indem Sie
darauf das sticky
Bit setzen. Loggen Sie sich
als root
ein und tun Sie folgendes:
shell> chmod +t /tmp
Das schützt Ihr /tmp
-Dateisystem, so dass
Dateien nur von ihren Besitzern oder dem Superuser
(root
) gelöscht werden können.
Sie können überprüfen, ob das sticky
Bit
gesetzt ist, indem Sie ls -ld /tmp
ausführen. Wenn das letzte Berechtigungsbit
t
ist, ist das Bit gesetzt.
Sie können den Speicherort ändern, den MySQL benutzt, um die Socket-Datei Socket-Datei abzulegen, indem Sie eine der folgenden Prozeduren ausführen:
Geben Sie den Pfad in einer globalen oder lokalen
Optionsdatei an. Beispielsweise können Sie in
/etc/my.cnf
eintragen:
[client] socket=pfad-fuer-socket-datei [mysqld] socket=pfad-fuer-socket-datei
Geben Sie den Pfad auf der Kommandozeile für
safe_mysqld
und die meisten Clients mit
der --socket=pfad-fuer-socket-datei
-Option
an.
Geben Sie den Pfad zum Socket in der
MYSQL_UNIX_PORT
-Umgebungsvariablen an.
variable.
Definieren Sie den Pfad mit der
configure
-Option
--with-unix-socket-path=pfad-fuer-socket-datei
.
See Abschnitt 3.3.3, „Typische configure
-Optionen“.
Mit folgendem Befehl können Sie testen, ob der Socket funktioniert:
shell> mysqladmin --socket=/pfad/zu/socket version
Wenn es Probleme damit gibt, dass SELECT
NOW()
Werte in GMT (Greenwich Mean Time) zurückgibt
und nicht in Ihrer lokalen Zeit, müssen Sie die
TZ
-Umgebungsvariable auf Ihre aktuelle
Zeitzone setzen. Das sollte für die Umgebung gemacht werden, in
der der Server läuft, zum Beispiel in
safe_mysqld
oder
mysql.server
. See
Anhang E, Umgebungsvariablen.
Vorgabemäßig sind MySQL-Suchen unabhängig von der verwendeten
Groß-/Kleinschreibung (obwohl es einige Zeichensätze gibt, die
nie unabhängig von der verwendeten Groß-/Kleinschreibung sind,
wie tschechisch
). Wenn Sie daher mit
spalten_name LIKE 'a%'
suchen, erhalten Sie
alle Spaltenwerte, die mit A
oder
a
anfangen. Wenn Sie die Suche abhängig von
der verwendeten Groß-/Kleinschreibung machen wollen, verwenden
Sie etwas wie INSTR(spalten_name, "A")=1
, um
ein Präfix zu überprüfen, oder benutzen Sie
STRCMP(spalten_name, "A") = 0
, wenn der
Spaltenwert exakt "A"
sein muss.
Einfache Vergleichsoperationen (>=, >, = , < ,
<=
, Sortieren und Gruppieren) basieren auf dem
``Sortierwert'' jedes Zeichens. Buchstaben mit demselben
Sortierwert (wie E, e und é) werden als dasselbe Zeichen
behandelt!
In älteren MySQL-Versionen wurden
LIKE
-Vergleiche mit dem Großschreibungswert
jedes Zeichens durchgeführt (E == e, aber E <> é). In
neueren MySQL-Versionen funktioniert LIKE
genau wie die anderen Vergleichsoperatoren.
Wenn Sie wollen, dass eine Spalte immer abhängig von der
verwendeten Groß-/Kleinschreibung behandelt wird, deklarieren
Sie sie als BINARY
. See
Abschnitt 7.5.3, „CREATE TABLE
-Syntax“.
Wenn Sie chinesische Daten in der so genannten Big5-Kodierung
verwenden, sollten Sie alle Zeichenspalten
BINARY
machen. Das funktioniert, weil die
Sortierreihenfolge von Big5-Zeichen auf der Reihenfolge von
ASCII-Codes basiert.
Das Format eines DATE
-Werts ist
'YYYY-MM-DD'
. Gemäß ANSI-SQL ist kein
anderes Format zulässig. Sie sollten dieses Format in
UPDATE
-Ausdrücken und in der WHERE-Klausel
von SELECT
-Statements benutzen. Beispiel:
mysql> SELECT * FROM tabelle WHERE date >= '1997-05-05';
Aus Gründen der Annehmlichkeit konvertiert MySQL automatisch
ein Datum in eine Zahl, wenn das Datum in einem numerischen
Zusammenhang benutzt wird (und umgekehrt). MySQL unterstützt
ausserdem ein ``entspanntes'' Zeichenkettenformat beim
Aktualisieren und in einer WHERE
-Klausel, die
ein Datum mit einer TIMESTAMP
-,
DATE
- oder einer
DATETIME
-Spalte vergleicht. (Entspannt heißt
hierbei, dass jedes beliebige Satzzeichen als Trennzeichen
zwischen Bestandteilen benutzt werden darf. Beispielsweise sind
'1998-08-15'
und
'1998#08#15'
äquivalent.) MySQL kann auch
eine Zeichenkette umwandeln, die keine Trennzeichen enthält
(wie '19980815'
), vorausgesetzt, dass diese
als Datum einen Sinn ergibt.
Das spezielle Datum '0000-00-00'
kann als
'0000-00-00'
gespeichert und abgerufen
werden. Wenn man ein '0000-00-00'
-Datum über
MyODBC benutzt, wird es
automatisch in NULL
umgewandelt
(MyODBC-Version 2.50.12 und
höher), weil ODBC diese Art von Datum nicht handhaben kann.
Weil MySQL die oben genannten Umwandlungen durchführt, funktionieren folgende Statements:
mysql>INSERT INTO tabelle (idate) VALUES (19970505);
mysql>INSERT INTO tabelle (idate) VALUES ('19970505');
mysql>INSERT INTO tabelle (idate) VALUES ('97-05-05');
mysql>INSERT INTO tabelle (idate) VALUES ('1997.05.05');
mysql>INSERT INTO tabelle (idate) VALUES ('1997 05 05');
mysql>INSERT INTO tabelle (idate) VALUES ('0000-00-00');
mysql>SELECT idate FROM tabelle WHERE idate >= '1997-05-05';
mysql>SELECT idate FROM tabelle WHERE idate >= 19970505;
mysql>SELECT mod(idate,100) FROM tabelle WHERE idate >= 19970505;
mysql>SELECT idate FROM tabelle WHERE idate >= '19970505';
Folgendes jedoch funktioniert nicht:
mysql> SELECT idate FROM tabelle WHERE STRCMP(idate,'19970505')=0;
STRCMP()
ist eine Zeichenkettenfunktion,
daher wird idate
in eine Zeichenkette
umgewandelt und ein Zeichenkettenvergleich durchgeführt. MySQL
wandelt '19970505'
nicht in ein Datum um und
führt einen Datumsvergleich durch.
Beachten Sie, dass MySQL nicht prüft, ob ein Datum korrekt ist
oder nicht. Wenn Sie ein falsches Datum wie
'1998-2-31'
speichern, wird das falsche Datum
gespeichert. Wenn das Datum in keinen vernünftigen Wert
umgewandelt werden kann, wird 0
im
DATE
-Feld gespeichert. Das ist hauptsächlich
eine Sache der Geschwindigkeit, und wir sind der Meinung, dass
es Sache der Applikation und nicht des Servers ist,
Datumsangaben zu überprüfen.
Das Konzept des NULL
-Wert ist eine häufige
Quelle der Verwirrung für SQL-Anfänger. Diese denken häufig,
NULL
sei dasselbe wie eine leere Zeichenkette
''
. Das ist nicht der Fall! So sind zum
Beispiel folgende Statements grundverschieden:
mysql>INSERT INTO meine_tabelle (Telefon) VALUES (NULL);
mysql>INSERT INTO meine_tabelle (Telefon) VALUES ("");
Beide Statements fügen einen Wert in die
Telefon
-Spalte ein, aber das erste fügt
einen NULL
-Wert und das zweite eine leere
Zeichenkette ein. Die Bedeutung des ersten ist etwa
``Telefonnummer unbekannt'' und des zweiten ``Keine
Telefonnummer''.
In SQL ist der NULL
-Wert im Vergleich mit
jedem anderen Wert immer UNWAHR (false), selbst im Vergleich mit
NULL
. Ein Ausdruck, der
NULL
enthält, erzeugt immer einen
NULL
-Wert, ausser wenn es in der
Dokumentation der Operatoren und Funktionen, die im Ausdruck
beteiligt sind, anders angegeben ist. Alle Spalten im folgenden
Beispiel geben NULL
zurück:
mysql> SELECT NULL,1+NULL,CONCAT('unsichtbar',NULL);
Wenn Sie nach Spaltenwerten suchen, die NULL
sind, können Sie nicht =NULL
benutzen.
Folgendes Statement gibt keine Zeilen zurück, weil
ausdruck = NULL
für jeden beliebigen
Ausdruck UNWAHR (false) ist:
mysql> SELECT * FROM meine_tabelle WHERE Telefon = NULL;
Um nach NULL
-Werten zu suchen, müssen Sie
IS NULL
benutzen. Folgende Beispiele zeigen,
wie Sie die NULL
-Telefonnummer und die leere
Telefonnummer finden:
mysql>SELECT * FROM meine_tabelle WHERE Telefon IS NULL;
mysql>SELECT * FROM meine_tabelle WHERE Telefon = "";
In MySQL können Sie - wie bei vielen anderen SQL-Servern -
keine Spalten indexieren, die NULL
-Werte
enthalten dürfen. Sie müssen solche Spalten aus NOT
NULL
deklarieren. Sie dürfen in eine indexierte
Spalte keine NULL
-Werte einfügen.
Wenn Sie Daten mit LOAD DATA INFILE
einlesen,
werden leere Spalten mit ''
aktualisiert.
Wenn Sie einen NULL
-Wert in einer Spalte
haben wollen, müssen Sie in der Textdatei \N
benutzen. Unter manchen Umständen kann auch das Literalwort
'NULL'
benutzt werden. See
Abschnitt 7.4.9, „LOAD DATA INFILE
-Syntax“.
Wenn Sie ORDER BY
benutzen, werden
NULL
-Werte zuerst angezeigt. Wenn Sie mit
DESC
in absteigender Reihenfolge sortieren,
werden NULL
-Werte zuletzt angezeigt. Wenn Sie
GROUP BY
benutzen, werden alle
NULL
-Werte als gleich betrachtet.
Um die Handhabung von NULL
zu erleichtern,
können Sie die IS NULL
- und IS NOT
NULL
-Operatoren und die
IFNULL()
-Funktion benutzen.
Bei manchen Spaltentypen werden NULL
-Werte
besonders behandelt. Wenn Sie NULL
in die
erste TIMESTAMP
-Spalte einer Tabelle
einfügen, werden das aktuelle Datum und die aktuelle Zeit
eingefügt. Wenn Sie NULL
in eine
AUTO_INCREMENT
-Spalte einfügen, wird die
nächste Zahl in der Zahlenfolge eingefügt.
Sie können ein Alias verwenden, um auf eine Spalte im
GROUP BY
-, ORDER BY
- oder
HAVING
-Teil zu verweisen. Aliase können auch
verwendet werden, um Spalten bessere Namen zu geben:
SELECT SQRT(a*b) as wurzel FROM tabelle GROUP BY wurzel HAVING wurzel > 0; SELECT id,COUNT(*) AS zaehl FROM tabelle GROUP BY id HAVING zaehl > 0; SELECT id AS "kunden-kennung" FROM tabelle;
Beachten Sie, dass ANSI-SQL verbietet, in einer
WHERE
-Klausel auf ein Alias zu verweisen. Das
liegt daran, dass der Spaltenwert möglicherweise noch nicht
feststeht, wenn der WHERE
-Code ausgeführt
wird. Folgende Anfrage zum Beispiel ist
unzulässig:
SELECT id,COUNT(*) AS zaehl FROM tabelle WHERE zaehl > 0 GROUP BY id;
Das WHERE
-Statement wird ausgeführt, um
festzulegen, welche Zeilen im GROUP BY
-Teil
enthalten sein sollen, während HAVING
benutzt wird, um zu entscheiden, welche Zeilen der Ergebnismenge
benutzt werden sollten.
Weil MySQL keine Sub-Selects oder die Benutzung von mehr als
einer Tabelle im DELETE
-Statement
unterstützt, müssen Sie folgenden Ansatz wählen, um Zeilen
aus zwei verwandten Tabellen zu löschen:
Wählen (SELECT
) Sie die Zeilen auf der
Grundlage einer WHERE
-Bedingung in der
Haupt-Tabelle aus.
Löschen (DELETE
) Sie die Zeilen in der
Haupt-Tabelle auf der Grundlage derselben Bedingung.
Löschen Sie die Zeilen aus der verwandten Tabelle, bei
denen die verwandte Spalte in den ausgewählten Zeilen
vorkommt (DELETE FROM verwandte_tabelle WHERE
verwandte_spalte IN (ausgewaehlte_zeilen)
.
Wenn die Gesamtzahl von Zeichen in der Anfrage mit
verwandte_spalte
mehr als 1.048.576 beträgt
(der Vorgabewert von max_allowed_packet
,
sollten Sie sie in kleinere Teile aufspalten und mehrfache
DELETE
-Statements ausführen. Wahrscheinlich
geht das Löschen (DELETE
) am Schnellsten,
wenn Sie nur 100 bis 1000
verwandte_spalte
-Kennungen pro Anfrage
löschen, wenn verwandte_spalte
ein Index
ist. Wenn verwandte_spalte
kein Index ist,
ist die Geschwindigkeit unabhängig von der Anzahl von
Argumenten in der IN
-Klausel.
Wenn Sie eine komplizierte Anfrage haben, die viele Tabellen hat und keine Zeilen zurückgibt, sollten Sie folgende Prozedur benutzen, um herauszufinden, was bei Ihrer Anfrage falsch ist:
Testen Sie die Anfrage mit EXPLAIN
und
prüfen Sie, ob Sie etwas finden können, das offensichtlich
falsch ist. See Abschnitt 6.2.1, „EXPLAIN
-Syntax (Informationen über ein SELECT
erhalten)“.
Wählen Sie in der WHERE
-Klausel nur die
Felder aus, die benutzt werden.
Entfernen Sie nacheinander Tabelle für Tabelle aus der
Anfrage, bis sie Zeilen zurückgibt. Wenn die Tabellen Groß
sind, ist es eine gute Idee, LIMIT 10
bei
der Anfrage zu benutzen.
Machen Sie ein SELECT
für die Spalte,
die mit einer Zeile hätte übereinstimmen sollen, gegen die
Tabelle, die als letzte aus der Anfrage entfernt wurde.
Wenn Sie FLOAT
- oder
DOUBLE
-Spalten mit Zahlen vergleichen,
die Dezimalstellen haben, können Sie nicht
=
benutzen! Das Problem tritt in den
meisten Computersprachen auf, weil Fließkommawerte keine
exakten Werte sind:
mysql>SELECT * FROM tabelle WHERE float_spalte=3.5;
mysql>SELECT * FROM tabelle WHERE float_spalte between 3.45 und 3.55;
In den meisten Fällen kann dies durch Umwandlung von
FLOAT
in DOUBLE
behoben werden!
Wenn Sie immer noch nicht herausfinden können, was schief
geht, erzeugen Sie einen minimalen Test, der mit
mysql test < anfrage.sql
laufen
gelassen werden kann, um Ihre Probleme aufzuzeigen. Sie
können eine Testdatei mit mysqldump --quick
datenbanktabellen > anfrage.sql
erzeugen.
Öffnen Sie die Datei in einem Editor, entfernen Sie ein
paar Einfügezeilen (wenn es davon zu viele gibt) und fügen
Sie Ihr SELECT--Statement am Ende der Datei an.
Testen Sie, ob es hiermit immer noch das Problem gibt:
shell>mysqladmin create test2
shell>mysql test2 < anfrage.sql
Schicken Sie die Testdatei mittels
mysqlbug
an
<mysql@lists.mysql.com>
.
ALTER TABLE
ändert eine Tabelle zum
aktuellen Zeichensatz. Wenn Sie während ALTER
TABLE
einen Fehler wegen doppelter Schlüsseleinträge
bekommen, liegt das entweder daran, dass die neuen Zeichensätze
auf bei Schlüsseln auf dieselben Werte gemappt sind, oder dass
die Tabelle beschädigt ist, wobei Sie REPAIR
TABLE
auf die Tabelle laufen lassen sollten.
Wenn ALTER TABLE
mit einem Fehler wie folgt
stirbt:
Error on rename of './datenbank/name.frm' to './datenbank/B-a.frm' (Errcode: 17)
Kann das Problem darin bestehen, dass MySQL bei einem
vorhergehenden ALTER TABLE
abgestürzt ist
und es eine alte Tabelle namens A-etwas
oder B-etwas
gibt, die herum liegt. Gehen
Sie in diesem Fall ins MySQL-Daten-Verzeichnis und löschen Sie
alle Dateien, die Namen wie A-
oder
B-
haben. (Statt löschen können Sie sie
auch an eine andere Stelle verschieben.)
ALTER TABLE
funktioniert auf folgenden Weise:
Erzeugt eine neue Tabellen namens A-xxx
mit den angeforderten Änderungen.
Alle Zeilen der alten Tabelle werden nach
A-xxx
kopiert.
Die alte Tabelle wird in B-xxx
umbenannt.
A-xxx
wird in Ihren alten Tabellennamen
umbenannt.
B-xxx
wird gelöscht.
Wenn etwas bei dieser Umbennungsoperation fehlschlägt, versucht
MySQL, die Änderungen rückgängig zu machen. Wenn etwas
Schwerwiegendes schief geht (was natürlich passieren kann),
läßt MySQL eventuell die alte Tabelle als
B-xxx
, aber ein einfaches Umbenennen auf
Systemebene sollte Ihre Daten zurückbringen.
Im großen und Ganzen geht es bei SQL darum, die Applikation vom Daten-Speicherformat zu abstrahieren. Sie sollten immer die Reihenfolge angeben, in der Sie Ihre Daten abrufen wollen. Beispiel:
SELECT spalten_name1, spalten_name2, spalten_name3 FROM tabelle;
Das gibt die Spalten in der Reihenfolge
spalten_name1
,
spalten_name2
,
spalten_name3
zurück, wohingegen:
SELECT spalten_name1, spalten_name3, spalten_name2 FROM tabelle;
die Spalten in der Reihenfolge spalten_name1
,
spalten_name3
,
spalten_name2
zurückgibt.
Sie sollten in einer Applikation
NIE SELECT *
benutzen und die Spalten basierend auf ihrer Position abrufen,
weil die Reihenfolge, in der Spalten zurückgegeben werden, im
Zeitablauf NICHT garantiert
werden kann. Eine einfache Änderung in Ihrer Datenbank kann
dazu führen, dass Ihre Applikation dramatisch scheitert.
Wenn Sie dennoch die Spalten-Reihenfolge ändern wollen, können Sie das wie folgt tun:
Erzeugen Sie eine neue Tabelle mit den Spalten in der richtigen Reihenfolge.
Führen Sie INSERT INTO neue_tabelle SELECT
felder-in-der-reihenfolge-von-neue_tabelle FROM
alte_tabelle
aus.
Löschen Sie alte_tabelle
oder benennen
Sie sie um.
Führen Sie ALTER TABLE neue_tabelle RENAME
alte_tabelle
aus.
Im Folgenden eine Auflistung der Beschränkungen bei
TEMPORARY TABLES
.
Eine temporäre Tabelle kann nur vom Typ
HEAP
, ISAM
oder
MyISAM
sein.
Sie können temporäre Tabellen nicht mehr als einmal in derselben Anfrage benutzen. Folgendes zum Beispiel funktioniert nicht:
select * from temporary_table, temporary_table as t2;
Das soll in Version 4.0 behoben werden.
Sie können kein RENAME
auf eine
TEMPORARY
-Tabelle benutzen. Beachten Sie,
dass ALTER TABLE alter_name RENAME
neuer_name
dagegen funktioniert! Das soll in
Version 4.0 behoben werden.
This is a translation of the MySQL Reference Manual that can be found at dev.mysql.com. The original Reference Manual is in English, and this translation is not necessarily as up to date as the English version.