Infinite dynamic Multi-level nested category with Codeigniter and MySQL


Here I will show you how to create infinite multi-level nested categories with Codeigniter and MySQL. In my previous tutorial Infinite dynamic Multi-level nested category with PHP and MySQL , I wrote how to build a nested multilevel categories. So I am again going to write the same tutorial but this time with Codeigniter 3 framework.


Codeigniter 3.1.11, PHP 7.4.3, MySQL 8.0.17, Apache 2.4

Project Directory Setup

It’s assumed that you have setup Apache, PHP and Codeigniter in Windows system.

Now I will create a project root directory called codeIgniter-mysql-infinite-level-nested-category under the Apache server’s htdocs folder.

Now move all the directories and files from CodeIgniter framework into codeIgniter-mysql-infinite-level-nested-category directory.

I may not mention the project root directory in subsequent sections and I will assume that I am talking with respect to the project’s root directory.

Edit the file application/config/autoload.php and

Change the configuration values as shown below. I do not want to load every time the repeatedly used helper functions, so it is always good to load those things once in order to use them uniformly throughout the application.

$autoload['libraries'] = array('database');
$autoload['helper'] = array('url');

Configure Database

Go to location /application/config/database.php file and change database parameter values for below parameters. Make sure to have your correct database name.

$db['default'] = array(
	'dsn'	=> '',
	'hostname' => 'localhost',
	'username' => 'root',
	'password' => 'root',
	'database' => 'roytuts',
	'char_set' => 'utf8mb4',
	'dbcollat' => 'utf8mb4_unicode_ci',

MySQL Table

Create a MySQL table – category under roytuts database in MySQL server.

CREATE TABLE `category` (
  `category_id` int unsigned NOT NULL AUTO_INCREMENT,
  `category_name` varchar(50) NOT NULL,
  `category_link` varchar(255) NOT NULL,
  `parent_id` int unsigned NOT NULL DEFAULT '0',
  `sort_order` int NOT NULL DEFAULT '0',
  PRIMARY KEY (`category_id`),
  UNIQUE KEY `unique` (`category_name`)

Dump Data

Dump some data into database table – category. It will help you to test the application right away once coding is done.

insert  into 

Model Class

Create a model file categorymodel.php under application/models directory with the below source code.

This model class connects to database and fetches the required records from category table. This class has also a function that formats the nested category into multiple levels.


if (!defined('BASEPATH'))
    exit('No direct script access allowed');

 * Description of categorymodel
 * @author
class CategoryModel extends CI_Model {

    private $category = 'category';

    function __construct() {

    public function category_menu() {
        // Select all entries from the menu table
        $query = $this->db->query("select category_id, category_name, category_link,
            parent_id from " . $this->category . " order by parent_id, category_link");

        // Create a multidimensional array to contain a list of items and parents
        $cat = array(
            'items' => array(),
            'parents' => array()
        // Builds the array lists with data from the menu table
        foreach ($query->result() as $cats) {
            // Creates entry into items array with current menu item id ie. $menu['items'][1]
            $cat['items'][$cats->category_id] = $cats;
            // Creates entry into parents array. Parents array contains a list of all items with children
            $cat['parents'][$cats->parent_id][] = $cats->category_id;

        if ($cat) {
            $result = $this->build_category_menu(0, $cat);
            return $result;
        } else {
            return FALSE;

    // Menu builder function, parentId 0 is the root
    function build_category_menu($parent, $menu) {
        $html = "";
        if (isset($menu['parents'][$parent])) {
            $html .= "<ul>\n";
            foreach ($menu['parents'][$parent] as $itemId) {
                if (!isset($menu['parents'][$itemId])) {
                    $html .= "<li>\n<a href='" . base_url() . 'index.php/category/index/' . $menu['items'][$itemId]->category_link . "'><span>" . $menu['items'][$itemId]->category_name . "</span></a>\n</li>\n";
                if (isset($menu['parents'][$itemId])) {
                    $html .= "<li>\n<a class='parent' href='" . base_url() . 'index.php/category/index/' . $menu['items'][$itemId]->category_link . "'><span>" . $menu['items'][$itemId]->category_name . "</span></a>\n";
                    $html .= $this->build_category_menu($itemId, $menu);
                    $html .= "</li>\n";
            $html .= "</ul>\n";
        return $html;


/* End of file categorymodel.php */
/* Location: ./application/models/categorymodel.php */

Controller Class

Create a controller file category.php under application/controllers with the following source code.

The controller class is responsible for handling request and response from clients and sends the data to UI (User Interface) or appropriate view file.


if (!defined('BASEPATH'))
    exit('No direct script access allowed');

 * Description of category
 * @author
class Category extends CI_Controller {

    function __construct() {
        $this->load->model('categorymodel', 'cat');

    function index() {
        $data['categories'] = $this->cat->category_menu();
        $this->load->view('category', $data);


/* End of file category.php */
/* Location: ./application/controllers/category.php */

View File

Create a view file category.php under application/views. The view file is responsible for displaying data on UI.

<!DOCTYPE html>
        <meta charset="UTF-8">
			echo $categories;

Configure Route

Modify file application/config/routes.php file as shown below to override the default controller here.

$route['default_controller'] = 'category';

Testing the Application

If everything is fine then run the application by hitting the URL http://localhost/codeIgniter-mysql-infinite-level-nested-category/. You will get the output in the browser as shown in the below image:

Source Code


That’s all. Thanks for reading.

1 thought on “Infinite dynamic Multi-level nested category with Codeigniter and MySQL

Leave a Reply

Your email address will not be published. Required fields are marked *