Choosing entity options for best performance in Drupal

In Drupal, it is possible to create entity types with multiple options - with or without revisions, fieldable or not and these options have a different performance impact when dealing with functionalities that handle a large number of entities in a single process, so you would want it to be as fast as possible. 

Changing entity definitions later can be complicated, so the best time to choose the correct options would be at the beginning of development. Let's find out what options we have and how these affect performance.

Base fields

When creating an entity, you most likely already use some of the base fields, like title, status, or user id. The fields are not depending on the bundle and if the entity has bundles, they are always there - for example the title is almost always needed regardless of bundles. The data is added to entity table until cardinality is 1, otherwise secondary table is created.

Fields are defined in the code and the default settings are added there. If field enables display mode configuration, it can be configured (choose widget or formatter and their settings) on the admin interface.

Field API fields

These fields are created through UI and are bundle dependent, although they are reusable between bundles. So they give flexibility and fast creation of entity fields without changing the code.

The downside is that they always create extra table and if revisions are enabled, second table for revisions. Because of extra tables, additional queries are needed.

Testing the performance

To see the difference between different options, I created a performance test with XHProf. For the test, 4 different custom entities were created, using drush generate entity:content.

The entity types that were included in the test:

  • An entity with base fields only, no revisions
  • An entity with base fields and revisions enabled
  • An entity with fields added through Field API, with no revisions
  • An entity with fields added through Field API, revisions enabled.

Testing conditions:

  • Each entity has 10 text fields added
  • Each test installed Drupal minimal installation and enabled all four entity types
  • Entities were always created on a new installation to reduce the possible influence on the database side
  • Before calculating performance, 10 entities were created to warm the cache and prevent anomalies
  • For creating entities, a custom Devel generate plugin was created to fill fields with sample data
  • The test was done in two parts - first, only 100 entities were generated, and then 1000 entities
  • To reduce anomalies, 5 runs were done
  • Tested on local machine, DDEV, Drupal 10, PHP 8.2

Results

Let's check the results with creating 100 entities. As we can see, there is no difference between entity types with base fields, enabling revisions doesn't add any significant processing time.

Using Field API fields, it adds some extra processing time to creating entities, adding roughly 0.5 seconds. Now adding revisions on top of that increases a lot more, around 1 second.

Creating 100 entities (in seconds)

Next, there is a performance result of creating 1000 entities at once. Here we can see that the first three options are similar in performance, but the entity with Fields API and revisions enabled is not performing well.

There are some anomalies where the run times aren't consistent, which could be CPU throttling or database issue.

Creating 1000 entities

In conclusion

Performance can be affected by multiple things in Drupal, and one of them is entity definition options. As these performance numbers show, when dealing with a large count of entities in Drupal, the best option from a performance standpoint would be to use an entity with only base fields and an entity with Field API fields to add marginal overhead. Field API using revisions seems to be the worst combination, according to the tests.

Why does it matter?

  • If you happen to implement functionality in Drupal that may deal with a lot of entities at once, the process should be as fast as possible.
  • When requesting the database over the network, every additional request adds additional latency, which may affect editing entities.

The tests didn't check whether enabling translations or not have any difference. 

Buy Me a Coffee at ko-fi.com

Add new comment