JeuWeb - Crée ton jeu par navigateur
[PHP] Pour quelles raisons un INSERT peut être executé 2 fois ? - Version imprimable

+- JeuWeb - Crée ton jeu par navigateur (https://jeuweb.org)
+-- Forum : Discussions, Aide, Ressources... (https://jeuweb.org/forumdisplay.php?fid=38)
+--- Forum : Programmation, infrastructure (https://jeuweb.org/forumdisplay.php?fid=51)
+--- Sujet : [PHP] Pour quelles raisons un INSERT peut être executé 2 fois ? (/showthread.php?tid=5660)

Pages : 1 2 3 4


RE: Pour quelles raisons un INSERT peut être executé 2 fois ? - Hideaki - 23-08-2011

Pour tes tests, ajoutes 2 echos avant et après l'insert avec un chiffre statique qui s'auto-incrémente à chaque appel, tu la stockeras dans une variable locale ( sinon cela sert à rien ) que tu afficheras dans ton écho.
J'ai déjà eu se problème cela peut venir du navigateur et oui ... ou d'un bouton image sous FF ( il y a 1 an et demi c'était le cas ).
Je ne sais pas si, sous php, un fonctionnement analogue au mot-clef synchronized existe, cela résoudrait se problème facilement ( à condition de bien le placer).
Pour finir le timestamp n'est pas un gage de fiabilité pour ton analyse, une même portion de code peut-être exécuter pendant le même laps de temps ( pour un temps timestamp et non absolu).


RE: Pour quelles raisons un INSERT peut être executé 2 fois ? - php_addict - 30-08-2011

salut

(23-08-2011, 10:37 PM)Hideaki a écrit : Pour tes tests, ajoutes 2 echos avant et après l'insert avec un chiffre statique qui s'auto-incrémente à chaque appel, tu la stockeras dans une variable locale ( sinon cela sert à rien ) que tu afficheras dans ton écho.

est ce que cela peut se faire dans un log fichier texte?

sur mon dédié l'horloge avance trop vite (2 minutes en plus en 1 semaine et pourtant ntpdate semble etre present dans les process en memoire). Est ce qu'une mauvaise horloge peut avoir une incidence? il semble que mon hardware est un peu pourri...ca peut être une cause possible ?

++


RE: Pour quelles raisons un INSERT peut être executé 2 fois ? - Hideaki - 30-08-2011

Oui, tu peux faire le log dans un fichier texte au lieu d'un echo.
Normalement le hardware ne devrait pas être la cause de ton problème.



RE: Pour quelles raisons un INSERT peut être executé 2 fois ? - php_addict - 13-09-2011

Salut

bon et bien je ne trouve toujours pas la cause du pourquoi du comment, c'est assez étrange...surtout que j'enregistre en SESSION le dernier timestamp du clic sur 'construire un batiment' et qu'il n'est pas possible d'en construire 2 dans un laps de temps de 2 secondes.

Même si pour une raison obscure le navigateur envois 2 fois la même requête HTTP, et avec ce timestamp enregistré en session, la requête SQL ne peut pas être executée 2 fois, non ?

(22-08-2011, 06:26 PM)niahoo a écrit : Un truc qui a rien a voir mais dans ton array, il ne faut pas mettre les ':' devant le nom des clés il me semble.

Il ne te reste qu'a détecter le moment ou ça arrive (par exemple en comparant le count() des lignes avant et après l'appel de ton script) et quand ça arrive, balancer un exception puis en afficher la trace

il semble bien que les ':' doivent être utilisés dans les array:

http://www.php.net/manual/fr/pdostatement.execute.php#example-990

bonne soirée et merci de m'avoir lu


RE: Pour quelles raisons un INSERT peut être executé 2 fois ? - php_addict - 15-09-2011

bonjour, toujours à la recherche du saint graal...

j'aimerais comprendre ce qu'il se passe quand on clique (ou double click) sur un lien qui declenche un script (exemple.php) qui execute une simple commande MySQL du type INSERT?

apache2 est multi trhead non? donc il y a plusieurs version de exemple.php chargé en memoire, non ?

au cas ou un meme script exemple.php est lancé simultanément par 2 postes client, que se passe t il exactement?

malgré que j'enregistre en SESSION le microtime du click sur un lien, il arrive que l'INSERT est executé 2 fois, et je n'arrive pas à comprendre d'où ca peut venir, je suis à peu près certain que mon script est bien codé...

un avi?



RE: Pour quelles raisons un INSERT peut être executé 2 fois ? - niahoo - 15-09-2011

Je sais pas si les avi ça passe en fichier joint, a mon avis, trop lourd Smile

Sinon bah tu as une race condition, il te faut donc utiliser les transactions et faire ta vérification de temps minimum à l'intérieur de celle-ci.


RE: Pour quelles raisons un INSERT peut être executé 2 fois ? - php_addict - 15-09-2011

salut niahoo, je ne suis pas certain de comprendre...

il y a peu être concurence (c'est bien ca que tu entends par "race condition" ?)

et qu’entends tu par "temps minimum" ?

je n'arrive pas à trouver une solution pour comprendre d'où cela peut venir...


PS, le fichier joint n'est pas passé


RE: Pour quelles raisons un INSERT peut être executé 2 fois ? - niahoo - 15-09-2011

je n'y connais pas assez, ni en serveur ni en transactions SQL mais imaginon un doubleclic

1 ere requete clic, tu regardes en session ton timestamp, il est ok
2 nde requete, idem => les deux requetes passent
1 ere requete, l'insert se fait,
2 eme l'insert se fait
1 ere , mise a jour de la session
2 nde, mise à jour de la session
3 eme clic
3 eme requete, timestamp pas ok, ça passe pas.

C'est difficile à imaginer car d'une part je suppose que PHP gère la session d'une manière plus consistante, et de deux le double clic n'est pas assez rapide ! (je compte à l'arrache, en 1 seconde je fais 7 clics à la vitesse de mon double clic normal.

Bon, donc si maintenant au lieu de stocker ton timestamp en session tu le mets dans la table où tu fais tes insert. (je ne sais pas quelles sont tes données, donc je ne sais pas si c'est judicieux;

1er clic, début de requete
2 eme clic, début de requete
1 ere requete début de transaction blocante en lecture (est-ce que ça existe ?)
2 eme requete : table bloquée, on patiente
1ere requete, on regarde si le timestamp dans la tables est ok ? il l'est, on fait l'insert et on met a jour le timestamp dans la table
1 ere requete toujours, on libère la table en mettant fin à la transaction
2 eme requete, début de transaction, on lit le timestamp, il est trop récent, on laisse tomber.

(par contre, logiquement le navigateur devrait afficher le résultat de la seconde requete, c'est dommage)

Voilà je ne sais pas si ce que je raconte est vraisemblable car je ne pense pas que ça se passe comme ça mais c'est une idée à explorer.

Si tu gères toi même la session PHP avec ta base de données (comme j'ai vu que tu en parlais sur des topics), tu peux également faire une transaction au niveau de la session pour empecher la seconde requete de lire le timestamp avant que la première ne l'ai mis à jour.

Dans les deux cas, même si la seconde requete arrive au serveur avant la première (c'est possible), ça marche aussi.

À condition de pouvoir bloquer une table en lecture lors des transactions et bien sur à condition de n'avoir pas trop de demandes sur cette table car la transaction la bloque pour tout le monde Smile


RE: Pour quelles raisons un INSERT peut être executé 2 fois ? - php_addict - 15-09-2011

Merci pour tes explications, je vais méditer là dessus...

Je vais également essayer de tester avec APC désactivé, car je pense que APC met les données cache sous forme de fichiers (et pas en mémoire, à verifier...) et qu'il peut y avoir concurrence d'accès aux fichiers...est ce crédible cette hypothese ?


RE: Pour quelles raisons un INSERT peut être executé 2 fois ? - popayan - 16-09-2011

J'ai pas tout suivi et je vais peut être dire une énormité mais pourquoi ne pas mettre un token unique sur ton lien au chargement de ta page.
Ensuite, pendant le traitement tu vérifies que le token n'a jamais été utilisé, si c'est le cas tu traites, sinon tu fais rien