Astuces SQL
Les astuces SQL peuvent être utilisées pour forcer le plugin à choisir un serveur particulier dans le pool. Ceci peut aider à palier aux problèmes de bascule entre les connexions oude changement d'état des connexions.
Les astuces SQL sont des commentaires de la syntaxe SQL. Comme ils sont supposés être ignorés, ils n'interfèrent pas avec les serveurs MySQL, le proxy MySQL ou même un pare-feu.
Trois astuces SQL sont supportées par le plugin :
MYSQLND_MS_MASTER_SWITCH
indique au plugin d'exécuter une
requête sur le maitre, MYSQLND_MS_SLAVE_SWITCH
force
l'utilisation de l'esclave et MYSQLND_MS_LAST_USED_SWITCH
exécutera la requête sur le même serveur que celui utilisé pour exécuter la
requête précédente.
Le plugin scanne le début de la requête pour rechercher une astuce SQL en commentaires. Les astuces SQL ne doivent être écrites qu'au début d'une requête pour être reconnues.
Exemple #1 Configuration du plugin avec un esclave et un maitre
<?php $mysqli = new mysqli("myapp", "username", "password", "database"); if (mysqli_connect_errno()) /* Evidemment, votre propre gestion des erreurs serait meilleure... */ die(sprintf("[%d] %s\n", mysqli_connect_errno(), mysqli_connect_error())); /* Connexion 1, la connexion a utilisé des variables SQL, pas de SELECT, donc maitre utilisé */ if (!$mysqli->query("SET @myrole='master'")) { printf("[%d] %s\n", $mysqli->errno, $mysqli->error); } /* Connexion 1, exécutée sur le maitre à cause de l'astuce SQL présente */ if (!($res = $mysqli->query(sprintf("/*%s*/SELECT @myrole AS _role", MYSQLND_MS_LAST_USED_SWITCH)))) { printf("[%d] %s\n", $mysqli->errno, $mysqli->error); } else { $row = $res->fetch_assoc(); $res->close(); printf("@myrole = '%s'\n", $row['_role']); } $mysqli->close(); ?>
<?php $mysqli = new mysqli("myapp", "username", "password", "database"); if (!$mysqli) /* Evidemment, votre propre gestion des erreurs serait meilleure... */ die(sprintf("[%d] %s\n", mysqli_connect_errno(), mysqli_connect_error())); /* Force l'utilisation du maitre, le maitre a toujours des données fraiches */ if (!$mysqli->query(sprintf("/*%s*/SELECT critical_data FROM important_table", MYSQLND_MS_MASTER_SWITCH))) { printf("[%d] %s\n", $mysqli->errno, $mysqli->error); } ?>
Autre exemple concrêt : créer des tables sur un esclave. Si aucune astuce SQL n'est fournie,
le plugin va envoyer les CREATE et INSERT
vers le maitre. L'astuce MYSQLND_MS_SLAVE_SWITCH
peut alors être
utilisée pour forcer l'utilisation d'un esclave.
Exemple #4 Création de table sur un esclave
<?php $mysqli = new mysqli("myapp", "username", "password", "database"); if (!$mysqli) /* Evidemment, votre propre gestion des erreurs serait meilleure... */ die(sprintf("[%d] %s\n", mysqli_connect_errno(), mysqli_connect_error())); /* Force l'utilisation d'un esclave */ if (!$mysqli->query(sprintf("/*%s*/CREATE TABLE slave_reporting(id INT)", MYSQLND_MS_SLAVE_SWITCH))) { printf("[%d] %s\n", $mysqli->errno, $mysqli->error); } /* Continue en utilisant cette connexion à l'esclave */ if (!$mysqli->query(sprintf("/*%s*/INSERT INTO slave_reporting(id) VALUES (1), (2), (3)", MYSQLND_MS_LAST_USED_SWITCH))) { printf("[%d] %s\n", $mysqli->errno, $mysqli->error); } /* N'utilisez pas MYSQLND_MS_SLAVE_SWITCH qui autoriserait la bascule vers un autre esclave ! */ if ($res = $mysqli->query(sprintf("/*%s*/SELECT COUNT(*) AS _num FROM slave_reporting", MYSQLND_MS_LAST_USED_SWITCH))) { $row = $res->fetch_assoc(); $res->close(); printf("There are %d rows in the table 'slave_reporting'", $row['_num']); } else { printf("[%d] %s\n", $mysqli->errno, $mysqli->error); } $mysqli->close(); ?>
L'astuce SQL MYSQLND_MS_LAST_USED
interdit la bascule de connexion
et force l'utilisation de la connexion de la requête précédente.