Drupal

Posts about Drupal, the open source content management system.

Drupal 8: Creating A Views Results Area Plugin

Drupal Views is a great way of exposing data to users via a search interface. This can be done directly via the database or via a Solr server. Plenty of Views plugins exist to allow reacting to the search input and output in a variety of different ways.

The other day I needed to add a personalised message to Views output to inform a user that their search keyword didn't find any results. There is a plugin for Views that allows this, but it only shows a basic search string.

What I needed was a way to print out the following block of HTML, containing the search term that the user searched for.

DrupalCamp London 2020

DrupalCamp London was held on the 14th and 15th March 2020 and I went down to City University London to partake in the event. I wasn't talking this year, so I was there purely to enjoy the conference.

Drupal 8: Theming With Tailwind CSS

Upon a recommendation from someone in my local Drupal user group I decided to give Tailwind CSS a go. The ultimate aim of this was to replace the base theme I am using here with a more stripped down theme. At the time of writing this I am using the Cog theme, and whilst it has it's merits, I find that it's a little too much for this simple site.

I decided, therefore, to create a new theme and use Tailwind CSS to alter the site a little. This meant an exercise in integrating Tailwind CSS into a Drupal theme.

Drupal8: Finding All FieldWidget Types

Whilst searching for an answer to a problem the other day I found a comment that details a command that prints out all of the FieldWidgets available in Drupal 8. This is useful if you are looking for all of the field widget classes in Drupal8.

Here is the command:

grep -rl '\@FieldWidget' | xargs grep -m1 'id = ' | grep -o FieldWidget.*

This prints out something similar to the following:

Drupal 8: Altering Update Dependencies

I perform a lot of Drupal updates, and they mostly go very well. The code updates without incident and the database updates apply whatever updates they need without a hitch. Every now and then, however, I will come across a project that hasn't received updates in a while, which means there are a lot of database updates to run through.

Having Drupal run 100+ database updates across modules and core can be a bit problematic. Some modules will require core updates to happen first, and when this happens out of order the database update update fails spectacularly.

Drupal 8: Altering Hook Weights

Drupal's hook system allows modules to interact with various parts of a Drupal application and is part of the power of the application.

One common issue I have found is altering things that have been added by other modules during the hooks process. For example, a hook might be called that involves gathering data from one or more modules. If you need to intercept this configuration there is no guarantee that your module will be called after the module you are trying to intercept.

Another (more concrete) example is when altering forms. The code below shows a hook_form_alter() being run on all node edit forms on a site.

Drupal 8: Prevent User Role Elevation

Drupal has a little flaw in its user permission system that allows users to give themselves, or other users, roles that they shouldn't be able to. If the user has the 'administer users' permission this essentially gives them access to alter roles for any user on the system, meaning that they can grand administrator access to any user on the system. The fix to this involves a couple of actions.

Drupal 8: Running A Batch Through An AJAX Request

This problem came out of a recent project I was working on. I had to perform a bunch of API lookups on behalf of a user that could take a minute or so to complete. The results of the API lookups were cached and so once it was done the site would be very quick, unfortunately the initial API lookup slowed down the page load quite considerably so this created a problem.

Rather than just doing the API loading in the page load process and making the user sit through it I created a batch process to load the API results in a more manageable manner. This created another problem as although the batch runner in Drupal is really good, it is perhaps a little too much just to show to users and expect them to understand what is going on. This led me to think if I could run a batch process via an AJAX callback from the page they were trying to load.

Drupal 8: Custom Cache Bins

Drupal's cache system is robust, feature full and extensible. It can be used to cache small blocks of rendered output or the results of more complex calculations. The cache can be stored in a for the page request, in a database or in a different cache system.

I recently needed to store a decent amount of data that was pulled from an API. Getting the data from the API took a few seconds so it was important to cache this within the site for quick retrieval. Even just storing the cache in the database was many times quicker than the API so it made sense to cache the results within the site. Having the user sat there waiting for the page to load every time they do anything isn't great.

To this end I created a small Drupal service that would manage this cache for me. Here is the record from the services YAML file within the module.

Creating A Language Cascade In Drupal 8

From the pages of 'crazy things you can do with Drupal 8' comes this idea that I recently had to implement on a site. This was on a site that had implemented translations, but they needed something a little extra. The central idea was that if you visited a page on the site in a particular language, and that language didn't exist, then to try and give the user a similar language.

If you weren't already aware, Drupal's default behaviour is to return the default language version of a page if the language requested doesn't exist. If the Path Auto module is installed (which is usually the case on most Drupal sites) then Drupal will not be able to translate the path alias correctly and will issue a 404 if the requested translation doesn't exist. Drupal can't take the path for the French page /fr/about-us and find the original node because as far as it's concerned /fr/about-us doesn't exist.