Building WordPress Plugins with Object Oriented Concept
The basic approach in the creation of plugins and themes with the OOP concept is consistent use of the MVC model together with several design patterns. The brightest example of such an approach is the Just Custom Fields plugin. By checking the plugin’s latest code base, you can better understand the principle use of the OOP when creating themes and plugins.
Let’s begin by reviewing the file structure of the plugin and its contents.
The plugin represents the following file structure and folders:
- assets – fonts, styles, js, etc.
- controllers – controllers
- core – basic components, classes, interfaces
- functions – files of support functions, helpers
- models – models
- views – views
- just-custom-fields.php – the main plugin singleton class
The main file of the plugin is just-custom-fields.php. It defines PSR-4 Autoload support for plugin namespaces (include of “
/core/Autoload.php“) and includes helper functions files from “/functions/” folder. All components of the plugin (classes of components, controllers, models) follow the same unique namespace base
\jcf, which point to the root of the plugin folder.
In the just-custom-fields.php file you can find the declaration of the main \JustCustomFields class. \JustCustomFields extends from an abstract Singleton class; its name speaks for itself. The Singleton class is constructed using the Singleton design pattern. It means that we can have only one object of \JustCustomFields in the memory. It helps us avoid duplicating this object when activating our plugin from the website’s admin panel and continues to aid us with the development and support. At the end of the file, we create the object of this class and this object registers all necessary components which are required in the plugin.
One more WordPress-specific pattern is used in every class of the plugin: we register all WordPress hooks in __construct() method, and when a hook is triggered it calls a corresponding class method of existing objects. We call it “Constructor Hook-Injection“. In order to register hooks for some component, all you need is to create an object of the component class. After, you can be sure that all methods will be called in the right places. Each class registers only the hooks required for the component its describing.
When initializing the main object of JustCustomFields, we create objects for the controllers and based on our hooks-injection pattern they register everything they need automatically for every part of the plugin.
As stated earlier, the plugin uses the MVC concept as well. This means that the plugin has controllers, models, and views. The main principle of MVC is the existence of a separation between logic, data layer, and views.
Controllers process all new requests added by our plugin. Each controller registers new endpoints required for specific sections. It can be a WordPress Admin menu item, AJAX action, or a custom rewrite rule. As stated earlier, all these requests are registered in the controller constructor with corresponding hooks. Each request corresponds to separate methods inside the class. Further, controller methods which are attached to hooks in the constructor collect in themselves all the necessary components, models for operation with a data layer, and render views in order to display the action result.
Models work with data layers. Most common data layers are filesystem and database. If you build a plugin based on a 3rd-party service, then the model can do requests to this service. Models have code to validate, create, and update different data inside the plugin. Usually, one Model corresponds to a specific section or entity.
Views are normal html/php templates. Usually, they are grouped in folders based on the controllers they are called from.
Based on everything said above, we can draw a conclusion that the plugin has the main JustCustomFields object, which is comprised of all the remaining auxiliary controllers. All controllers are placed in a separate “controllers” folder. Each controller contains WordPress hooks, which are collected in the constructor. Therefore, methods of controllers attached to these hooks work with models, components, and views. Models are stored in the “models” folder. All models are inherited from the \jcf\core\Model class, which contains the general methods for all models. Views are stored in the “views” folder. All files from the assets folder are connected to hooks and methods of controllers.
The JustCustomFields plugin gives you the possibility to create fields and store their settings in the database and files. This is made possible when the Factory design pattern is used. Therefore, in order to work with the storage, we have created a special class \core\DataLayerFactory, which decides what storage is used in the application and initializes corresponding classes for it. This type of approach gives you more flexible application support and the ability to easily create new storage types.
Let’s sum up the results of our article. In order to use OOP in the plugin, we use the MVC model. Controllers and Models are main classes which build the plugin architecture. Constructor Hook-Injection patterns help us keep WordPress integration in one place, which makes it easy to find. By using the Singleton and Factory design patterns we keep our code clean, accurate, and load corresponding parts only when we need them.