Erreur dans une requête SQL

Rechercher

Erreur dans une requête SQL

Par Sithran  -  7 reponses  -  Le 07/05/2008 20:11  -  Editer  - 

Bonsoir à tous,

Voilà, alors que je programmais paisiblement, j'en vins à écrire une requête. La voici

<?php
$query = mysql_query("SELECT id, message, auteur DATE_FORMAT(temps, '%d-%m-%Y') as temps FROM ".PREFIX."articles ORDER BY id DESC LIMIT ".$msg_affich.", ".$nbre_msg_page."") or die (mysql_error());
?>

Et voilà l'erreur générée : You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near 'DATE_FORMAT(temps, '%d-%m-%Y') as temps FROM waikblog_articles ORDER BY id DESC ' at line 1.

Pourriez-vous me dire si vous voyez où le script bug ? Et si éventuellement, il y a moyen de l'optimiser ?

 

Réponses apportées à cette discussion

Par Emacs  -  Le 07/05/2008 20:20  -  Haut de page  - 

L'erreur est bête, il manque une virgule avant le DATE_FORMAT(). Ce qui donne corrigé :

<?php
$query = mysql_query(sprintf(
    'SELECT id, message, auteur, DATE_FORMAT(temps, "%d-%m-%Y") as temps FROM '. PREFIX .'articles ORDER BY id DESC LIMIT %d,%d',
    intval($msg_affich),
    intval($nbre_msg_page)
));
?>

Au passage :

1/ Le "or die()" ne doit être présent qu'en développement et pas en production

2/ Les fonctions mysql_*() ont tendance à devenir obsolètes viennent petit à petit à être remplacées par l'extension PDO qui est une interface commune d'accès aux SGBR.

 
Par Sithran  -  Le 07/05/2008 20:22  -  Haut de page  - 

Merci beaucoup de ta réponse rapide et précise. Pour le or die, bien évidemment, et pour PDO, je n'arrive toujours pas à me familiariser avec, peut-être que le jour où un tuto dessus arrivera sur A-PHP, je m'y mettrai :P .

 
Par Emacs  -  Le 07/05/2008 20:27  -  Haut de page  - 

Pas de quoi ! Je t'invite à lire les tutoriels de création d'un livre d'or et des flux RSS qui te permettront de te familiariser avec les bases de PDO.

++

 

 
Par Julgates  -  Le 07/05/2008 21:52  -  Haut de page  - 

L'intérêt de sprint_f à part compliquer la mise à jour de la requête ?

Quant à PDO, l'intérêt est vraiment moindre d'utiliser une usine à gaz quand une petite classe SQL faite maison est contrôlable de A à Z et donc complètement modifiable / améliorable. En plus c'est pas comme si vous utilisez 15 fonctions propriétaires... connect, select db, query, fetch_assoc, fetch_row, num_row... ah bah 6 !

 
Par Emacs  -  Le 07/05/2008 22:49  -  Haut de page  - 

@Julgates :

Sprintf() permet de formater proprement ta requête SQL et de t'assurer que les types des variables sont bien ceux attendus. Si tu préfères, utiliser ici sprintf() est quelque peu semblable à créer des requêtes préparées ("prepared statements") avec PDO ou MySQLi. De plus, je trouve personnellement que c'est plus confortable à lire puisque l'on a d'un côté la requête purement textuelle et de l'autre les paramètres. La requête est ainsi bien plus lisible que si l'on avait des concaténations en chaine... Mais là ce n'est qu'un avis personnel.

Pourquoi PDO ? Tout d'abord parceque les fonctions mysql_() deviennent de plus en plus obsolètes avec le déploiement constant de PHP5 et l'arrivée prochaine de PHP 6. Globalement, mysql_() appartient plus à PHP4 et donc au passé. Quand tu parles de développer une classe maison pour gérer l'accès aux données, que fais-tu ? Et bien tu réinventes la roue, c'est-à-dire ce que fait très bien (et en mieux) PDO. Développer ta classe maison implique aussi que tu vas utiliser les fonctions mysql_*(). Donc tu vas réutiliser des fonctions technologiquement obsolètes, moins performantes et moins secure que PDO.

Deuxièmement, PDO n'est pas une usine à gaz en soit. Ce n'est qu'une simple interface commune d'accès aux SGBDR. Son utilisation n'est pas plus compliquée qu'une autre classe PHP5. Il y'a en plus une super doc pour apprendre à l'utiliser.

Troisièmement, PDO est et sera l'interface d'accès aux SGBDR par défaut de PHP. Certes, on n'a beau dire que c'est plus lent aujourd'hui mais néanmoins cela permet d'accèder aux BDD de manière plus saine et sécurisée. Notamment avec les requêtes préparées. C'est quand même bien plus secure que la concaténation des variables à la requête SQL... Il faut également savoir qu'une version 2 de PDO est en cours de développement et sera bien plus scalable que celle-ci. C'est encore une raison supplémentaire pour l'utiliser.

Quatrièmement, comme toute classe, PDO est dérivable. Tu peux donc développer à ta guise des classes dérivées pour étendre les possibilités de PDO. Donc là aussi tu peux garder la main sur l'accès aux données. La plupart des frameworks PHP5 à la mode utilisent aujourd'hui des classes d'abstractions de BDD qui dérivent PDO.

Enfin, PDO permet de bénéficier des avantages des transactions des bases de données qui respectent la norme ACID (Atomicité, Cohérence, Intégrité, Durabilité). Avec les fonctions mysql_*(), c'est aussi possible mais loin d'être terrible. C'est par contre supporté dans MySQLi. Bref, le mécanisme des transactions permet de s'assurer qu'une série d'enregistrements s'est bien opérée. Dans le cas contraire, tout est annulé (rollback). Cela garantit l'intégrité et la cohérence des données dans la base de données. La plupart des développeurs débutants et confirmés avec PHP utilisent MySQL avec le moteur de stockage MyISAM, mais ne connaissent bien souvent que trop peu de choses sur les bases de données. De ce fait, cela ne leur permet pas de profiter des spécificités et de la scabilité de chacun des SGBDR. D'autre part, cela ne les incite pas à s'orienter vers des solutions plus professionnelles et saine d'accès aux données comme l'est PDO.

Pour en revenir à MySQL, MyISAM est le moteur de stockage des données par défaut de MySQL. Il a la particularité d'être très rapide mais en revanche il n'est pas du tout ACID. Contrairement au moteur InnoDB. De ce fait, si plusieurs requêtes doivent être éxécutées les unes à la suite des autres, et qu'il y'en a une qui échoue en cours de route, alors la base de données conserve les données inscrites et se fout de savoir si tout s'est bien passé. On risque alors d'altérer la cohérence de la base de données... Prenons un exemple simple et classique. La gestion d'un compte bancaire. Quand on effectue une transaction bancaire, cela implique deux écritures dans une base de données : le débit d'un compte et le crédit d'un autre. Pour que la transaction bancaire soit valide, il faut obligatoirement que les deux écritures se soit bien réalisée. Si l'une d'elle échoue en cours de route, alors la base de données n'est plus cohérente... Et ça MyISAM ne le gère pas car il n'intègre pas le mécanisme des transactions. Avec InnoDB par contre, on peut placer ces deux requêtes dans la même transaction pour contrôler que leur exécution s'est bien passée. Si oui alors très bien, sinon toute la transaction est annullée et il faut la refaire. Grâce à ce mécanisme, l'intégrité et la cohérence de la base de données sont conservées.

Donc, je recommande fortement d'utiliser MySQL avec InnoDB et donc avec PDO qui plus est.

PDO + SGBDR transactionnel = duo gagnant pour faire du développement sain avec des BDD

J'espère que ces quelques arguments te feront comprendre pourquoi PDO est largement plus intéressant à tout point de vue pour le développement d'applications couplées à des BDD. Cette extension comble énormément de lacunes reprochables aux fonctions mysql_*() standards et permet d'utiliser au maximum les possibilités des systèmes de gestion de bases de données relationnels.

++

 
Par Palleas  -  Le 08/05/2008 00:09  -  Haut de page  - 

Bon moi j'étais parmis les pro-sprintf, j'avais les mêmes arguments, mais desormais je ne m'en sers plus du tout, je teste avant mes données, ex : page.php?id=8, si l'id n'est pas un nombre (testé avec is_numeric()) gogo 404.

Quand à PDO, je trouve ça vraiment cool, mais je préfère utiliser ma classe à moi plutot que ça parce qu'effectivement c'est bien moins lourd (PDO reste une usine à gaz). De plus, on parle d'abstraction, mais quel interet ? Si tu changes de SGBD, du devras changer la syntaxe de tes requetes (cf différence pour limiter le nombre de résultats entre MySQL et PostgreSQL, notamment).

Après effectivement la norme ACID, je ne sais pas, je n'ai pas encore eu de soucis donc...

Je publierai ma classe quand elle sera au point, et je dominerai le monde o//

 
Par Emacs  -  Le 08/05/2008 12:20  -  Haut de page  - 

Je n'ai pas dit que PDO faisait de l'abstraction de base de données bien au contraire. J'ai dit que les nouvelles classes d'abstraction de bases de données s'appuient aujourd'hui sur PDO.

 

Ajouter une réponse à la discussion

Seuls les membres connectés sont autorisés à poster dans les forums !

Identifiez-vous
Join |  ID/MDP? |