Lorsque vous utilisez PHP pour manipuler les bases de données MySQL, si vous utilisez l'extension MySQLI pour la multi-Quey, vous êtes susceptible de rencontrer la méthode Next_Result () . Et beaucoup de gens ignorent un détail important -.
Cet article vous montrera les causes, les manifestations et comment éviter ce problème.
Lorsque vous exécutez plusieurs SQL via MySQLI :: Multi_Query () , MySQL renvoie plusieurs ensembles de résultats. Ces ensembles de résultats sont accessibles un par un via mysqli :: next_result () , et le contenu de chaque résultat peut être obtenu conjointement avec mysqli :: store_result () .
$mysqli = new mysqli("localhost", "user", "password", "database");
$sql = "SELECT * FROM users; SELECT * FROM orders;";
if ($mysqli->multi_query($sql)) {
do {
if ($result = $mysqli->store_result()) {
while ($row = $result->fetch_assoc()) {
// Traiter chaque rangée de données
echo $row["id"] . "<br>";
}
// Libérez l'ensemble de résultats
$result->free();
}
} while ($mysqli->next_result());
}
Dans cet exemple, obtenez un résultat défini via Store_Result () à chaque fois et relâchez-le via $ result-> free () après utilisation.
Si vous omettez $ résultat-> gratuit () , comme suit:
// ? 未Libérez l'ensemble de résultats的代码示例
if ($result = $mysqli->store_result()) {
while ($row = $result->fetch_assoc()) {
echo $row["id"] . "<br>";
}
// Ignoré $result->free();
}
Ensuite, l'utilisation de la mémoire dans votre programme continuera de croître, en particulier lors du traitement de grandes quantités de données ou de demandes simultanées élevées, cette fuite de mémoire sera très évidente. Étant donné que l'extension MySQLI cache les résultats définis dans la mémoire du client, PHP ne peut recycler ces ressources qu'en la libérant explicitement.
La mémoire augmente après que le programme fonctionne pendant longtemps;
La réponse du serveur ralentit ou même plante;
PHP rapporte une erreur épuisée de taille de mémoire autorisée ;
Problèmes de performances non suivies.
Ceci est particulièrement mortel dans les API à haut trafic, les tâches de synchronisation ou les démons.
N'oubliez pas d'appeler $ result-> gratuit () après le traitement de l'ensemble de résultats. De plus, vérifiez s'il existe de nouveaux ensembles de résultats et traitez-les après chaque appel next_result () .
$mysqli = new mysqli("localhost", "user", "password", "database");
$sql = "CALL complex_procedure(); CALL another_procedure();";
if ($mysqli->multi_query($sql)) {
do {
if ($result = $mysqli->store_result()) {
while ($row = $result->fetch_assoc()) {
// Traiter chaque ligne
}
$result->free(); // ? Relâchez correctement
}
} while ($mysqli->more_results() && $mysqli->next_result());
}
Utilisez des outils Memory_get_Usage () ou XDebug pour surveiller l'utilisation de la mémoire;
Utilisez des commandes Linux telles que TOP ou HTOP pour surveiller la mémoire du processus;
Enregistre l'utilisation de la mémoire après chaque requête.
Ne pas publier le jeu de résultats lorsque l'utilisation de MySqli :: next_result () conduit à une fuite de mémoire dans les scripts PHP. La bonne façon est d'appeler $ result-> gratuit () chaque fois que le jeu de résultats est traité. Cela maintient non seulement le programme robuste, mais évite également les problèmes de performance causés par une utilisation excessive de la mémoire.
Ceci est particulièrement important si vous créez des interfaces de données complexes ou des services qui traitent les données par lots.
Pour plus de documentation officielle sur le traitement des ensembles multi-résultats mysqli , vous pouvez accéder:
https://gitbox.net/docs/php/mysqli-multi-Query (lien supposé)
J'espère que cet article peut vous aider à éviter les pièges courants dans le développement de PHP.