Lorsque plusieurs scripts PHP s'exécutent en parallèle, chacun effectuant une requête UPDATE sur le même enregistrement dans la même table de manière répétée, est-il possible qu'il y ait un 'lag time' avant que la table soit mise à jour avec chaque requête?MySql Délai d'attente de requête/blocage?
J'ai essentiellement 5-6 instances d'un script PHP fonctionnant en parallèle, ayant été lancé via cron. Chaque script récupère tous les enregistrements dans la table items
, puis les parcourt et les traite.
Cependant, pour éviter de traiter le même élément plusieurs fois, je stocke l'identifiant du dernier élément en cours de traitement dans une table distincte. Donc, voici comment fonctionne mon code:
function getCurrentItem()
{
$sql = "SELECT currentItemId from settings";
$result = $this->db->query($sql);
return $result->get('currentItemId');
}
function setCurrentItem($id)
{
$sql = "UPDATE settings SET currentItemId='$id'";
$this->db->query($sql);
}
$currentItem = $this->getCurrentItem();
$sql = "SELECT * FROM items WHERE status='pending' AND id > $currentItem'";
$result = $this->db->query($sql);
$items = $result->getAll();
foreach ($items as $i)
{
//Check if $i has been processed by a different instance of the script, and if so,
//leave it untouched.
if ($this->getCurrentItem() > $i->id)
continue;
$this->setCurrentItem($i->id);
// Process the item here
}
Malgré toutes les précautions, la plupart des articles sont traités plusieurs fois. Ce qui me fait penser qu'il y a un certain décalage entre les requêtes de mise à jour qui sont exécutées par le script PHP et quand la base de données met à jour l'enregistrement.
Est-ce vrai? Et si oui, quel autre mécanisme devrais-je utiliser pour m'assurer que les scripts PHP obtiennent toujours seulement les derniers currentItemId
même quand il y a plusieurs scripts fonctionnant en parallèle? Serait l'aide d'un fichier texte au lieu de l'aide db?
Dans votre code, d'où '$ rows' est-il défini? C'est à côté d'une requête de mise à jour. Pouvez-vous éléborer? –
Eh bien, je ne connais pas beaucoup PHP. L'idée est que l'émission d'un UPDATE retournera le non. des lignes qui ont été affectées. si c'est 0, cela signifie que 'where status = 'pending'' ne correspond pas parce que quelqu'un d'autre a changé le statut entre-temps. – nos
En plus de vérifier les lignes affectées par la requête, y a-t-il une autre solution plus infaillible? Comme en utilisant des fichiers texte ..? –