Bonjour,
Dans mon framework PHP, je dispose d'une classe Model simple, qui sert de base à tous mes modèles :
Je voudrais ajouter des fonctionnalités à mes modèles, de manière optionnelle et en réutilisant mon code.
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10
11 abstract class Model { public function save() { /* Sauvegarde les données en base */ } public function delete() { /* Supprime les données en base */ } }
Mon idée est d'utiliser le pattern Decorator.
Je définis une classe Decorator abstraite :
J'aurais par exemple un Decorator permettant de gérer un modèle multilingue, en ajoutant simplement un suffixe (_en, _fr) aux noms des champs.
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10
11 abstract class Decorator { $protected $model; public function __construct( $model ) { $this->model = $model; } public function __call( $method, $args ) { return call_user_func_array( array( get_class( $this->model ), $method), $args ); } }
Ou Decorator permettant de gérer une corbeille :
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20 class TranslateDecorator extends Decorator { public $language; public $translated; public function __construct() { parent::__construct(); if ( !empty( $_SESSION['language'] ) ) { $this->language = $_SESSION['language']; } } public function __set( $name, $value ) { if ( in_array( $name, $this->translated ) ) { $name .= '_' . $this->language; } $this->model->name = $value; } }
Je définis mes modèles :
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19 class TrashDecorator extends Decorator { /* Surcharge de delete() */ public function delete() { $this->model->is_deleted = 1; $this->model->save(); } public function unDelete() { $this->model->is_deleted = 0; $this->model->save(); } public function emptyTrash() { foreach ( $this->model->findAll() as $model ) { $model->delete(); } } }
Ensuite je peux instancier mon modèle et ajouter mes decorators :
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3 class ArticleModel extends Model { // Définition de la classe }
Je trouve ce système efficace, simple et élégant.
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10 $article = new TrashDecorator( new TranslateDecorator( new ArticleModel ) ); $article->translated = array( 'title', 'text' ); $article->language = 'fr'; $article = $article->findOne( 4 ); $article->title = 'Mon titre'; $article->save(); $article->delete(); $article->emptyTrash();
Que pensez-vous de cette approche ?
Partager