In the previous CakePHP 4.x tutorial, we familiarized ourselves with CakePHP installation, configuration, database creation, data lists, and basic functions. We will now take a look at CakePHP’s powerful features by creating a blog post application as an example.
The basic configuration and list of blog posts was explained in the previous tutorial. Before you start any advanced lessons, you can read the CakePHP 4.x Tutorial for Beginners. In this advanced Cakephp tutorial, we will implement the add, edit, and delete blog post functions.
Create File in src/controller/PostsController.php
The index() function fetch posts data from the database and displays the posts. Now let’s allow new posts to be added.
You need to load FlashComponent into PostsController to see success and error messages. First, create an add() action in PostsController. The add() action returns a form view for adding a post and tries to save data using the Posts model when the HTTP request method is POST. This action is also used to show validation errors or other warnings.
src/controller/PostsController.php
<?php // src/Controller/PostsController.php namespace App\Controller; use App\Controller\AppController; use Cake\Event\EventInterface; use Cake\Datasource\FactoryLocator; class PostsController extends AppController{ public $postsTableObj; public function beforefilter(EventInterface $event){ parent::beforefilter($event); $this->postsTableObj = FactoryLocator::get('Table')->get('Posts'); } public function index(){ $posts = $this->postsTableObj->find(); $this->set(compact('posts')); } public function add(){ $postEnt = $this->postsTableObj->newEmptyEntity(); if ($this->request->is('post')) { $postData = $this->request->getData(); $posts = $this->postsTableObj->patchEntity($postEnt, $postData); if ($this->postsTableObj->save($posts)) { $this->Flash->success(__('Your post has been saved.')); return $this->redirect(['controller'=>'Posts','action' => 'index']); }else{ $this->Flash->error(__('Unable to add your post.')); return $this->redirect(['controller'=>'Posts','action' => 'add']); } } $this->set(compact('postEnt', $postEnt)); } }
newEmptyEntity() creates a new object and passes it to the save() method in the Table class.patchEntity() combines an array of raw data into an existing object.
Fetch and Display Posts Records
templates/Posts/index.php
<div class="container"> <div class="row"> <div class="col-md-12"> <h2 class="text-center" style="margin-top:50px;">Posts View</h2> <table class="table"> <thead> <tr> <th>Id</th> <th>Title</th> <th>Description</th> <th>Created</th> <th>Updated</th> <th>Action</th> </tr> </thead> <tbody> <?php foreach ($posts as $post) { ?> <tr> <td><?php echo $post->id ?></td> <td><?php echo $post->title ?></td> <td><?php echo $post->description ?></td> <td><?php echo date('d-M-Y', strtotime($post->created)) ?></td> <td><?php echo date('d-M-Y', strtotime($post->updated)) ?></td> <td> <a href="<?php echo $this->Url->build(['controller'=>'Posts', 'action'=>'edit', $post->id]) ?>">Edit</a> <a href="<?php echo $this->Url->build(['controller'=>'Posts', 'action'=>'delete', $post->id]) ?>" onclick="return confirm('Are you sure you want to delete this item?');">Delete</a> </td> </tr> <?php } ?> </tbody> </table> </div> </div> </div>
Output

Create Model Validation
To validate data, you need to create a src/Model/Table/PostsTable.php model and define validation rules. The validationDefault () method tells CakePHP how your data should be validated when the write method is called. Here we have given the title and the description should not be empty.
src/Model/Table/PostsTable.php
<?php namespace App\Model\Table; use Cake\ORM\Table; use Cake\Validation\Validator; class PostsTable extends Table { public function initialize(array $config): void { $this->addBehavior('Timestamp', [ 'events' => [ 'Model.beforeSave' => [ 'created' => 'new', 'updated' => 'always' ] ] ]); } public function validationDefault(Validator $validator): Validator { $validator ->notEmptyString('title') ->notEmptyString('description'); return $validator; } }
Create View File in
templates/Posts/add.php
<div class="text-center" style="margin-top: 50px;"> <h4>Add a Pots</h4> </div> <div class="container"> <div class="row"> <div class="col-sm-3"></div> <div class="col-sm-6"> <?php echo $this->Form->create($postEnt, ['name'=>'add_post', 'class'=>'was-validated']) ?> <div class="form-group"> <?php echo $this->Form->control('title', ['type'=>'text', 'class'=>'form-control','placeholder'=>'Enter title','required'=>true]);?> </div> <div class="form-group"> <?php echo $this->Form->control('description', ['type'=>'text', 'class'=>'form-control','placeholder'=>'Enter description','required'=>true]);?> </div> <button type="submit" class="btn btn-success" style="float: right;">Save</button> <?php echo $this->Form->end() ?> </div> </div> </div>
output

Now update and Edit Posts
Create edit method in PostsController
edit() method pass an $id parameter to access an existing data.
PostsController/edit.php
public function edit($id=null){ $postEnt = $this->postsTableObj->get($id); if ($this->request->is(['post', 'put'])) { $editPost = $this->request->getData(); $this->postsTableObj->patchEntity($postEnt, $editPost); if ($this->postsTableObj->save($postEnt)) { $this->Flash->success(__('Your post has been updated.')); return $this->redirect(['controller'=>'Posts','action' => 'index']); }else{ $this->Flash->error(__('Unable to update your post.')); return $this->redirect(['controller'=>'Posts','action' => 'add']); } } $this->set(compact('postEnt', $postEnt)); }
View
template/Posts/edit.php
<!-- src/Template/Posts/edit.ctp --> <div class="text-center" style="margin-top: 50px;"> <h4>Edit Pots</h4> </div> <div class="container"> <div class="row"> <div class="col-sm-3"></div> <div class="col-sm-6"> <?php echo $this->Form->create($postEnt, ['name'=>'add_post', 'class'=>'was-validated']) ?> <div class="form-group"> <?php echo $this->Form->control('title', ['type'=>'text', 'class'=>'form-control','placeholder'=>'Enter title','required'=>true]);?> </div> <div class="form-group"> <?php echo $this->Form->control('description', ['type'=>'text', 'class'=>'form-control','placeholder'=>'Enter description','required'=>true]);?> </div> <button type="submit" class="btn btn-success" style="float: right;">Update</button> <?php echo $this->Form->end() ?> </div> </div> </div>
Edit output

Deleting Post
Postscontroller/delete.php
public function delete($id=null){ $postEnt = $this->postsTableObj->get($id); if ($this->postsTableObj->delete($postEnt)) { $this->Flash->success(__('Post has been deleted.')); return $this->redirect(['controller'=>'Posts','action' => 'index']); }else{ $this->Flash->error(__('Unable to delete your Post.')); return $this->redirect(['controller'=>'Posts','action' => 'index']); } }
You can always support by sharing on social media or recommending my blog to your friends and colleagues. If you have any suggestions / problems about this tutorial, please comment on the form below.😊