A schema for Gutenberg blocks

At Jetpack we recently created a new Gutenberg block which displays “Related Posts”. This block is similar in content to the “Latest Posts” block in WordPress.org; it’s just a list of posts. The difference is the way the posts are displayed:

There are plans afoot to update the “Latest Posts” block, so that it contains an image and a post summary (see image below).

As these two blocks grow they seem to be converging on similar layouts, but with different content.

There are similar overlaps with other blocks. For example the layout of the WordPress.org gallery block could also be used to display a list of posts, as could the recently launched Tiled Gallery block. Evidently there are many layout possibilities for a list of posts!

The problem

As the number of Gutenberg blocks grows these overlaps become more obvious. As we start to build pages with Gutenberg it starts to become apparent that this is going to get very messy very quickly.

Essentially blocks have a content and a presentation element. Taking the example we began with, we can see overlap between many different types of content:

Lists of content

One type of content is a list of text, images and links. These come in many different forms, but they share the same structure:

  • Latest posts
  • List of posts in a category
  • List of post in a tag
  • Archive of posts by month/year etc
  • List of categories/tags
  • List featured posts
  • List of images
  • List of authors
  • List of [custom post type]

Similarly, all of the above types of content could be displayed in any of the following ways:

Layouts

Here are some examples of the different types of layout that this content could use:

The challenge is that each of these different types content can be displayed in each of these different layouts. If we wanted to create blocks for each of these combinations we’d end up with over a hundred different blocks. On the other hand we could build one single block which was so complex that it could display all these combinations within one block. Neither of these would be sensible solutions.

Can we use Block Style Variations?

Block Style Variations offer an API which allows us to modify the CSS for a block – they let us overlay a presentation layer on top of an existing block. This is ideal when modifying the way a block looks. However many of the layout variations I have examined above require more than just a different CSS, they need different markup and additional JavaScript.

Separating Content and Presentation

One solution to this problem could be to separate content from presentation in our blocks. What if we were able to define semantics for the content in our blocks, which could be interpreted by different layouts? This would mean users would first think about the content they wanted to show, and then all display options would be open to them.

A Shared Data Structure

The overlap between these blocks occurs because they all share the same data structure (an array of text, image and link). It would be possible to define a standard data structure that blocks can use. When blocks share a data structure, then it should be possible for them to share common layouts. This would mean a photo gallery display could be reused to display a list of posts, or a block that displays a list of recent posts could be reused to show a list of authors.

How Could this work?

“Block Transformations” are an existing mechanism which converts one block into another. At present every transformation has to be coded separately.

Could we re-imagine the way that transformations work, so that if blocks share a common data-structure, they can easily be transformed into each other, without writing custom transformation code?

Similarly, could we make changes to the way “Block Style Variations” work, so that they can apply a layout to our structured data?

Feedback

What do you think? Is this a problem? Are there other solutions I haven’t considered? Leave a comment!

7 responses

  1. Great post!

    I see this problem everywhere with page builders. There are hundreds of modules in page builders serving the same purpose. So, obviously, this is a big problem.

    I think in addition to the data structure, we should add a new terminology for data source. So the schema looks like:

    [input = data source] -> [output = data that is parsed into the united data structure] -> [rendered by blocks]

    The output of the data is the input of the blocks. Gutenberg blocks don’t need to care about the data. This part should be handled by developers and is considered as a black box for Gutenberg. Of course WordPress core should make an example for the recent posts.

    This opens many possibilities for blocks and make the front-end part much easier for developers, since they don’t have to work with JavaScript to render the data. All they need to do is adding more data sources for blocks.

  2. […] « A schema for Gutenberg blocks » via ThemeShaper [en] […]

  3. Block style variations could be much more advanced for sure. Out of the box, they just simply add a class to the block’s parent div. It’s possible to execute logic based on style variations, but it’s really clunky and a bit of a hack.

    I’m a huge fan of block transformations — it’s one of Gutenbergs best kept secrets in my opinion. ,It would so neat if block data can be tagged in a way that other blocks would know what to do with specific data. For example, marking a heading within a block so that the heading is properly migrated when the block is transformed. This could be super cool!

  4. Great exploratory piece. I got a little confused near the end:

    > “Block Transformations” are an existing mechanism which converts one block into another. At present every transformation has to be coded separately.”

    This read as if you were proposing to define a new shared terminology, but eventually I figured out that you were referring to the leveraging the existing [Transforms API](https://wordpress.org/gutenberg/handbook/designers-developers/developers/block-api/block-registration/#transforms-optional)

    I can see how this could be useful. My experience so far with Transforms is that they’re a means to gracefully deprecate from one markup to another, but no reason they couldn’t be used in a more productive manner.

    > Evidently there are many layout possibilities for a list of posts!

    Welcome to the world of Front End 😀

    1. Ben Dwyer Avatar

      Sorry for the confusion; you are right I was referring to the Transforms API.

  5. David Huyck Avatar
    David Huyck

    A block-level templating system (somewhat different from what you proposed in your earlier post: https://themeshaper.com/2019/01/17/blocks-templates-and-styles-architecture-for-a-gutenberg-world/) seems like a good path forward here. If we are using a common set of inputs across different blocks, there is a lot of potential for those blocks to share a rendering template. Similarly, in the case of a single block whose data can be displayed a number of different ways, templates again provide a convenient solution.

    It’s always seemed to me like a constrained choice to pre-render blocks in the content. It makes it very difficult to change your display based on theme or other options, especially when your desired display requires markup that is different from what your block already rendered. Migrating to a new look becomes a very steep hill to climb.

    With a template system, the admin user could select the display they want, and while the input data stays the same, the change in markup could be handled by a change of template behind the scenes. Markup, styling, and scripts could be bundled together, so from a UI point-of-view you’d open up a lot of flexibility with a single template-toggle. I could also see this being a hookable option, so you could add template options to a plugin or core block in a very WordPressy way.

    Let me know when you’ve got that all ready for me 😉

  6. Very interesting and definitely a problem that needs solving!

    > If we wanted to create blocks for each of these combinations we’d end up with over a hundred different blocks.

    I’m scared of seeking out custom blocks right now, because I’m seriously worried about “block bloat” fit this exact reason. I also have a widget on need of block conversion that would fit perfectly within what’s described.

    Block variations were really important to get in, but they feel like a solution to a separate but extremely similar issue. I think leaving your alone for their intended use makes sense.