• Aucun résultat trouvé

Les Méthodes du Controller

Pour une liste complète des méthodes de controller avec leurs descriptions, consultez l’API CakePHP http ://api20.cakephp.org/class/controller.

Interactions avec les vues

Les Controllers interagissent avec la vue de plusieurs façons. Premièrement, ils sont capables de passer des données aux vues, en utilisant set(). Vous pouvez aussi décider quelle classe de vue utiliser, et quel fichier de vue doit être rendu à partir du controller.

Controller::set(string $var, mixed $value)

La méthode set() est la voie principale utilisée pour transmettre des données de votre controller à votre vue. Une fois set() utilisée, la variable de votre controller devient accessible par la vue : // Dans un premier temps vous passez les données depuis le controller:

$this->set(’couleur’, ’rose’);

CakePHP Cookbook Documentation, Version 2.x

// Ensuite vous pouvez les utiliser dans la vue de cette manière:

?>

Vous avez sélectionné un glaçage <?php echo $couleur; ?> pour le gâteau. La méthode set() peut également prendre un tableau associatif comme premier paramètre. Cela peut souvent être une manière rapide d’affecter en une seule fois un jeu complet d’informations à la vue. Modifié dans la version 1.3 : Les clefs de votre tableau ne seront plus infléchies avant d’être assignées à la vue (‘clef_avec_underscore’ ne devient plus ‘clefAvecUnderscore’, etc...).

$data = array(

’couleur’ => ’rose’, ’type’ => ’sucre’, ’prix_de_base’ => 23.95 );

// donne $couleur, $type, et $prix_de_base // disponible dans la vue:

$this->set($data);

L’attribut $pageTitle n’existe plus, utilisez set() pour définir le titre :

$this->set(’title_for_layout’, ’Ceci est la page titre’); Controller::render(string $action, string $layout, string $file)

La méthode render() est automatiquement appelée à la fin de chaque action exécutée par le con- troller. Cette méthode exécute toute la logique liée à la présentation (en utilisant les variables trans- mises via la méthode set()), place le contenu de la vue à l’intérieur de sa mise en page et transmet le tout à l’utilisateur final.

Le fichier de vue utilisé par défaut est déterminé par convention. Ainsi, si l’action search() de notre controller RecettesController est demandée, le fichier de vue situé dans /app/view/recettes/search.ctp sera utilisé :

class RecettesController extends AppController { // ...

public function search() {

// Rend la vue dans /View/Recettes/search.ctp

$this->render(); }

// ... }

Bien que CakePHP appellera cette fonction automatiquement à la fin de chaque action (à moins que vous n’ayez défini $this->autoRender à false), vous pouvez l’utiliser pour spécifier un fichier de vue alternatif en précisant le nom d’une action dans le controller, via le paramètre $action. Si $action commence avec un ‘/’ on suppose que c’est un fichier de vue ou un élément dont le chemin est relatif au dossier /app/View. Cela permet un affichage direct des éléments, ce qui est très pratique lors d’appels ajax.

// Rend un élément dans /View/Elements/ajaxreturn.ctp

$this->render(’/Elements/ajaxreturn’);

Vous pouvez aussi spécifier une vue alternative ou un fichier element en utilisant le troisième paramètre, $file. Le paramètre $layout vous permet de spécifier le layout de la vue qui est rendue.

Rendre une vue spécifique

Dans votre controller, vous pourriez avoir envie de rendre une vue différente que celle rendue par défaut. Vous pouvez faire cela en appelant directement render(). Une fois que vous avez appelé render() CakePHP n’essaiera pas de re-rendre la vue :

class PostsController extends AppController {

public function mon_action() {

$this->render(’fichier_personnalise’); }

}

Cela rendrait app/View/Posts/fichier_personnalise.ctp au lieu de

app/View/Posts/mon_action.ctp.

Vous pouvez aussi rendre les vues des plugins en utilisant la syntaxe suivante :

$this->render(’PluginName.PluginController/custom_file’). Par exemple :

class PostsController extends AppController {

public function my_action() {

$this->render(’Users.UserDetails/custom_file’); }

}

Cela rendrait la vue app/Plugin/Users/View/UserDetails/custom_file.ctp

Contrôle de Flux

Controller::redirect(mixed $url, integer $status, boolean $exit)

La méthode de contrôle de flux que vous utiliserez le plus souvent est redirect(). Cette méthode prend son premier paramètre sous la forme d’une URL relative à votre application CakePHP. Quand un utilisateur a réalisé un paiement avec succès, vous aimeriez le rediriger vers un écran affichant le reçu. :

public function regler_achats() {

// Placez ici la logique pour finaliser l’achat...

if ($success) {

$this->redirect(array(’controller’ => ’paiements’, ’action’ => ’remerciements’)); } else {

$this->redirect(array(’controller’ => ’paiements’, ’action’ => ’confirmations’)); }

}

Vous pouvez aussi utiliser une URL relative ou absolue avec $url :

$this->redirect(’/paiements/remerciements’));

$this->redirect(’http://www.exemple.com’);

CakePHP Cookbook Documentation, Version 2.x

Vous pouvez aussi passer des données à l’action :

$this->redirect(array(’action’ => ’editer’, $id));

Le second paramètre de la fonction redirect() vous permet de définir un code de statut HTTP accompagnant la redirection. Vous aurez peut-être besoin d’utiliser le code 301 (document déplacé de façon permanente) ou 303 (voir ailleurs), en fonction de la nature de la redirection.

Cette méthode réalise un exit() après la redirection, tant que vous ne mettez pas le troisième paramètre à false.

Si vous avez besoin de rediriger à la page appelante, vous pouvez utiliser :

$this->redirect($this->referer());

Cette méthode supporte aussi les paramètres nommés de base. Si vous souhaitez être redirigé sur une

URL comme : http://www.example.com/commandes/confirmation/produit:pizza/quantite:5 vous pouvez utiliser :

$this->redirect(array(’controller’ => ’commandes’, ’action’ => ’confirmation’, ’produit’ => ’pizza’, ’quantite’ => 5)); Un example d’utilisation des requêtes en chaînes et hashés ressemblerait à ceci :

$this->redirect(array(

’controller’ => ’commandes’, ’action’ => ’confirmation’, ’?’ => array(’produit’ => ’pizza’, ’quantite’ => 5), ’#’ => ’top’)); L’url généré serait : http://www.example.com/commandes/confirmation?produit=pizza&quantite=5#top

Controller::flash(string $message, string $url, integer $pause, string $layout)

Tout comme redirect(), la méthode flash() est utilisée pour rediriger un utilisateur vers une autre page à la fin d’une opération. La méthode flash() est toutefois différente en ce sens qu’elle affiche un message avant de diriger l’utilisateur vers une autre url.

Le premier paramètre devrait contenir le message qui sera affiché et le second paramètre une URL relative à votre application CakePHP. CakePHP affichera le $message pendant $pause secondes avant de rediriger l’utilisateur.

Si vous souhaitez utiliser un template particulier pour messages flash, vous pouvezspécifier le nom du layout dans le paramètre $layout.

Pour définir des messages flash dans une page, regardez du côté de la méthode setFlash() du compo- nent Session (SessionComponent).

Callbacks

En plus desRequest Life-cycle callbacks, CakePHP supporte aussi les callbacks liés au scaffolding.

Controller::beforeScaffold($method)

$method nom de la méthode appelée, par exemple index, edit, etc. Controller::afterScaffoldSave($method)

$method nom de la méthode appelée soit edit soit update. Controller::afterScaffoldSaveError($method)

$method nom de la méthode appelée soit edit soit update. Controller::scaffoldError($method)

$method nom de la méthode appelée , par exemple index, edit, etc...

Autres Méthodes utiles

Controller::constructClasses()

Cette méthode charge en mémoire les models requis par le controller. Cette procédure de chargement est normalement effectuée par CakePHP, mais cette méthode est à garder sous le coude quand vous avez besoin d’accéder à certains controllers depuis une perspective différente. Si vous avez besoin de CakePHP dans un script utilisable en ligne de commande ou d’autres utilisations externes, construct- Classes() peut devenir pratique.

Controller::referer(mixed $default = null, boolean $local = false)

Retourne l’URL référente de la requête courante. Le Paramètre $default peut être utilisé pour fournir une URL par défaut à utiliser si HTTP_REFERER ne peut pas être lu par les headers. Donc, au lieu de faire ceci :

class UtilisateursController extends AppController {

public function delete($id) {

// le code de suppression va ici, et ensuite...

if ($this->referer() != ’/’) {

$this->redirect($this->referer()); } else {

$this->redirect(array(’action’ => ’index’)); }

} }

vous pouvez faire ceci :

class UtilisateursController extends AppController {

public function delete($id) {

// le code de suppression va ici, et ensuite...

$this->redirect($this->referer(array(’action’ => ’index’))); }

}

Si $default n’est pas défini, la fonction se met par défaut sur à la racine (root) de votre domaine - ‘/’.

Le paramètre $local si il est défini à true, restreint les URLs se référant au serveur local. Controller::disableCache()

Utilisée pour indiquer au navigateur de l’utilisateur de ne pas mettre en cache le résultat de la requête courante. Ceci est différent du système de cache de vue couvert dans le chapitre suivant.

Les en-têtes HTTP envoyés à cet effet sont :

Expires: Mon, 26 Jul 1997 05:00:00 GMT Last-Modified: [current datetime] GMT

Cache-Control: no-store, no-cache, must-revalidate Cache-Control: post-check=0, pre-check=0

Pragma: no-cache

Controller::postConditions(array $data, mixed $op, string $bool, boolean $exclusive)

Utilisez cette méthode pour transformer des données de formulaire, transmises par POST (depuis les inputs du Helper Form), en des conditions de recherche pour un model. Cette fonction offre un rac- courci appréciable pour la construction de la logique de recherche. Par exemple, un administrateur

CakePHP Cookbook Documentation, Version 2.x

aimerait pouvoir chercher des commandes dans le but de connaître quels produits doivent être embal- lés. Vous pouvez utiliser les Helpers Form et Html pour construire un formulaire rapide basé sur le model Commande. Ensuite une action du controller peut utiliser les données postées par ce formulaire pour construire automatiquement les conditions de la recherche :

public function index() {

$conditions = $this->postConditions($this->request->data);

$commandes = $this->Commande->find(’all’, compact(’conditions’));

$this->set(’commandes’, $orders); }

Si $this->data[‘Commande’][‘destination’] vaut “Boulangerie du village”, postCon- ditions convertit cette condition en un tableau compatible avec la méthode Model->find(). Soit dans notre cas, array("Commande.destination" => "Boulangerie du village"). Si vous voulez utiliser un opérateur SQL différent entre chaque terme, remplacez-le en utilisant le second paramètre : /* Contenu de $this->request->data array( ’Commande’ => array( ’nb_items’ => ’4’, ’referrer’ => ’Ye Olde’ )

) */

// Récupérons maintenant les commandes qui ont au moins 4 items et contenant ’Ye Olde’

$conditions = $this->postConditions(

$this->request->data,

array(

’nb_items’ => ’>=’, ’referrer’ => ’LIKE’ )

);

$commandes = $this->Commande->find(’all’, compact(’conditions’));

Le troisième paramètre vous permet de dire à CakePHP quel opérateur booléen SQL utiliser entre les conditions de recherche. Les chaînes comme ‘AND’, ‘OR’ et ‘XOR’ sont des valeurs possibles. Enfin, si le dernier paramètre est défini à vrai et que $op est un tableau, les champs non-inclus dans $op ne seront pas inclus dans les conditions retournées.

Controller::paginate()

Cette méthode est utilisée pour paginer les résultats retournés par vos models. Vous pouvez définir les tailles de la page, les conditions à utiliser pour la recherche de ces données et bien plus. Consultez la sectionpaginationpour plus de détails sur l’utilisation de la pagination.

Controller::requestAction(string $url, array $options)

Cette fonction appelle l’action d’un controller depuis tout endroit du code et retourne les données associées à cette action. L’$url passée est une adresse relative à votre application CakePHP (/nom- ducontroleur/nomaction/parametres). Pour passer des données supplémentaires au controller desti- nataire ajoutez le tableau $options.

Note : Vous pouvez utiliser requestAction() pour récupérer l’intégralité de l’af- fichage d’une vue en passant la valeur ‘return’ dans les options : requestAction($url, array(’return’)). Il est important de noter que faire un requestAction en utilisant ‘return’ à partir d’une méthode d’un controller peut entraîner des problèmes de fonctionnement dans les script et tags css.

Warning : Si elle est utilisée sans cache, la méthode requestAction peut engendrer des faibles performances. Il est rarement approprié de l’utiliser dans un controller ou un model.

requestActionest plutôt utilisé en conjonction avec des éléments (mis en cache) - comme moyen

de récupérer les données pour un élément avant de l’afficher. Prenons l’exemple de la mise en place d’un élément “derniers commentaires” dans le gabarit (layout). Nous devons d’abord créer une méth- ode de controller qui retourne les données :

// Controller/CommentsController.php

class CommentsController extends AppController {

public function latest() {

if (empty($this->request->params[’requested’])) {

throw new ForbiddenException(); }

return $this->Comment->find(’all’, array(’order’ => ’Comment.created DESC’, ’limit’ => 10)); }

}

Vous devriez toujours inclure des vérifications pour vous assurer que vos méthodes de requestAction sont en fait originaires de requestAction. Ne pas le faire va autoriser les méthodes requestAction à être directement accessible d’une URL, ce qui est généralement non souhaité.

Si nous créons un élément simple pour appeler cette fonction : // View/Elements/latest_comments.ctp

$comments = $this->requestAction(’/comments/latest’);

foreach ($comments as $comment) {

echo $comment[’Comment’][’title’]; }

On peut ensuite placer cet élément n’importe où pour obtenir la sortie en utilisant :

echo $this->element(’latest_comments’);

Ecrit de cette manière, dès que l’élément est affiché, une requête sera faite au controller pour obtenir les données, les données seront traitées, et retournées. Cependant, compte tenu de l’avertissement ci-dessus il vaut mieux utiliser des éléments mis en cache pour anticiper des traitements inutiles. En modifiant l’appel à l’élément pour qu’il ressemble à ceci :

echo $this->element(’latest_comments’, array(), array(’cache’ => true)); L’appel à requestAction ne sera pas effectué tant que le fichier de vue de l’élément en cache existe et est valide.

De plus, requestAction prend désormais des urls basées sur des tableau dans le style de cake :

CakePHP Cookbook Documentation, Version 2.x

echo $this->requestAction(

array(’controller’ => ’articles’, ’action’ => ’featured’),

array(’return’) );

Cela permet à l’appel de requestAction d’éviter l’utilisation de Router : :url ce qui peut améliorer la performance. Les url basées sur des tableaux sont les mêmes que celles utilisées par HtmlHelper::link() avec une seule différence. Si vous utilisez des paramètres nommés ou passés dans vos url, vous devez les mettre dans un second tableau et les inclures dans la clé cor- recte. La raison de cela est que requestAction fusionne seulement le tableau des arguments nommés avec les membres du tableau de Controller : :params et ne place pas les arguments nommés dans la clé ‘named’. Des membres supplémentaires dans le tableau $option va aussi être rendu disponible dans le tableau Controller : :params de l’action requêtée

echo $this->requestAction(’/articles/featured/limit:3’);

echo $this->requestAction(’/articles/view/5’); En array dans requestAction serait ainsi :

echo $this->requestAction(

array(’controller’ => ’articles’, ’action’ => ’featured’),

array(’named’ => array(’limit’ => 3)) );

echo $this->requestAction(

array(’controller’ => ’articles’, ’action’ => ’view’),

array(’pass’ => array(5)) );

Note : Contrairement aux autres places où les urls en tableau sont analogues aux urls en chaîne de caractère, requestAction les traite différemment.

Quand vous utilisez une url en tableau en conjonction avec requestAction(), vous devez spécifier tous les paramètres dont vous aurez besoin dans l’action requêtée. Ceci inclut les paramètres comme $this->request->data. En plus de passer tous les paramètres requis, les paramètres nommés et passés doivent être faits dans le second tableau comme vu ci-dessus.

Controller::loadModel(string $modelClass, mixed $id)

La fonction loadModel devient pratique quand vous avez besoin d’utiliser un model qui n’est pas le model du controller par défaut ou un de ses models associés :

$this->loadModel(’Article’);

$recentArticles = $this->Article->find(’all’, array(’limit’ => 5, ’order’ => ’Article.created DESC’));

$this->loadModel(’User’, 2);

$user = $this->User->read();