Multiple Site Setup in Phalcon

Dear friends, this is my first blog and I am excited to share some of my recent learnings in Phalcon with you all. In this blog I would like to share process for multiple site setup in Phalcon. It is an easy process and fun to try!

Let’s start with understanding what Phalcon is?

"Phalcon is a high-performance PHP Web Framework based on the model-view-controller (MVC) pattern. Unlike most PHP frameworks, Phalcon is implemented as a web server extension written in Zephir and C, aiming to boost execution speed, reduce resource usage, and handle more HTTP requests per second than comparable frameworks written primarily in PHP. One drawback of this approach is that root/administrative access is required on the server to install Phalcon by building a custom binary or using a precompiled one."

For more info check on https://en.wikipedia.org/wiki/Phalcon_(framework)

In short, Phalcon is an open-source PHP framework built as a C-extension. It is available under the new BSD License.

Features of Phalcon

  1. Low Overhead - Low memory consumption and cpu compared to traditional frameworks
  2. MVC & HMVC - Modules, components, models, views and controllers
    - Build single and multi-module applications with ease and pleasure, using the file structure, scheme and patterns.
  3. Dependency Injection - Phalcon\Di is a component implementing Dependency Injection and Location of services and it’s itself a container for them. Since Phalcon is highly decoupled, Phalcon\Di is essential to integrate the different components of the framework.
  4. Autoloader - It provides the autoloading mechanism of php
  5. Router - Phalcon\Mvc\Router provides advanced routing capabilities

Where we used Phalcon?

Phalcon used as front end for a high traffic newspaper site to improve performance and integrate with an existing Drupal backend. As there are multiple newspaper sites running with a single code base, we needed a similar approach for our Phalcon front end as well.

Below is a simple diagram depicting the overall architecture and where Phalcon was used.

 Multiple Site Setup in Phalcon

Phalcon Basics

Folder Structure

Here we discuss the file structure of Phalcon. Phalcon does not impose a particular file structure for application development. Due to the fact that it is loosely coupled, you can implement Phalcon powered applications with a file structure you are most comfortable to using.

We suggest this very simple structure for files which is best recommended for MVC.

  sitename/

  app/

  controllers/ 

  models/ 

  views/

  public/

  css/

  img/

  js/

Dependency Injection

This section shows how to create dependency injection. This is needed to ensure extending functionality or class. (This is similar to how we extend Drupal 8 classes in Symphony).

  //Create the Dependency Injector Container

  $di = new Phalcon\DI();

  //Register classes, functions, components

  $di->set("request", new Phalcon\Http\Request());

  ..

  //Use anywhere else in code

  $request = $di->getShared("request")

Autoloader

This to register namespaces, again similar to registering namespace in Drupal 8 and include function in Drupal 7

  use Phalcon\Loader;

  // Creates the autoloader

  $loader = new Loader();

  // Register some namespaces

  $loader->registerNamespaces(

  array (

  "Example\Base" => "vendor/example/base/",

  "Example\Adapter" => "vendor/example/adapter/",

  "Example" => "vendor/example/"

  )

  );

  // Register autoloader

  $loader->register();

Router

This is backbone of any application, redirecting the user path to associated controller. Similar to routers in Drupal 8 and menu callbacks in Drupal 7.

  // Create the router

  $router = new \Phalcon\Mvc\Router();

  //Define a route

  $router->add(

  "/admin/users/my-profile",

  array(

  "controller" => "users",

  "action" => "profile",

  )

  );

Implementing Multi site with Phalcon:

If we need to set multiple sites in phalcon, we set up some common functionalities in phalcon. We would have some common models, controllers, views that should be put into common folder and we have some site specific models, controllers, views that to be put into specific folder.

Some benefits would be:

  1. If I need anything to be changed in one particular site I should be able to change in that particular site without affecting other sites.
  2. Just by creating independent/ single models and controllers we can extend it to other sites.
  3. If I need to change anything in all sites then I could be able to change it in a single place.

The structure is also inspired by Drupal multisite setup and Joomla template system. Detailed structure

├── apps
    │   ├── common (register namespace as common/controller)
    │   │   ├── controllers        
    │   │   │   ├── IndexController.php 
    │   │   ├── models  (register namespace as common/models)           
    │   │   │   └── Index.php  
    │   │   └── views
    │   │       ├── user
    │   │       │   └── login.volt
    │   │       └── registration
    │   │       |    └── register.volt
    |   |       └──index.volt   
    │   ├── example.com
    │   │   ├── controllers
    │   │   │   ├── IndexController.php (extend common/controller) 
    │   │   │   └── UsersController.php   Site Specific Controller
    │   │   ├── models
    │   │   │   └── Index.php (extend Common/Model)
    |   |   |   └── Users.php (Site Specific Model)
    │   │   └── views
    │   │       └── users             
    │   │           └── index.volt
    │   ├── example2.com
    │   │   ├── controllers
    │   │   │   ├── IndexController.php (extend common/controller)
    │   │   │   ├── UsersController.php (extend Common/Controller)
    │   │   │   └── RegisterController.php   Site Specific Controller
    │   │   ├── models
    │   │   │   └── Users.php (extend Common/Model)
    |   |   |   └── Register.php (Site Specific Model)
    │   │   └── views
    │   │       └── sitespecific        
    │   │           └── index.volt
    └── public
        └── example.com   (site specific theme)
        └── example2.com  (site specific theme)
        └── index.php

* Register namespace in public->index.php

// aspects of index.php to implement multisite

 <?php

        use Phalcon\Loader;

        // ...

        $loader = new Loader();

        $loader->registerDirs(

            [

               'Common\Controller' => '../app/common/controllers',

                'Common\Model' => '../app/common/models',

            ]

        );

        $loader->register();

        

        *setting a database connection

        

        <?php

        use Phalcon\Db\Adapter\Pdo\Mysql as DbAdapter;

        // Setup the database service

        $di->set(

            "db",

            function () {

                return new DbAdapter(

                    [

                        "host"     => "localhost",

                        "username" => "root",

                        "password" => "secret",

                        "dbname"   => "test_db",

                    ]

                );

            }

        );

Watch Out for my next blogs on handling Session in Phalcon, Best practices and designing MongoDB tables, Drupal to MongoDB integration. Interested, post your comment and I can respond with a blog

.