CakePHP’s builtin scaffolding is great but sometimes I wish it would do more or behave a little differently. Until recently, I assumed this couldn’t be accomplished with the way scaffolding was baked in. Thanks to the clever way CakePHP handles includes, we can easily use our own scaffolding implementation by adding 2 lines to AppController.
In this tutorial we will built a scaffolding plugin that is aware of the TreeBehavior. If you use scaffolding for a Tree model the parent dropdown in the add/edit view is unordered and confusing.

Non-indented Parent Association dropdown box
In our scaffolding plugin we will generate ordered/indented dropdowns for all belongsTo associations that implement the TreeBehavior. This is accomplished by calling Model->generateTreeList() instead of Model->find(‘list’). Here is an example.

Indented Parent dropdown box
To get started you want to first setup our own scaffolding implementation housed inside a plugin.
-
Create a new CakePHP plugin
sudo cake bake plugin TreeAwareScaffold
Note: The name TreeAwareScaffold is just for illustration purposes. You can name your plugin whatever you want, but keep it descriptive. Oh, and don’t forget to share it with others via github.
-
Create the Scaffold class
Copy the core Scaffold class into your plugin as a starting point.
cp lib/Cake/Controller/Scaffold.php app/Plugin/TreeAwareScaffold/Controller/
Modify the Scaffold class to use the ScaffoldView class from your plugin (we will create it in the next step). Change line 147 to…
$this->controller->viewClass = 'TreeAwareScaffold.Scaffold';
-
Extend the Scaffold class to use generateTreeList() for Tree enabled models
We want scaffolding to generate a nice indented dropdown list for our add and edit scaffold views but only for belongsTo associations that have the Tree behavior
enabled.To accomplish this, add the following method to app/Plugin/TreeAwareScaffold/Controller/Scaffold.php
/** * Detect if Tree Behavior is enabled on $Model * * @param mixed $Model */ protected function _isTree( $Model ) { if ( $Model->hasMethod('generateTreeList') ) { return true; } return false; }
Next, Change line 274 of app/Plugin/TreeAwareScaffold/Controller/Scaffold.php from…
$this->controller->set($varName, $this->ScaffoldModel->{$assocName}->find('list'));
to the following…
if ( $this->_isTree( $this->ScaffoldModel->{$assocName} ) ) { $this->controller->set($varName, $this->ScaffoldModel->{$assocName}->generateTreeList(null, null, null, '---') ); } else { $this->controller->set($varName, $this->ScaffoldModel->{$assocName}->find('list')); }
-
Hide lft,rght fields in scaffolding
The lft,rght columns are characteristic of Models with the Tree behavior enabled. We don’t really want to see or edit them so the following will hide them in our scaffold views.
Note: Manually editing lft,rght field values is the primary reason for inconsistent tree tables so hiding them is a great idea!
Replace line 137 of app/Plugin/TreeAwareScaffold/Controller/Scaffold.php…
$scaffoldFields = array_keys($this->ScaffoldModel->schema());
with the following…
/** * Hide the lft,rght fields for Tree Models * this will not work if left and right fields * are named anything other than lft,left,rght,right */ if ( $this->_isTree( $this->ScaffoldModel ) ) { $fields = $this->ScaffoldModel->schema(); unset($fields['lft']); unset($fields['left']); unset($fields['rght']); unset($fields['right']); $scaffoldFields = array_keys( $fields ); } else { $scaffoldFields = array_keys($this->ScaffoldModel->schema()); }
-
Create the ScaffoldView class and scaffolding view templates
Copy the core Scaffold View class into your plugin as a starting point.
cp lib/Cake/View/ScaffoldView.php app/Plugin/TreeAwareScaffold/View/
Copy the core scaffolding views(form.ctp, index.ctp, view.ctp) into your plugin.
cp -r lib/Cake/View/Scaffolds app/Plugin/TreeAwareScaffold/View/
-
Tell ScaffoldView to load scaffolding views from the plugin
Edit Plugin/TreeAwareScaffold/View/ScaffoldView.php, changing line 67-68 from…
$names[] = $this->viewPath . DS . $subDir . $scaffoldAction; $names[] = 'Scaffolds' . DS . $subDir . $name;
to the following…
$names[] = $this->viewPath . DS . $subDir . $scaffoldAction; $names[] = '..' . DS . 'Plugin' . DS . 'TreeAwareScaffold' . DS . 'View' . DS .'Scaffolds' . DS . $subDir . $name; $names[] = 'Scaffolds' . DS . $subDir . $name;
That’s it! You are ready to test drive your new scaffolding plugin.
Part 2: Using TreeAwareScaffold in your app
-
Enable the TreeAwareScaffold plugin
Add the following line to app/Config/bootstrap.php
CakePlugin::load('TreeAwareScaffold');
-
Configure AppController to use the new Scaffolding plugin
App::uses('Scaffold', 'TreeAwareScaffold.Controller'); App::uses('ScaffoldView', 'TreeAwareScaffold.View');
-
Create a Category Model and enable the Tree behavior
app/Model/Category.php
<?php App::uses('AppModel', 'Model'); class Category extends AppModel { public $displayField = 'name'; public $actsAs = array('Tree'); public $hasMany = array( 'ChildCategory'=>array( 'className'=>'Category', 'foreignKey'=>'parent_id', 'dependent'=>true ) ); public $belongsTo = array( 'ParentCategory'=>array( 'className'=>'Category', 'foreignKey'=>'parent_id' ) ); }
-
Create the associated table in MySQL
CREATE TABLE IF NOT EXISTS `categories` ( `id` int(10) unsigned NOT NULL AUTO_INCREMENT, `name` varchar(128) NOT NULL, `parent_id` int(10) unsigned DEFAULT NULL, `lft` int(10) unsigned DEFAULT NULL, `rght` int(10) unsigned DEFAULT NULL, PRIMARY KEY (`id`) ) ENGINE=InnoDB DEFAULT CHARSET=utf8 AUTO_INCREMENT=1 ;
-
Create a CategoriesController with Scaffolding
<?php App::uses('AppController', 'Controller'); class CategoriesController extends AppController { public $scaffold; public $paginate = array( 'order'=>array( 'Category.lft'=>'asc' ), 'limit'=>100 ); }
More Scaffold Plugins
A list of scaffolding plugins that you can use in your CakePHP Application. If you have created a scaffolding plugin, let us hear about in the comments below and I will add it to this list.
TreeAwareScaffold – If you want to try out the plugin we created in this tutorial without following along step-by-step you can download the plugin from github!
Keywords:
- pronique com
- cakephp generate list scaffolding
- cakephp 2 1 tutorial
- cakephp scaffold
- installer cakephp-mongodb-template
- App::Import(Model Aro )
- how to scaffolds in cakephp2 x
- cakephp scaffolding
- plugins in cakephp2
- cakephp 2 x tutorial