Nombre de requête SQL pour un script de visite

  • Auteur de la discussion Auteur de la discussion xTrade
  • Date de début Date de début
WRInaute passionné
Pour un script de compteur de visite, ) votre avis quel est le nombre moyen maximal de requetes qu'on devrait utiliser?

J'imagine (peut-être à tort) que cela dépend de la taille des bases, du nombre de lignes... mais en ce qui me concerne, je ne récupère généralement qu'un seul champ (indexé) et une seule ligne sur chaque table.

La plus grosse table concerne les visites, mais là je ne fais qu'une insertion (table indexée sur l'id auto-incrémenté, donc cela ne doit pas être trop lent).
Cette table est intensivement utilisée lorsque j'admire mes statistiques détaillées :wink:

L'autre "grosse" table (enfin, pour moi!), c'est la table qui conserve les user agents et l'os/navigateur correspondants.
Je faisais cela afin d'éviter de recalculer à chaque fois l'os, le browser, la version... De cette manière, en un select, j'obtenais l'id de l'os et du browser correspondant.

Question 1 :

Finalement, je me demande si c'est si intelligent que ça.
Ne sachant pas trop ce qui bouffe le plus de ressources, le nombre de lignes ou la taille de la base.
Et je n'ai aucune idée du nombre de users agents existants (robots compris), à part beaucoup (mais vu que certains n'existent plus, cela doit limiter un peu)


Question 2 :

Je fais "souvent" ce genre de trucs :

req1 : SELECT id FROM table WHERE toto='bidule'

si j'obtiens un resultat nb, je fais "UPDATE hits=hits+1 FROM table WHERE id=nb"
sinon je fais un INSERT INTO table SET hits=1,toto='bidule'.

Le problème est que statistiquement, le cas où je dois faire un UPDATE est évidemment le plus fréquent.

si je fais :
$result=mysql_query(UPDATE hits=hits+1 WHERE toto='bidule')
if ($result===FALSE) mysql_query(INSERT ... )

est-ce possible?

Evidemment, si la table ne contient pas toto='bidule', cela prendra plus de temps, mais vu que les insertions sont statistiquement beaucoup plus rares, cela fait gagner une requete.

Voila pour le moment :D

Merci!
 
WRInaute passionné
xTrade a dit:
si je fais :
$result=mysql_query(UPDATE hits=hits+1 WHERE toto='bidule')
if ($result===FALSE) mysql_query(INSERT ... )

est-ce possible?

Je viens de voir ça

INSERT INTO table (hits,toto) VALUES (1,'bidume') ON DUPLICATE KEY UPDATE hits=hits+1;

Cela semble correspondre à ce que je cherche, mais est-ce plus rapide?

Merci!
 
Nouveau WRInaute
salut,

Vu ta requete, il est egalement important que le champ toto soit indexé (en UNIQUE ou en PRIMARY KEY, ça dépend...), là la requete devrait être plus rapide que si toto n'est pas indéxé.
 
WRInaute occasionnel
xTrade a dit:
Je viens de voir ça

INSERT INTO table (hits,toto) VALUES (1,'bidume') ON DUPLICATE KEY UPDATE hits=hits+1;

Cela semble correspondre à ce que je cherche, mais est-ce plus rapide?

Merci!
C'est forcément plus rapide ! Mais alors de combien je sais pas....

Perso j'utilise cette syntaxe de temps en temps (il faut MySql 5 mini attention)

Sinon pour la rapidité de tes requètes, le plus important est d'avoir choisi tes index de manière judicieuse.
Après, tu peux aussi imaginer chronometrer leur temps d'execusion pour chaque script pour te donner une petite idée...
 
WRInaute passionné
easyzik a dit:
Perso j'utilise cette syntaxe de temps en temps (il faut MySql 5 mini attention)

Ah?

Bon ben je vais utiliser ma première solution, j'ai déjà gagner 8 requêtes dans le cas le plus pénalisant (visiteur provenant d'un moteur)

Sinon pour la rapidité de tes requètes, le plus important est d'avoir choisi tes index de manière judicieuse.
Après, tu peux aussi imaginer chronometrer leur temps d'execusion pour chaque script pour te donner une petite idée...

Oui, je viens de vérifier : sur mes grosses tables, c'est le cas.
J'ai également vérifier que je n'importais que les champs utiles.

Sinon, est-ce que le nombre lui-même de requetes est important : autrement dit, est-ce que cela vaut le coup de se faire ch... à dimininuer ce nombre?

Actuellement, je fais (14+nbr de mots) requètes dans le cas d'un nouveau visiteur qui vient par un moteur de recherche (cas le plus défavorable) et 7 pour un visiteur qui parcourt mon site.
En utilisant des cookies, je peux virer deux requètes.

Cela vous parait correct? (les SELECT apporte au maximum 3 champs, généralement des nombres car je croise pas mal de table pour éviter de tout surcharger. Sinon ce sont des UPDATE)

Merci
 
WRInaute occasionnel
Ce n'est pas le nombre de requète qui est important mais la quantité de ressources qu'elles demandent.
Les requètes de selection uniquement basées sur des clé primaires sont extrêmement rapides.
Les update sont déja beaucoup plus lents.
Enfin, utiliser un ORDER BY, un GROUP BY ou tout autre truc du genre sur un SELECT peux ruiner les perfs...

Globallement, il vaut mieux essayer de reduire au maximum le nombre de requetes quand même. L'utilisation d'un système de cache sur les pages principale (index etc...) est souvent une solution qui marche bien quand c'est possible...

Tu peux aussi utiliser des tables en memoire (HEAP) qui sont plus rapides d'accès que les autres mais volatiles...
A toi de voir et de combiner tout ça.

Un bon moyen de tester tes requètes et aussi de te documenter sur le mot clé EXPLAIN.
C'est surtout por vérifier que tes clés sont correctement choisies

Amuse toi bien ;)
 
WRInaute passionné
En clair, mysql est tout un art :lol:

Pour un début, je suis assez content de moi :lol:

Petites précisions :

- ON DUPLICATE KEY fonctionne sous mysql 4.1
- En utilisant cette commande, mysql_last_id retourne toujours l'id de la ligne insérée OU modifiée, contrairement à un UPDATE tout seul qui renvoie 0 ou 1 (je crois) -> dans ma recherche à la diminution du nombre de requètes, je vais en gagner quelques unes :D

En réfléchissant, je pense que tu as raison sur la rapidité : pour faire un update, en interne, il doit bien y avoir l'équivalent d'un SELECT tout comme pour un INSERT sur une clé unique donc cela doit avoir la même vitesse sinon mieux vu qu'on fait une requete en moins.
 
Nouveau WRInaute
tu as aussi mysql_insert_id pour récupérer l'id d'un autoincrément apres insertion dans une table (utile quand une création touche plusieurs tables).....
 
Discussions similaires
Haut