Les problèmes suivants sont connus, et sont en tête de liste pour être corrigés :
Il n'est pas possible de mélanger UNION
ALL
et UNION DISTINCT
dans la
même requête. Si vous utilisez ALL
pour UNION
alors il faut l'utiliser
partout.
Si un utilisateur a une transaction longue, et qu'un autre
utilisateur efface une table qui est modifiée par la
même transaction, il y a quelques chances que le log
binaire n'enregistre pas la commande DROP
TABLE
avant que la table ne soit utilisée par
la transaction elle-même. Nous envisageons de corriger
cela en version 5.0, en for¸ant DROP
TABLE
a attendre jusqu'à ce que la table ne
soit plus utilisée par la transaction.
Lors de l'insertion d'un grand entier (valeur entre 2^63 et 2^64-1) dans une colonne de type décimal ou chaîne, il sera enregistré comme une valeur négative, car le nombre est considéré comme un entier signé dans ce contexte. Il est prévu de corriger cela en 4.1.
FLUSH TABLES WITH READ LOCK
ne bloque
pas CREATE TABLE
ou
COMMIT
, ce qui peut causer des
problèmes avec la position du log lors d'une sauvegarde
complète des tables et du log binaire.
ANALYZE TABLE
sur une table de type
BDB
, peut rendre la table inutilisable,
dans certains cas, jusqu'au prochain redémarrage de
mysqld
. Lorsque cela survient, vous
rencontrez les erreurs suivantes dans le fichier d'erreur
MySQL :
001207 22:07:56 bdb: log_flush: LSN past current end-of-log
MySQL accepte les parenthèses dans la clause
FROM
, mais les ignore silencieusement.
La raison de l'absence d'erreur est que de nombreux
clients qui génèrent des requêtes, ajoutent les
parenthèses dans la clause FROM
même
si elles sont inutiles.
Concaténer plusieurs RIGHT JOINS
ou
combiner des jointures LEFT
et
RIGHT
dans la même requête ne donnera
pas de résultat correct si MySQL ne génère que des
lignes NULL
pour la table précédent
le LEFT
ou avant la jointure
RIGHT
. Cela sera corrigé en 5.0, en
même temps que le support des parenthèses pour la clause
FROM
.
N'exécutez pas de commande ALTER TABLE
sur une table BDB
sur laquelle vous
avez exécuté des transactions à plusieurs commandes,
jusqu'à ce que ces transactions soient achevées : la
transaction sera probablement ignorée.
ANALYZE TABLE
, OPTIMIZE
TABLE
et REPAIR TABLE
peuvent
causer des problèmes sur les tables avec lesquelles vous
utilisez la commande INSERT DELAYED
.
Faire un LOCK TABLE ...
et
FLUSH TABLES ...
ne vous garantit pas
qu'il n'y a pas une transaction en court sur la table.
Les tables BDB
sont lentes à ouvrir.
Si vous avez de nombreuses tables BDB
dans une base, cela prendra du temps au client
mysql
pour accéder à la base si vous
n'utilisez pas l'option -A
, ou si vous
utilisez la commande rehash
. C'est
particulièrement vrai si vous n'avez pas de cache de
table important.
La réplication utilise un log de niveau requête : le maître écrit les requêtes exécutées dans le log binaire. C'est une méthode de log rapide, compacte et efficace, qui fonctionne à la perfection dans la plupart des situations. Même si nous n'avons jamais vu d'occurrence de ce problème, il est théoriquement possible pour les données du maître et de l'esclave de différer si une requête non-déterministe est utilisée pour modifier les données, c'est à dire si elle est laissé au bon vouloir de l'optimiseur, ce qui n'est pas une bonne pratique même sans la réplication. Par exemple :
Des commandes CREATE ... SELECT
ou
INSERT ... SELECT
qui insèrent
zéro ou NULL
valeurs dans la
colonne AUTO_INCREMENT
.
DELETE
si vous effacez des lignes
dans une table qui a une propriété ON
DELETE CASCADE
.
Les commandes REPLACE ... SELECT
,
INSERT IGNORE ... SELECT
, si vous
avez des clés en double, dans les données
insérées.
IF et seulement si ces requêtes
n'ont pas de clause ORDER BY
, qui
garantisse un ordre déterministe.
Effectivement, par exemple, pour les commandes
INSERT ... SELECT
sans clause
ORDER BY
, le SELECT
peut retourner les lignes dans un ordre différent, ce qui
aura pour résultat de donner des rangs différents et
donnera des numéros d'identifiants différents aux
colonnes auto_increment
), en fonction
des choix fait par les optimiseurs du maître et de
l'esclave. Une requête sera optimisée différemment sur
l'esclave et sur le maître si :
Les fichiers utilisés par les deux requêtes ne sont
pas exactement les mêmes. Par exemple,
OPTIMIZE TABLE
a été exécuté
sur le maître et pas sur l'esclave (pour corriger
cela, depuis MySQL 4.1.1, OPTIMIZE
,
ANALYZE
et
REPAIR
sont aussi écrits dans le
log binaire).
La table est stockées sur un moteur de stockage
différent sur le maître et sur l'esclave : c'est
possible d'utiliser des moteurs de tables différents.
Par exemple, le maître utiliser
InnoDB
et l'esclave MyISAM, car
l'esclave a moins d'espace disque.
Les tailles de buffer MySQL
(key_buffer_size
, etc.) sont
différentes sur le maître et sur l'esclave.
Le maître et l'esclave utilisent des versions différentes de MySQL, et le code de l'optimiseur est différent entre ces versions.
Ce problème peut aussi affecter la restauration de base,
utilisant mysqlbinlog
ou
mysql
.
Le plus simple pour éviter ces problèmes dans tous les
cas est d'ajouter toujours une clause ORDER
BY
aux requêtes non-déterministe, pour
s'assure que les lignes sont traitées dans le même
ordre. Dans le futur, MySQL va ajouter automatiquement une
clause ORDER BY
si nécessaire.
Les problèmes suivants sont connus et seront corrigés en leur temps :
mysqlbinlog
n'efface pas les fichiers
temporaires laissés après une commande LOAD
DATA INFILE
. See Section 8.5, « mysqlbinlog
, Exécuter des requêtes dans le log
binaire ».
Il n'est pas possible de renommer une table temporaire.
Lors de l'utilisation de la fonction
RPAD
, ou de toute autre fonction de
chaîne qui peut ajouter des espaces à droite de la
chaîne, dans une requête qui utilise une table
temporaire pour la résolution, alors toutes les chaînes
verront leurs espaces terminaux être supprimés. Voici un
exemple d'une telle requête :
SELECT RPAD(t1.field1, 50, ' ') AS f2,
RPAD(t2.field2, 50, ' ') AS f1 FROM table1 as t1 LEFT JOIN
table2 AS t2 ON t1.record=t2.joinID ORDER BY
t2.record;
Le résultat final de ceci est que vous ne pourrez pas obtenir les espaces à gauche dans ces chaînes.
Le comportement décrit ci-dessus existe dans toutes les versions de MySQL.
La raison à cela est due au fait que les tables de type HEAP, qui sont utilisées en premier comme table temporaires, ne sont pas capables de gérer des colonnes de type VARCHAR.
Ce comportement sera corrigé dans l'une des versions de la série des 4.1.
A cause de la méthode de stockage des tables de
définitions de fichiers, il n'est pas possible d'utiliser
le caractère 255 (CHAR(255)
) dans les
noms des tables, colonnes ou énumérations. Il est prévu
de corriger de problème dans les versions version 5.1,
lorsque nous aurons établi un nouveau format de
définition des fichiers.
Lorsque vous utilisez la commande SET CHARACTER
SET
, il n'est pas possible d'utiliser les
caractères traduits dans les noms de bases, de tables ou
de colonnes.
Il n'est pas possible d'utiliser _
ou
%
avec la commande
ESCAPE
dans la clause LIKE...
ESCAPE
.
Si vous avez une colonne de type
DECIMAL
avec un nombre stocké dans un
autre format (+01.00, 1.00, 01.00), GROUP
BY
peut considérer ces valeurs comme
différentes.
Lorsque DELETE FROM merge_table
est
utilisé sans la clause WHERE
, elle va
simplement effacer le fichier de la table, et ne pas
effacer les tables associées.
Vous ne pouvez pas compiler le serveur dans un autre
dossier lorsque vous utilisez les
MIT-pthreads
. Comme cela requiert une
modification des MIT-pthreads
, nous ne
corrigerons pas ce problème. See
Section 2.4.5, « Notes relatives aux MIT-pthreads
».
Les valeurs de type BLOB
ne peuvent pas
être utilisées ``correctement'' dans les clauses
GROUP BY
ou ORDER BY
ou DISTINCT
. Seuls, les
max_sort_length
premiers octets (par
défaut, 1024) seront utilisés pour les comparaisons de
BLOB
. Ceci peut être modifié avec
l'option -O max_sort_length
de
mysqld
. Un palliatif à ce problème
est d'utiliser une sous partie de chaîne :
SELECT DISTINCT LEFT(blob,2048) FROM
tbl_name
.
Les calculs sont faits avec des BIGINT
ou DOUBLE
(les deux sont normalement de
64 bits). La précision dépend alors de la fonction
utilisée. La règle générale est que les fonctions de
bits utilisent la précision des
BIGINT
, IF
et
ELT()
utilisent la précision des
BIGINT
ou DOUBLE
, et
les autres utilisent la précision des
DOUBLE
. Il faut donc éviter d'utiliser
les entiers non signés de grande taille, surtout s'ils
dépassent la taille de 63 bits (9223372036854775807) pour
toute autre fonction que les champs de bits ! La version
4.0 gère bien mieux les BIGINT
que la
3.23.
Toutes les colonnes de type chaînes, hormis les
BLOB
et TEXT
, voient
automatiquement leurs caractères blancs finaux
supprimés. Pour le type CHAR
c'est
correct, et c'est considéré comme une fonctionnalité
par la norme ANSI SQL92. Le hic est que pour le serveur
MySQL les colonnes VARCHAR
sont
traitées de la même fa¸on.
Vous ne pouvez avoir que des colonnes de taille 255 pour
les ENUM
et SET
.
Avec les fonctions d'agrégation MIN()
,
MAX()
et compagnie, MySQL compare
actuellement les colonnes de type ENUM
et SET
par leur valeur de chaîne,
plutôt que par leur position relative dans l'ensemble.
safe_mysqld
redirige tous les messages
de mysqld
vers le log
mysqld
. Le problème est que si vous
exécutez mysqladmin refresh
pour
fermer et ouvrir à nouveau l'historique,
stdout
et stderr
sont toujours redirigés vers l'ancien log. Si vous
utilisez --log
, vous devriez éditer
safe_mysqld
pour envoyer les messages
vers 'hostname'.err
au lieu de
'hostname'.log
, de fa¸on à pouvoir
facilement récupérer la place de l'ancien log, en
effa¸ant les vieux, et en exécutant mysqladmin
refresh
.
Dans la commande UPDATE
, les colonnes
sont modifiées de gauche à droite. Si vous faite
référence à une colonne modifiée, vous obtiendrez sa
valeur modifiée, plutôt que sa valeur originale. Par
exemple :
mysql> UPDATE tbl_name SET KEY=KEY+1,KEY=KEY+1;
Cette commande va modifier la colonne
KEY
avec 2
au lieu
de 1
.
Vous ne pouvez pas utiliser les tables temporaires plus d'une fois dans la même requête. Par exemple, cette commande ne fonctionne pas :
mysql> SELECT * FROM temporary_table, temporary_table AS t2;
RENAME
ne fonctionne pas avec les
tables TEMPORARY
, ou les tables
utilisées dans un rassemblement
(MERGE
).
L'optimiseur peut gérer la clause
DISTINCT
différemment si vous utilisez
des colonnes cachées dans une jointure. Dans une
jointure, les colonnes cachées sont comptées comme une
partie du résultat (même si elles ne sont pas
montrées), tandis que dans les requêtes normales, les
colonnes cachées ne participent pas aux
DISTINCT
. Nous allons probablement
modifier ceci dans le futur, pour ne jamais exploiter les
colonnes cachées avec DISTINCT
.
Voici un exemple :
SELECT DISTINCT mp3id FROM band_downloads WHERE userid = 9 ORDER BY id DESC;
et
SELECT DISTINCT band_downloads.mp3id FROM band_downloads,band_mp3 WHERE band_downloads.userid = 9 AND band_mp3.id = band_downloads.mp3id ORDER BY band_downloads.id DESC;
Dans le second cas, MySQL 3.23.x pourrait vous donner deux
lignes identiques dans le résultat (car les lignes
cachées id
diffèrent).
Notez que cela n'arrive que pour les requêtes où vous n'avez pas de colonnes de la clause ORDER BY dans le résultat, ce que vous ne pourriez pas faire en ANSI SQL.
Comme le serveur MySQL vous permet de travailler avec des
tables qui ne supportent pas les transactions, et donc,
l'annulation rollback
, certains
comportements sont différents avec MySQL d'avec d'autres
serveurs SQL. C'est nécessaire pour s'assurer que MySQL
n'a jamais besoin d'annuler une commande SQL. Cela peut
sembler un peu étrange au moment où les colonnes doivent
être vérifiées par l'application, mais cela vous
fournit une accélération notable, à cause
d'optimisations qui ne pourraient pas avoir lieu ailleurs.
Si vous donnez une valeur incorrecte à une colonne, MySQL
va stocker le meilleur code possible
dans la colonne, au lieu d'annuler la transaction :
Si vous essayez de stocker une valeur qui est hors de l'intervalle de validité dans une colonne numérique, MySQL va stocker la plus petite ou la plus grande valeur qu'il connaisse dans cette colonne.
Si vous essayez de stocker une chaîne qui ne commence pas par un chiffre dans une colonne numérique, MySQL va stocker 0.
Si vous essayez de stocker la valeur
NULL
dans une colonne qui n'accepte
pas la valeur NULL
, le serveur
MySQL va stocker 0 ou ''
(chaîne
vide) à la place : ce comportement peut être
modifié avec l'option de compilation
-DDONT_USE_DEFAULT_FIELDS
).
MySQL vous autorise le stockage de dates erronées
dans les colonnes de type DATE
et
DATETIME
(comme 2000-02-31 ou
2000-02-00). L'idée est que ce n'est pas au serveur
SQL de faire le travail de validation. Si MySQL peut
stocker une date, et relire exactement cette date,
alors MySQL va stocker cette date. Si la date est
totalement fausse (hors de l'intervalle de validité
du serveur), la valeur spéciale
0000-00-00
sera utilisée.
Si vous utilisez une valeur non supportée avec une
colonne de type ENUM
, la valeur
stockée sera la chaîne vide, de valeur numérique 0.
Si vous utilisez une valeur invalide dans une colonne
de type SET
, la valeur sera
ignorée.
Si vous exécutez une PROCEDURE
sur une
requête qui retourne un résultat vide, dans certains
cas, PROCEDURE
ne transformera pas les
colonnes.
La création de table de type MERGE
ne
vérifie pas si les tables sous-jacentes sont de type
compatible.
Le serveur MySQL ne supporte pas encore les valeurs Server
NaN
, -Inf
et
Inf
pour les doubles. Utiliser ces
valeurs générera des problèmes lorsque vous essayerez
d'exporter et d'importer des données. Comme solution
temporaire, vous pouvez remplacer NaN
par NULL
(si possible) et
-Inf
et Inf
par les
valeurs maximales possibles des colonnes
double
.
Si vous utilisez la commande ALTER
TABLE
pour ajouter un index de type
UNIQUE
à un table utilisée dans un
rassemblement de tables MERGE
, puis que
vous utilisez ALTER TABLE
pour ajouter
un index normal à la table MERGE
,
l'ordre des clés sera différent pour les tables s'il y
avait déjà une ancienne clé qui n'était pas unique.
Ceci est dû au fait que ALTER TABLE
place les clés UNIQUE
avant les clés
normales, pour être capable de détecter les clés
doublons plus vite.
Les bogues suivants sont connus dans les anciennes versions de MySQL :
Vous pouvez obtenir un thread gelé si vous utilisez la
commande DROP TABLE
sur une table qui
fait partie des tables verrouillées par LOCK
TABLES
.
Dans les cas suivants, vous pouvez obtenir un crash :
Le gestionnaire d'insertions retardées a déjà des insertions en attente pour une table.
LOCK table
avec
WRITE
.
FLUSH TABLES
.
Pour les versions de MySQL avant la 3.23.2, une commande
UPDATE
qui modifiait une clé avec la
clause WHERE
sur la même clé, pouvait
échouer car la même clé était utilisée pour
rechercher les lignes et la même ligne pouvait être
trouvée plusieurs fois :
UPDATE tbl_name SET KEY=KEY+1 WHERE KEY > 100;
Un palliatif est :
MySQL> UPDATE tbl_name SET KEY=KEY+1 WHERE KEY+0 > 100;
Cela fonctionnera, car MySQL ne va pas utiliser d'index
sur une expression dans la clause
WHERE
.
Avant la version 3.23 de MySQL, tous les types numériques étaient traités comme des champs à virgule fixe. Cela signifie que vous deviez spécifier le nombre de décimales que le champ devait avoir. Tous les résultats étaient retournés avec le nombre correct de décimales.
Pour les bogues spécifiques aux systèmes d'exploitation, voyez la section sur la compilation et le port. See Section 2.4, « Installation de MySQL avec une distribution source ». See Annexe D, Port vers d'autres systèmes.
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.