Section: Ajouter des méthodes en XML
« Récupération de liste d'enregistrements DAO | ^ jDao : mapping objet relationnel | Développer des méthodes en php » |
− Table des matières
Une factory générée par jDao contient par défaut un certain nombre de méthodes
(find
, findAll
, get
, insert
, etc...) comme décrit sur la page sur
l'utilisation des daos. Cependant, elles ne sont pas forcément
suffisantes, et l'on a souvent besoin de faire des sélections, des mises à jour
ou des suppressions particulières.
La section <factory>
permet de définir des méthodes supplémentaires à
générer, chacune des méthodes exécutant une requête SQL. L'avantage de déclarer
de telles méthodes ici, par rapport à la création de requête SQL dans une classe
normale, est que vous n'avez plus à vous préoccuper de problème de sql injection,
de l'écriture fastidieuse des requêtes SQL, etc...
Balise <method> ¶
Les méthodes sont déclarées via la balise <method>
. Celle-ci doit avoir au
moins un attribut, name
, indiquant le nom de la méthode. Il y a différents
types de méthode. On indique le type via l'attribut type
.
Une balise <method>
peut contenir une ou plusieurs balises <parameter>
,
qui définissent des paramètres. Une balise <parameter>
doit avoir un
attribut name
indiquant son nom.
<parameter name="foo" />
...
Il est possible d'indiquer une valeur par défaut :
<parameter name="foo" default="20"/>
Voici les différents types de méthodes. La balise <conditions>
est décrite
plus loin.
Méthode de type select, selectfirst ¶
Déclaration ¶
<method type="select"> <!-- ou type="selectfirst" -->
<parameter />
<conditions />
<order />
<limit />
</method>
Une méthode de type select
renvoient une liste d'objets "record", qui ont
donc comme propriétés celles indiquées dans la section record. Une méthode de
type selectfirst
renvoi le premier objet correspondant aux critères.
À noter qu'il n'est pas possible de limiter un select/selectfirst à un nombre réduit de propriétés. En effet, cela n'aurait pas vraiment de sens au niveau du concept de "mapping" et serait même dangereux pour les données puisqu'alors les propriétés non sélectionnées seraient vides dans le record, et si on fait ensuite un update derrière... Si on veut sélectionner un nombre restreint des propriétés définies, la seule possibilité pour le moment est de créer un autre DAO.
On peut ajouter un attribut distinct
pour récupérer seulement les éléments
distincts.
<method type="select" name="findThem" distinct="true">
..
La balise <conditions>
(facultative) décrit une condition (la clause
WHERE
en SQL). Voir la section correspondante plus loin.
On peut aussi ajouter une balise <order>
qui permet de spécifier l'ordre des
enregistrements récupérés (clause ORDER
en SQL). Il faut indiquer une ou
plusieurs balises <orderitem>
, qui contiennent un attribut property
indiquant le nom de la propriété sur lequel l'ordre s'effectue et un attribut
way
. L'attribut way doit contenir "asc" ou "desc" ou un nom de paramètre de
méthode (précédé alors par un $
).
<order>
<orderitem property="foo" way="asc" />
</order>
À noter que property
peut contenir, soit un nom d'une propriété, soit un nom
de paramètre de la méthode (précédé d'un $
) qui doit alors contenir un nom de
propriété.
<parameter name="bar"/>
<parameter name="baz" />
<order>
<orderitem property="$bar" way="$baz" />
</order>
Enfin, une balise <limit>
optionnelle permet de restreindre le nombre
d'enregistrement retournés.
<limit offset="5" count="10" />
Les attributs count
et offset
contiennent soit un nombre, soit un nom de
paramètre de méthode (précédé alors par un $
).
<method type="select" name="getFewRecord" >
<parameter name="count"/>
<parameter name="offset"/>
<limit offset="$offset" count="$count"/>
</method>
Utilisation ¶
L'utilisation des méthodes déclarées en XML a été pensée pour être transparente vis-à-vis du développeur qui n'a pas envie de se soucier de la déclaration du DAO.
Reprenons notre méthode getFewRecord
. On veut normalement récupérer un
tableau en PHP afin de manipuler plus facilement les enregistrements. Rien de
plus simple :
$dao = jDao::get('module~list'); // Récupèration du DAO si ce n'est pas fait
$records = $dao->getFewRecord(10, 5); // Appel de la méthode XML avec ses arguments et récupération des données
foreach ($records as $record) { // Parcours des données
jLog::log($record->name); // Accès au champ "name" d'un enregistrement
}
Ainsi, pour chaque méthode XML ajoutée dans le DAO, une méthode est générée et utilisable directement via PHP. Comme pour toute requête SQL, il ne faut pas oublier de "fetcher" les données.
Méthode de type count ¶
<method type="count">
<parameter .../>
<conditions ../>
</method>
ce type de méthode est équivalent à un SELECT COUNT(*)
, avec les conditions
indiquées.
Si on veut plutôt faire un SELECT COUNT(DISTINCT un_champs)
, il faut
indiquer le nom de la propriété dans l'attribut distinct
.
Méthode de type delete ¶
<method type="delete">
<parameter .../>
<conditions .../>
</method>
Génère une méthode qui execute une requête DELETE.
Méthode de type update ¶
<method type="update">
<parameter .../>
<conditions .../>
<values .../>
</method>
Ce type de méthode exécute une requête de type UPDATE. En plus des paramètres et
des conditions, il faut indiquer les valeurs que l'on met sur telle ou telle
propriété avec les balises <value>
.
<values>
<value property="foo" value="123"/>
<value property="foo" expr="$myparam"/>
</values>
L'attribut property
indique la propriété que l'on va mettre à jour. Comme
dans les conditions, l'attribut value
doit contenir une valeur. Mais si on
veut indiquer une expression SQL ou un paramètre de la méthode, il faut utiliser
l'attribut expr
.
Clause conditions ¶
Voici la description de la balise <conditions>
qui peut être utilisée dans
la plupart des méthodes précédentes.
<conditions logic="AND">
<eq property="foo" value="" />
<neq property="foo" value="" />
<lt property="foo" value="" />
<gt property="foo" value="" />
<lteq property="foo" value="" />
<gteq property="foo" value="" />
<like property="foo" value="" />
<notlike property="foo" value="" />
<isnull property="foo"/>
<isnotnull property="foo"/>
<in property="foo" value="" />
<notin property="foo" value="" />
<binary_op property="foo" value="" operator="" dbtype=""/>
</conditions>
On peut mettre plusieurs balises <conditions>
imbriquées pour faire des groupes
or/and. Si l'attribut logic
n'est pas spécifié, il vaut AND
par défaut.
Sinon il doit valoir "OR" ou "AND".
L'attribut value
doit contenir une valeur. Le type de cette valeur est celui de
la propriété. Si on préfère utiliser une expression SQL ou indiquer un paramètre
de méthode, il faut utiliser l'attribut expr
.
Si dans la condition, vous voulez comparer la valeur donnée avec une valeur
calculée du champs, vous pouvez utiliser l'attribut pattern
, qui peut
contenir la chaine "%s". Celle-ci sera remplacée par le nom du champ.
Un exemple : on veut faire une comparaison sur l'année d'un champs date.
<eq property="create_date" value="2017" pattern="YEAR(%s)" />
Cela équivaut en SQL :
WHERE YEAR(la_table.create_date) = 2017
Cas de in/notin ¶
<in>
et <notin>
sont les équivalents de foo IN (a, b, c)
et
foo NOT IN (a, b, c)
. L'usage de value
et expr
est différente. Si vous
avez une liste de valeurs statiques, vous les mettrez dans l'attribut value
comme vous le feriez en SQL :
<in property="foo" value="5,3,2" />
ou
<in property="foo" value="'toto','titi','tata'" />
Vous utiliserez expr
quand vous aurez un paramètre de méthode (donc une
liste de valeurs dynamiques) :
<in property="foo" expr="$liste" />
Ce paramètre doit obligatoirement contenir un tableau PHP de valeurs. Et
l'attribut expr
ne peut contenir autre chose qu'un nom de paramètre.