Travail avec la base de données dans Drupal 7 - leçon 3 - Requêtes statiques (SELECT)
La forme la plus générale d'une requête dans Drupal est la requête statique. Une requête statique sera transmise à la base de données telle quelle. Seule la requête de sélection (select) peut être statique.
Il ne faut utiliser les requêtes statiques que pour des requêtes très simples. Vous devriez utiliser des requêtes dynamiques si vous devez écrire une requête complexe, créée dynamiquement ou modifiée après exécution.
Une manière simple d’exécuter une requête statique est via la méthode query :
<?php $result = $conn->query("SELECT nid, title FROM {node}"); ?>
La fonction procédurale est préférable :
<?php $result = db_query("SELECT nid, title FROM {node}"); ?>
Appeler db_query()
comme ci-dessus est équivalent à :
<?php $result = Database::getConnection()->query("SELECT nid, title FROM {node}"); ?>
Examinons pourquoi il est préférable d’utiliser db_query
plutôt que d’appeler directement l’objet Database.
Préfixe
Dans les requêtes statiques, toutes les tables doivent être entourées de {}. Cela permet d’ajouter un préfixe aux noms de tables. Les préfixes permettent d’installer plusieurs sites dans une même base de données, en utilisant des préfixes différents pour les tables, par exemple : "site1_", "site2_".
Placeholders (remplacements)
Les placeholders sont marqués par des noms où une valeur doit être insérée. En séparant les placeholders dans la requête, on permet à la base de données de distinguer la syntaxe SQL des valeurs fournies par l’utilisateur, afin de prévenir les injections SQL.
<?php $result = db_query("SELECT nid, title FROM {node} WHERE created > :created", array( ':created' => REQUEST_TIME - 3600, )); ?>
Le code ci-dessus sélectionne tous les nœuds créés il y a moins d’une heure. Le placeholder :created
sera remplacé dynamiquement par la valeur REQUEST_TIME - 3600
, où REQUEST_TIME
est le temps d’exécution de la requête. Une requête peut avoir autant de placeholders que nécessaire, mais tous doivent avoir des noms uniques, même s’ils ont la même valeur.
Selon le cas d’utilisation, le tableau de placeholders peut être défini en ligne (comme dans l’exemple) ou défini à l’avance puis passé plus tard. L’ordre dans le tableau n’a pas d’importance. Les placeholders commençant par "db_" sont réservés au système et ne doivent pas être utilisés explicitement.
Notez que les placeholders doivent être entourés de guillemets ou non selon leur type. Par exemple, les valeurs chaînes doivent être sans guillemets dans la requête, tandis que les valeurs numériques n’en ont pas besoin.
<?php // FAUX : $result = db_query("SELECT nid, title FROM {node} WHERE type = ':type'", array( ':type' => 'page', )); // CORRECT : $result = db_query("SELECT nid, title FROM {node} WHERE type = :type", array( ':type' => 'page', )); ?>
Les placeholders ne doivent pas être utilisés pour les noms de tables ou de colonnes. Ils servent uniquement à remplacer des chaînes ou des valeurs numériques.
Tableaux de placeholders
La couche Database de Drupal offre une fonctionnalité supplémentaire pour les placeholders. Si les valeurs sont passées sous forme de tableau dans les placeholders, elles seront automatiquement transformées en une liste séparée par des virgules. Cela signifie que les développeurs n’ont plus à gérer le nombre exact de placeholders nécessaires. Voici un exemple :
<?php db_query("SELECT * FROM {node} WHERE nid IN (:nids)", array(':nids' => array(13, 42, 144))); // Ce qui est équivalent à écrire explicitement : db_query("SELECT * FROM {node} WHERE nid IN (:nids_1, :nids_2, :nids_3)", array( ':nids_1' => 13, ':nids_2' => 42, ':nids_3' => 144, )); // Ce qui équivaut à la requête suivante : db_query("SELECT * FROM {node} WHERE nid IN (13, 42, 144)"); ?>
Paramètres de la requête
Le troisième argument de db_query()
est un tableau de paramètres qui indique directement comment la requête doit être exécutée. En général, seuls deux paramètres sont couramment utilisés, les autres sont pour un usage interne.
La clé target
définit la cible de la requête. Si elle n’est pas spécifiée, la valeur par défaut est "default". Actuellement, seule la valeur "slave" indique que la requête doit être exécutée sur un serveur esclave, s’il en existe un. La clé fetch
indique la manière dont les enregistrements seront retournés depuis la base. Les valeurs possibles sont : PDO::FETCH_OBJ, PDO::FETCH_ASSOC, PDO::FETCH_NUM, PDO::FETCH_BOTH ou une chaîne représentant un nom de classe. Si une chaîne est donnée, chaque enregistrement sera retourné comme une instance de cette classe.
Le comportement de ces valeurs est défini par PDO et permet d’extraire les enregistrements en tant qu’objet stdClass, tableau associatif, tableau indexé ou tableau à double index respectivement.
- PDO::FETCH_OBJ - objet.
- PDO::FETCH_ASSOC - tableau associatif.
- PDO::FETCH_NUM - tableau indexé numériquement.
- PDO::FETCH_BOTH - tableau à double index (associatif et numérique).
Pour plus d’informations, consultez http://php.net/manual/en/pdostatement.fetch.php. Par défaut, c’est PDO::FETCH_OBJ, que vous pouvez utiliser si vous n’avez pas de préférence particulière.
Dans cet exemple, la requête sera exécutée sur un serveur esclave si disponible, et les enregistrements seront traités sous forme de tableau associatif :
<?php $result = db_query("SELECT nid, title FROM {node}", array(), array( 'target' => 'slave', 'fetch' => PDO::FETCH_ASSOC, )); ?>