IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

Requêtes MySQL Discussion :

Collisions de requetes sur bdd MySQL


Sujet :

Requêtes MySQL

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Membre confirmé
    Profil pro
    Inscrit en
    Septembre 2007
    Messages
    193
    Détails du profil
    Informations personnelles :
    Âge : 45
    Localisation : France

    Informations forums :
    Inscription : Septembre 2007
    Messages : 193
    Par défaut Collisions de requetes sur bdd MySQL
    Bonjour le forum!

    J'ai le probleme suivant:

    J'ai lu a plusieurs endroits que la protection contre la collision de deux requetes sur une base de données est bien meilleure que celle fournie par la fonction php flock pour le verrouillage des fichiers. Donc on nous conseille d'utiliser de préférnces les bdd que les fichiers pour stocker les données.
    Donc j'ai décidé de faire une systeme personnalisé de verrouillage des fichiers par stockage du nom du fichier dans une bdd mysql (et aussi car flock ne marche pas pour toutes les fonctions d'ecriture et de lecture dans les fichiers).

    Voila le probleme: le blocage d'un fichier se fait par inclusion de son nom qui est une clé primaire dans la bdd. Or apparemment parfois il se produit deux écritures en meme temps sur le fichier donc deux requetes d'inclusion du nom de fichier dans la bdd sont entrées en collision (si elle n'etaient pas rentrées en collision, la premiere aurait été acceptée mais pas le deuxieme car clé primaire). Est-ce possible?

    NB:voila comment j'ai vérifié produit la collision: le script php qui se trouve sur un serveur distant (chez un hébergeur) est sollicité par moi par deux ordis différents, et ce script contient une boucle qui écrit 5000 fois (assez pour que les deux appels au script se superposent) sur le meme fichier (en rajoutant le texte a la fin du fichier). Le texte obtenu montre un mélange des données rentrées et des caractere non reconnus ????? preuve qu'il y a eu superposition. Je me disais q'etant donné qu'on effectue les requetes a la vitesse d'exécution du programme il est normal qu'il y ai des collisions de requetes dans la bdd. Mais j'ai fait un test avec flock a la place du verrouillage par bdd et avec flock on a légerement moins de superpositions...?

  2. #2
    Membre Expert Avatar de Maximil ian
    Profil pro
    Inscrit en
    Juin 2003
    Messages
    2 622
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2003
    Messages : 2 622
    Par défaut
    Salut,

    Tu as tenté un truc du genre

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    while (!$fini) {
       if (mysql_query ("INSERT INTO latable VALUES ('$nom_fichier')")) {
         fopen ($nomfichier, "a");
         fwrite(...);
         mysql_query("DELETE FROM latable WHERE ...");
         $fini = true;
       }
    }
    Ceci dit j'y vois un gros défaut de PHP qui ne sait pas se reposer sur le système de fichiers sous-jacent pour gérer les accès concurrents...

  3. #3
    Membre confirmé
    Profil pro
    Inscrit en
    Septembre 2007
    Messages
    193
    Détails du profil
    Informations personnelles :
    Âge : 45
    Localisation : France

    Informations forums :
    Inscription : Septembre 2007
    Messages : 193
    Par défaut
    en gros oui (avec un usleep(100) dans la boucle, pour attendre 0.1 secondes avant le prochain essai).

    Par contre je ne suis pas sur d'avoir compris ta remarque...
    Tu veux dire que php ne sais pas gérer les acces concurrents a...un fichier? Si c'est ce que tu veux dire, c'est justement pour ca que j'utilise une base de données, car selon ce que j'ai lu elles gerent mieux les acces concurrents (moi j'ai appelé ca collision de requetes :o) )

    Mais ce qui m'etonnes, c'est qu'avec la base de donnée j'ai toujours des collisions (moins que sans systeme de verrouillage, mais autant qu'avec flock).

  4. #4
    Membre Expert Avatar de Maximil ian
    Profil pro
    Inscrit en
    Juin 2003
    Messages
    2 622
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2003
    Messages : 2 622
    Par défaut
    Citation Envoyé par lysandre Voir le message
    Par contre je ne suis pas sur d'avoir compris ta remarque...
    Tu veux dire que php ne sais pas gérer les acces concurrents a...un fichier?
    Oui, PHP ou le système de fichiers (NTFS...) ce qui serait encore plus surprenant.

    Concernant tes collisions tout ce que je peux dire c'est qu'une contrainte de clé primaire ou unique est inviolable donc tant que le DELETE n'a pas été fait, pas d'autre insertion dans la base.

    Peut-être que fwrite() est fait de telle façon que le script continue en séquence alors que le travail d'écriture s'exécute toujours en parallèle ? Dans ce cas ça pourrait expliquer que le fichier soit encore en cours d'écriture même après le DELETE.

    Tu as essayé en combinant flock() et la méthode base de données ?

  5. #5
    Membre confirmé
    Profil pro
    Inscrit en
    Septembre 2007
    Messages
    193
    Détails du profil
    Informations personnelles :
    Âge : 45
    Localisation : France

    Informations forums :
    Inscription : Septembre 2007
    Messages : 193
    Par défaut
    Citation Envoyé par Maximilian Voir le message
    Peut-être que fwrite() est fait de telle façon que le script continue en séquence alors que le travail d'écriture s'exécute toujours en parallèle ? Dans ce cas ça pourrait expliquer que le fichier soit encore en cours d'écriture même après le DELETE.
    Ca aurait pu etre possible effectivement, mais j'ai fait le petit essai suivant:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    $link=fopen("fichier.txt","w+");
    echo microtime()." ";
    fwrite($link,$texteassezlong);
    echo microtime();
    echo file_get_contents("fichier.txt");
    et le texte entier m'a été affiché (donc au moment ou est exécuté le file_get_contents tout le texte a été ecrit par le fwrite). Le texte $texteassezlong est au moins aussi long que les textes avec lesquels j'ai eu des collisions. Apres il y a toujours possibilité que le script php continue et que toutes les requetes sur le fichier soient mises a la queue en parallele...
    La différence des microtime donne en moyenne sur plusieurs essais 0.2 microseconde quand le texte est long, 0.13 microsecondes quand le texte est court...ce n'est pas fulgurant comme différence, mais ca laisse penser que le fichier php attends le fin de l'exécution du fwrite. D'ailleur fwrite retourne une valeur suivant le succes ou l'echec de l'opération, donc je pense que le script php attends l'exécution du fwrite avant de continuer.

    Peut-etre que la base de donnée peut avoir des faiblesses si elle recoit des enchainements de requetes de deux scripts différents et a la cadence d'exécution du code php...?

    Je pense que je vais pouvoir tester ca, car j'ai introduit une sécurité de plus dans mon systeme de verrouillage: quand un utilisateur ajoute le nom du fichier dans le base de données, il y ajoute en plus un code généré aléatoirement, attends 30 microsecondes, et vérifie que le code qui est dans la base de donnée est bien le sien. Si c'est le sien, le verrouillage est effectif et il peut commencer a ecrire sur le fichier. Si ce n'est pas le sien, cela veut dire que deux requetes "insert" son passées en meme temps (car sa requete insert est passée, et si le code n'est pas le sien, une autre requete insert est aussi passée avec la meme clef primaire) et ca m'envoie un message d'erreur. Quand j'aurai testé ce code je reviens ecrire les resultats!

  6. #6
    Membre Expert Avatar de Maximil ian
    Profil pro
    Inscrit en
    Juin 2003
    Messages
    2 622
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2003
    Messages : 2 622
    Par défaut
    Citation Envoyé par lysandre Voir le message
    Peut-etre que la base de donnée peut avoir des faiblesses si elle recoit des enchainements de requetes de deux scripts différents et a la cadence d'exécution du code php...?
    Cela provoquera un rejet d'un des deux INSERT qui essaient d'insérer le même nom de fichier, au pire des deux s'ils sont réellement "simultanés", mais jamais une acceptation des deux à la fois qui serait une violation de la contrainte d'unicité.

    Pour t'en persuader, remplace tes fichiers par une table contenant les données et tes fwrite() par des UPDATE. Non seulement il n'y aura plus de problèmes de "collision" (données qui seraient le mélange d'un bout de modification et d'un bout d'une autre) mais il n'y aura jamais non plus deux clés primaires de même valeur.

Discussions similaires

  1. problème de requete sur BDD
    Par madcode dans le forum Android
    Réponses: 5
    Dernier message: 24/11/2011, 06h11
  2. Triggers sur BDD MySQL de Free
    Par Superleo2999 dans le forum MySQL
    Réponses: 4
    Dernier message: 14/05/2010, 19h13
  3. Réponses: 4
    Dernier message: 13/07/2009, 15h37
  4. [MySQL] Requete insertion BDD mysql
    Par mjs21 dans le forum PHP & Base de données
    Réponses: 2
    Dernier message: 19/06/2008, 08h53
  5. DBexpress, Simple requete sur server MySql
    Par Ice-tea dans le forum Bases de données
    Réponses: 7
    Dernier message: 02/06/2006, 14h57

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo