Create Basic Blocks Content programmatically in Drupal 8

Currently, our Drupal team is at work on the second stage of a Drupal corporate website for a US-based energy company. The site is in production and the client’s content management team is working on content population. However, they still need some additional functionality, as well as new types of content pages and other matters.

Using a case study, I will describe below how we overcame some of the challenges for this project.

A set of pages on the site was built on a previous step. These pages have specific path patterns:

markets/[category name]/[subcategory name]

There should be four special blocks with reference materials that will be shown in the sidebar of each category page and its subcategories. That is, the first block will be shown on all pages with path ‘markets/Category1*’ and the second block will be shown on ‘markets/Category2*’, etc.

Because there are no special requirements for those blocks, we decided to use native Drupal blocks (the basic block type) in the interest of saving time.

I have set all these blocks locally, but how can I put them on production without manual work?

I used Features module and select all necessary blocks in the Features UI. IN the module that I used the Features module and selected all the necessary blocks in the Features UI. In the module that was generated, there were several files with block settings in the folder /config/install/. (By the way, we can export these configurations with the Config manager, and the result will be the same.)

Let me describe the issue and our solution on the basis of one such block. For example, there is a basic block called “Communications.” Its configuration will be exported in the file ‘block.block.communications.yml’:

langcode: en
status: true
dependencies:
  content:
    - 'block_content:basic:4eac474a-b60f-4abf-aa2d-5bc8f71b4ad9'
  module:
    - block_content
    - system
  theme:
    - custom_theme
id: communications
theme: custom_theme
region: sidebar
weight: -14
provider: null
plugin: 'block_content:4eac474a-b60f-4abf-aa2d-5bc8f71b4ad9'
settings:
  id: 'block_content:4eac474a-b60f-4abf-aa2d-5bc8f71b4ad9'
  label: 'Communications'
  provider: block_content
  label_display: '0'
  status: true
  info: ''
  view_mode: full
visibility:
  request_path:
    id: request_path
    pages: '/markets/communications*'
    negate: false
    context_mapping: {  }

There is no content in this block! What’s more, if you put this configuration on production site you will get the following message in the sidebar instead of the block content:

This block is broken or missing. You may be missing content or you might need to enable the original module.

I did not find a quick solution to this problem with the help of Drupal contributed modules. The default content module looks like a rather complex solution that serves only to deploy a few basic blocks. If this kind of issue continues to arise, you might add a  Drupal Deploy module. However, I am not sure that it works with block content; I have used it for node content only.

On my own, I have come up with a simpler way to put block content on production. This can be done programmatically. We can create a [your feature name].install file in the module generated by Features UI. Or we can create a separate module that will contain two files: ([your module name].info.yml and [your module name].install).

For the previous module that used as a simple example, the [your module name].install file will look like this:

<?php

use Drupal\block\Entity\Block;

/**
 * Implements hook_install().
 */
function your_module_install() {
    // Grab a block entity manager from EntityManager service
    $blockEntityManager = \Drupal::service('entity.manager')
      ->getStorage('block_content');
    
    // Tell block entity manager to create a block of type 'basic'
    $block = $blockEntityManager->create(array(
      'type' => 'basic'
    ));
    
    // Every block should have a description, but strangely it's property
    // is not 'description' but 'info'
    $block->info = 'Communications';
    
    // we should take this UUID from configuration file, see example above
    $block->uuid = '4eac474a-b60f-4abf-aa2d-5bc8f71b4ad9'; 

    // Block content 
    $block->body->value = '...text of the block with allowed HTML tags...';
    
    // Block Input Format, because block content formated long text
    $block->body->format = 'full_html';

    // In the end, save our new block.
    $block->save(); 
}

One thing to keep in mind is that you should set the same UUID as in your configuration file. This will create a connection between block configuration and block content.

Who to Hire to Do Web Development?

1. Staff

Pros: easy to collaborate with, having staff on-site all day long.

Cons: value (talent for the cost). Strong engineering talent is very hard to find—you’d have to pay a lot more than you would pay S&amp;F for the same level of talent (if you could even find it). Most likely you’ll find someone junior who will cost about the same as Speed and Function.

2. Contractor(s)

Pros: same as above if on-site. If off-site, contracts can be cheaper because individuals typically spend less time than a team.

Cons: same as the cons if on-site. Off-site, you’ll run into management issues, availability, responsiveness, etc. You don’t get access to specialized talent that comes with the team: you are limited to the knowledge that the individual contractor has.

3. A Team

Pros: you get access to all the skills on the team (QA, DevOps, front-end, back-end, Scrum Master, etc.). The company does development for a living: they will never let you down and they will deliver a product no matter what, as long as it’s funded. They herd the cats for you.

Cons: can be more expensive, since teams come with a management overhead.

Your smart refrigerator can be my enemy

Akamai reports that hackers are turning “smart” devices into botnets, or a group of computers that, without their owners’ knowledge, send out spam or viruses to other computers on the Internet. A common tactic is to use a proxy that hits a target from a variety of locations.  The most widespread device used in such attacks is a CCTV camera with a DVR, satellite antennas, networking routers and modems, and NAS.

Will You Save by Cutting Daily Scrum Time?

A company’s daily use of Scrum time adds up.  Why not cut this cost?  Imagine how much money you could save with a five-person team if it didn’t need to spend time in daily scrums, doing actual work instead.  It can be as many as five hours a week.

The reality is that, in our experience, the cost of an engineer’s dissociation from a project is higher.  Building the wrong project because an employee made wrong assumptions, because they didn’t talk to the client, can be a lot more costly than the cost of Scrum for one employee, one hour per week per person.

Trying out Meteor

Most of the JavaScript frameworks I’ve seen suffered from over-configuration and exposing too much detail. Error reporting is usually obscure, there are too many ways to accomplish the same thing, and there are no clearly defined conventions.

And then came Meteor, a “full-stack JavaScript platform for developing modern web and mobile applications.” It works right out of the box, provides a nice command line tool with readable output, and clearly establishes a “meteor way” of doing things.

Read More

Switching Themes Programmatically in Drupal 8

Sometimes we need to use different designs for separate pages or for separate menu items in a site. The most obvious way to perform this task is to set separate templates for each case in the current theme and customize CSS and JS for these pages. But there is another way, which is a less complex front-end solution. We can use a different theme.

I used this solution for the first time in Drupal 5. My team worked on an informational resource about the state of Colorado, and each county had a different design. To resolve this discrepancy, we used the Taxonomy Theme module.

Read More

Java’s Anonymous Inner Classes: Proceed With Caution

Java’s anonymous inner classes can be useful, but you must take care when using them. In particular: A memory leak will occur if an instance of an inner class survives longer than its containing outer class because the inner class maintains a reference to its outer class.

This is not a merely academic concern, this comes up in Android development when we use inner classes to encapsulate and pass around some code, and instances of an outer class (Activities) can be constantly created and destroyed. Read More

Exploring South America

Speed and Function Works Hard, Plays Hard

Recently we spent a month exploring South America. In that month, we visited Brazil (the north, the south, and the Amazon River), Peru (Lima and Cusco with Machu Picchu), Bolivia (La Paz, Santa Cruz, and Salar de Uyuni), and Paraguay (Asunción).

We arrived in São Paulo, which is a municipality located in the Southeast Region of Brazil.

0

Read More