it-swarm.dev

Étrange erreur "lecture seule" de MySQL

Je rencontre une étrange erreur MySQL, apparemment liée à l'indicateur read-only de la base de données. Une application Web utilisant MySQL s'exécute sous Debian 7.9. Il fonctionnait bien pendant des semaines, sinon plus, alors que, tout à coup, les tentatives pour accéder au site Web alimenté par l'application ont commencé à produire le message d'erreur suivant sur une page Web vierge:

Erreur: 500 - SQLSTATE [HY000]: Erreur générale: 1290 Le serveur MySQL est s'exécutant avec l'option --read-only afin qu'il ne puisse pas exécuter ceci déclaration

Voici les étapes que j'ai effectuées dans le cadre de mon enquête:

  • trouvé et lu lu des informations pertinentes sur Internet (certains ont indiqué le drapeau read-only de MySQL);
  • sur la base de ce qui précède, a essayé de trouver le drapeau read-only dans la configuration MySQL. file (my.cnf) - n'a pas pu le trouver ici, mais lisez que la valeur par défaut de l'indicateur est OFF quand même;
  • vérifié le système de fichiers pour s'assurer qu'il y avait beaucoup d'espace disque (df -h): Filesystem Size Used Avail Use% Mounted on udev 10M 0 10M 0% /dev tmpfs 3.2G 1.4M 3.2G 1% /run /dev/disk/by-uuid/xxxxxxxxxxxxxxxxx 113G 14G 94G 13% / tmpfs 5.0M 0 5.0M 0% /run/lock tmpfs 7.3G 72K 7.3G 1% /run/shm

  • ran mysqlcheck --all-databases: toutes les tables sont OK;

  • vérifié qu'il y avait beaucoup de RAM disponible sur le serveur (free): total used free shared buffers cached Mem: 32898332 2090268 30808064 0 425436 970348 -/+ buffers/cache: 694484 32203848 Swap: 5105660 0 5105660
  • enfin, j'ai décidé de prendre un "instantané" des processus liés à MySQL (ps ax | grep mysql) pendant l'existence du problème et après une résolution temporaire (redémarrage de la base de données), dans l'espoir de donner aux gens un contexte supplémentaire pour leurs idées. voici les résultats correspondants:

    Problème: 20307 ? S 0:00 /bin/sh /usr/bin/mysqld_safe 20635 ? Sl 0:37 /usr/sbin/mysqld --basedir=/usr --datadir=/var/lib/mysql --plugin-dir=/usr/lib/mysql/plugin --user=mysql --pid-file=/var/run/mysqld/mysqld.pid --socket=/var/run/mysqld/mysqld.sock --port=3306 20636 ? S 0:00 logger -t mysqld -p daemon.error 36427 pts/0 S+ 0:00 grep mysql

    Pas de problème: 36948 pts/0 S 0:00 /bin/sh /usr/bin/mysqld_safe 37275 pts/0 Sl 0:00 /usr/sbin/mysqld --basedir=/usr --datadir=/var/lib/mysql --plugin-dir=/usr/lib/mysql/plugin --user=mysql --pid-file=/var/run/mysqld/mysqld.pid --socket=/var/run/mysqld/mysqld.sock --port=3306 37276 pts/0 S 0:00 logger -t mysqld -p daemon.error 38313 pts/0 S+ 0:00 grep mysql

METTRE À JOUR:

Je viens juste de connaître à nouveau le problème et j'ai décidé de vérifier si le drapeau global en lecture seule est réglé sur OFF ou non, en supposant que ce soit le cas. Mon hypothèse a confirmé:

mysql> SELECT @@global.read_only;
+--------------------+
| @@global.read_only |
+--------------------+
|                  1 |
+--------------------+
1 row in set (0.00 sec)

Malgré la valeur par défaut de OFF, étant donné qu’il est écrasé par un processus quelconque du système, je devrais définir le drapeau en lecture seule sur OFF de manière explicite et permanente via le fichier de configuration MySQL. Rendra compte des résultats plus tard dans une réponse.

7
Aleksandr Blekh

Selon moi, votre base de données est configurée en lecture seule pour deux raisons principales:

1) MySQL se met en lecture seule

Je ne suis pas sûr de ce qui pourrait amener MySQL à aller en lecture seule, peut-être des problèmes de disque ou une corruption de la base de données? Dans tous les cas, je m'attendrais à ce que quelque chose apparaisse dans les journaux, vérifiez donc les journaux de MySQL (et du système).

2) Un client met la base de données en lecture seule

Les clients se connectant à MySQL peuvent définir la lecture de la base de données uniquement à l'aide de la commande suivante:

SET GLOBAL read_only = ON;

toutefois, pour ce faire, l'utilisateur doit disposer des privilèges SUPER. Cette autorisation ne devrait pas être nécessaire pour les sites Web, les applications, etc. qui utilisent MySQL. Conservez-la uniquement pour un compte administrateur que vous utilisez pour administrer la base de données.

Verrouillez les autorisations dont dispose chaque utilisateur pour qu'il ne dispose que de la possibilité d'effectuer les tâches nécessaires sur les bases de données/tables applicables. Si vous utilisez des applications prêtes à l'emploi, elles doivent être accompagnées d'instructions précisant les autorisations requises (par exemple, SELECT, INSERT, DELETE, UPDATE).

9
Eborbob

Si vous êtes dans AWS Aurora, vous pouvez accéder à l'instance de réplica en lecture seule , vous devez donc utiliser le point de terminaison DB Cluster.

2
sashoalm

Je viens de rencontrer la même erreur et je l'ai corrigé en me connectant au nom d'hôte du serveur mysql, par opposition à l'adresse IP. Je ne sais pas pourquoi cela a résolu le problème, mais c'est ce qui s'est passé. juste FYI

1
Chris Hall

Sur la base des commentaires de ma question (merci tout spécialement à @Eborbob) et de ma mise à jour, j'ai estimé qu'un processus du système réinitialise l'indicateur read-only sur ON (1), ce qui semble provoquer le problème et rendre le site Web inaccessible. Afin de résoudre le problème et de résoudre ce problème persistent après le redémarrage du logiciel et du serveur, j'ai décidé de mettre à jour le fichier de configuration MySQL my.cnf et de redémarrer le serveur de base de données.

Après avoir effectué la mise à jour appropriée (dans mon cas, ajout) au fichier de configuration

read_only=0

vérifions que le drapeau est bien défini sur OFF (0):

# mysql
mysql> SELECT @@global.read_only;
+--------------------+
| @@global.read_only |
+--------------------+
|                  0 |
+--------------------+
1 row in set (0.00 sec)

Enfin, redémarrons le serveur MySQL (pour une raison quelconque, un rechargement dynamique de la configuration MySQL (/etc/init.d/mysql reload) ne fonctionnait pas, je devais donc redémarrer le serveur de base de données de manière explicite:

service mysql stop
service mysql start

Voila! Maintenant, l'accès au site Web est restauré. Mettra à jour ma réponse si des changements se produisaient.

1
Aleksandr Blekh

Comme le dit Eborbob, c'est probablement un client, 

Avez-vous vérifié votre outil de sauvegarde?

Utilisez-vous un proxy SQL comme proxySQL ou maxscale? Par exemple, Mascale peut appliquer la lecture seule en surveillant: https://jira.mariadb.org/browse/MXS-1859

Le gestionnaire de réplication peut également changer l'indicateur READ ONLY

0
NicoMinsk