Drupal development concepts
What can Drupal custom code do?
- Alter existing or add a new functionality
- Integrate with third party systems
- Provide new ways to manage, display or interact with content or users
Let's see which Drupal concepts are used to achieve this.
Drupal is a modular system. It means that it is built from small pieces of code that can be enabled or disabled. These pieces of code are called modules.
One of the newcomer mistake is programming too much (opens in a new tab). If you need to implement a rather common feature, chances are that there is a module for that, so you don't have to reinvent the wheel.
Here is a short list of the most used modules.
Drupal is also pretty well integrated with the PHP ecosystem (Symfony (opens in a new tab), Composer (opens in a new tab) / Packagist (opens in a new tab), PSR's (opens in a new tab)) since version 8, so you can still find documentation outside of the Drupal scope.
OK, now it's really time to see what Drupal provides to build custom code.
Hooks are functions that are called at a specific moment of the execution. Modules are able to implement these hooks to alter the behavior of Drupal core or other contributed modules.
They are defined in the module's
For themes, they are defined in the
For the core, hooks are defined in the API documentation (opens in a new tab).
A module can also define its own hooks. They are usually discoverable through the modules
A simple way to find hooks is to search for
hook_ in the codebase or just let PHPStorm autocomplete the function name for you when Drupal is configured (opens in a new tab).
Then type your module name and PHPStorm will provide you with a list of available hooks.
This hook is called when a form is built. It allows to alter the form rendering and its state.
Has this hook has a pretty large scope, it is preferred to use more specific hooks when possible, like
This hook is called when an entity type is defined. It allows to alter the entity type definition, for example to add a new field to all nodes.
This hook is called when an entity is inserted in the database. It allows to react to the creation of an entity.
There are various other hooks like this one, for example
hook_form_alter, it is preferred to use more specific hooks when possible, like
Events are objects that are dispatched at a specific moment of the execution. They are roughly similar to hooks, they are just implemented in a different way, that follows object oriented principles. Hooks are still used in Drupal, because there is a lot of legacy code that uses them, but events are the recommended way to alter the behavior of Drupal Core if it is possible to use them.
React to events, like Symfony
Dispatch events, with
Similar to hooks, PHPStorm shines here, especially with the Symfony plugin installed.
Drush can also do that:
drupal debug:container then pipe it to
grep to find a specific service.
Most of the time, the only thing that you need to do is to define a route in your module via a .routing.yml file.
Here is a very minimal example from the core Book module, that defines the route for a Controller method.
# The path always starts with a leading forward-slash.
# Defines the default properties of a route.
# For page callbacks that return a render array use _controller.
# Require a permission to access this route.
_permission: 'access content'
Same goes for a form:
_title: 'Personal information'
_permission : 'custom_module_permission'
Read more (opens in a new tab) - Drupal.org
drush route or the Devel (opens in a new tab) module.
And how can I find the current route used by the frontend.
There are several ways to do that:
- Without any dependency (Drush, Devel, ...): implement a rather global hook like
drush route --path=/the-path
Useful e.g. to add a new access control or to change the controller method that is called.
This is rather straigthforward, you just need to implement a
RouteSubscriberInterface and implement the
Read more (opens in a new tab) - Drupal.org
- Render array
- Response / cacheable response
- JSON response / JSON cacheable response
- Binary file response
- Taxonomy term:
We already discovered some of them: node_types and vocabularies.
user_rolecontains a set of
This can be used to import data from a legacy system or to migrate from another CMS once.
But it can also be used to import data from a third party system on a regular basis.
Drupal 7 sites have their own migration system, as version 8 introduced many breaking changes in the model.
Plugin manager, plugin types, plugin discovery
- Access handlers
Cache API (opens in a new tab) - Drupal.org
Form API - validation (opens in a new tab) - Drupal.org
Entity validation API overview (opens in a new tab) - Drupal.org Validation constraints (opens in a new tab) - Drupal.org