The WordPress coreCoreCore is the set of software required to run WordPress. The Core Development Team builds WordPress. development team builds WordPress! Follow this site for general updates, status reports, and the occasional code debate. There’s lots of ways to contribute:
Found a bugbugA bug is an error or unexpected result. Performance improvements, code optimization, and are considered enhancements, not defects. After feature freeze, only bugs are dealt with, with regressions (adverse changes from the previous version) being the highest priority.?Create a ticket in the bug tracker.
What if effortlessly creating performant, fluid, and idiomatic frontend interactivity on blockBlockBlock is the abstract term used to describe units of markup that, composed together, form the content or layout of a webpage using the WordPress editor. The idea combines concepts of what in the past may have achieved with shortcodes, custom HTML, and embed discovery into a single consistent API and user experience.-based WordPress sites was possible? Imagine plugins providing interactions like “heart this post” or “add to cart” without page reloads. Picture instant search, commenting, and native full-page transitions as best-in-class built-ins without complex scaffolding or external tools. Envision achieving this in any block theme by default without sacrificing PHPPHPThe web scripting language in which WordPress is primarily architected. WordPress requires PHP 5.6.20 or higher server rendering and the pluginPluginA plugin is a piece of software containing a group of functions that can be added to a WordPress website. They can extend functionality or add new features to your WordPress websites. WordPress plugins are written in the PHP programming language and integrate seamlessly with WordPress. These can be free in the WordPress.org Plugin Directory https://wordpress.org/plugins/ or can be cost-based plugin from a third-party ecosystem for a JSJSJavaScript, a web scripting language typically executed in the browser. Often used for advanced user interfaces and behaviors. runtime. Visualize block developers easily declaring and extending such behaviors in a way that is immediately familiar and compatible with the block ecosystem.
That’s what we, the contributors involved in this project, aim to explore and unlock with the Interactivity APIAPIAn API or Application Programming Interface is a software intermediary that allows programs to interact with each other and share data in limited, clearly defined ways.. The demo below shows some of this power and flexibility in action.
GutenbergGutenbergThe Gutenberg project is the new Editor Interface for WordPress. The editor improves the process and experience of creating new content, making writing rich content much simpler. It uses ‘blocks’ to add richness rather than shortcodes, custom HTML etc. https://wordpress.org/gutenberg/ has evolved a lot over the past few years, though most of the improvements have focused on the block developer experience within the block editor. Today, we’d like to update you on the Interactivity API, which aims to be a standard way to allow developers to add interactivity to the frontend of their blocks.
The Interactivity API is for the frontend of blocks, not for the block editor. This means the API is not expected to be used inside the edit function. It’s a way to create interactive user interfaces for your site visitors. Having said that, we’d like to explore whether some directives could be reused across the frontend and the editor to unify the whole block developer experience.
This is still experimental. Functionalities are missing, documentation is scarce, and the final API may look different. The API’s design is open to debate, and any feedback is key to ensuring the Interactivity API accounts for the entirety of WordPress’ diverse needs and requirements.
The main goal of the Interactivity API is to provide a standard and simple way to handle the frontend interactivity of Gutenberg blocks.
A standard makes it easier for developers to create rich, interactive user experiences, from simple cases like counters or popups to more complex features like instant page navigation, instant search, or carts and checkouts.
All these user experiences are technically possible right now without the Interactivity API. However, the more complex the user experience and the more blocks interact with each other, the harder it becomes for developers to build and maintain sites. There are a lot of challenges they have to figure out themselves. The API aims to provide out-of-the-box means for supporting these kinds of interactions.
To address this challenge, before researching different approaches, some requirements/goals for the API were defined:
Block-first and PHP-first: The API must work well with PHP and the current block system, including dynamic blocks, widely extended in WordPress. It must support server-side rendering. Server-rendered HTMLHTMLHyperText Markup Language. The semantic scripting language primarily used for outputting content in web browsers. and client-hydrated HTML must be exactly the same. This is important for SEO and the user experience.
Backward compatible: The API must be compatible with WordPress hooksHooksIn WordPress theme and development, hooks are functions that can be applied to an action or a Filter in WordPress. Actions are functions performed when a certain event occurs in WordPress. Filters allow you to modify certain functions. Arguments used to hook both filters and actions look the same., which could, for example, modify server-rendered HTML. It must also be compatible with internationalization and existing JS libraries on the site (such as jQuery).
Optional and gradual adoption: Related to the previous point, the API must remain optional. It should be possible to adopt it gradually, meaning that interactive blocks not using this API can coexist with those using it.
Declarative and reactive: The API must use declarative code, listen to changes in the data, and update only the parts of the DOM that depend on that data.
Performant: The runtime must be fast and lightweight to ensure the best user experience.
ExtensibleExtensibleThis is the ability to add additional functionality to the code. Plugins extend the WordPress core software.: In the same way WordPress focuses on extensibility, this new system must provide extensibility patterns to cover most use cases.
Atomic and composable: Having small reusable parts that can be combined to create more complex systems is required to create flexible and scalable solutions.
Compatible with the existing block development tooling: The API must be integrated with the existing block-building tools without requiring additional tooling or configuration by the developer.
Apart from all these requirements, integrating client-side navigation on top of any solution should be easy and performant. Client-side navigation is the process of navigating between site pages without reloading the entire page, which is one of the most impressive user experiences demanded by web developers. For that reason, this functionality should be compatible with this new system.
What’s being proposed?
The Interactivity API is a standard system of directives, based on declarative code, for adding frontend interactivity to blocks.
Directives extend HTML with special attributes that tell the Interactivity API to attach a specified behavior to a DOM element or even to transform it. For those familiar with Alpine.js, it’s a similar approach but explicitly designed to work seamlessly with WordPress.
The API is designed for the world of blocks and takes WordPress history of being closely attached to web standards to heart.
As directives are added to the HTML, they work great with dynamic blocks and PHP.
Dynamic block example
<div
data-wp-context='{ "isOpen": false }'
data-wp-effect="effects.logIsOpen"
>
<button data-wp-on.click="actions.toggle">
Toggle
</button>
<p data-wp-show="context.isOpen">
This element is now visible!
</p>
</div>
As you can see, directives like data-wp-on.click or data-wp-show are added as custom HTML attributes. WordPress can process this HTML on the server, handling the directives’ logic and creating the appropriate markup.
Backward compatible
As the Interactivity API works perfectly with server-side rendering, you can use all the WordPress APIs, including:
WordPress filters and actions: You can keep using WordPress hooks to modify the HTML or even to modify directives. Additionally, existing hooks will keep working as expected.
CoreCoreCore is the set of software required to run WordPress. The Core Development Team builds WordPress.TranslationtranslationThe process (or result) of changing text, words, and display formatting to support another language. Also see localization, internationalization. API: e.g. __() and _e(). You can use it to translate the text in the HTML (as you normally would) and even use those APIs on the server side of your directives.
Optional and gradual adoption
The Interactivity API pipeline promotes progressive enhancementenhancementEnhancements are simple improvements to WordPress, such as the addition of a hook, a new feature, or an improvement to an existing feature. by building on top of WordPress’s solid foundation and patterns. It was carefully designed not to force any use cases to pay for the costs of other use cases.
For example, blocks with directives can coexist with other (interactive or non-interactive) blocks. This means that if there are other blocks on the page using other frameworks like jQuery, everything will work as expected.
Declarative and reactive
The Interactivity API follows an approach similar to other popular JS frameworks by separating state, actions, and effects and defining them declaratively. Why declaratively?
Declarative code describes what a program should do, while imperative code describes how the program should do it. Using a declarative approach, the UIUIUser interface automatically updates in response to changes in the underlying data. With an imperative approach, you must manually update the UI whenever the data changes. Compare the two code examples:
Imperative code
<button id="toggle-button">Toggle Element</button>
<p>This element is now visible!</p>
<script>
const button = document.getElementById("toggle-button");
button.addEventListener("click", () => {
const element = document.getElementById("element");
if(element) {
element.remove();
} else {
const newElement = document.createElement("p");
newElement.textContent = "This element is visible";
document.body.appendChild(newElement);
}
});
</script>
Declarative code
This is the same use case shared above but serves as an example of declarative code using this new system. The JavaScriptJavaScriptJavaScript or JS is an object-oriented computer programming language commonly used to create interactive effects within web browsers. WordPress makes extensive use of JS for a better user experience. While PHP is executed on the server, JS executes within a user’s browser. https://www.javascript.com/. logic is defined in the view.js file of the block, and add the directives to the markup in the render.php .
<!-- Render.php file -->
<div data-wp-context="{ 'isOpen': true }">
<button data-wp-on.click="actions.toggle">
Toggle Element
</button>
<div data-wp-show="context.isOpen">
<p>This element is visible!</p>
</div>
</div>
Don’t worry if you don’t fully understand this example yet. It will be explained in detail later in the post.
Using imperative code may be easier when creating simple user experiences, but it becomes much more difficult as blocks become more complex. The Interactivity API must cover all use cases, from the simplest to the most challenging. That’s why a declarative approach using directives better fits the Interactivity API.
Performant
The API has been designed to be as performant as possible:
The runtime code needed for the directives is just ~10 KB, and it only needs to be loaded once for all the blocks.
It only loads the directives needed by the blocks present on the page. For example, if no blocks are using data-wp-show, the code for this directive won’t be loaded.
The scripts will load without blocking the page rendering.
There are ongoing explorations about the possibility of delaying the scripts loading once the block is in the viewport. This way, the initial load would be optimized without affecting the user experience.
Extensible
Directives can be added, removed, or modified directly from the HTML. For example, users could use the render_block filter to modify the HTML and its behavior.
In addition to using built-in directives, users can create custom directives to add any custom behaviors to their HTML.
Atomic and composable
Each directive controls a small part of the DOM, and you can combine multiple directives to create rich, interactive user experiences.
Compatible with the existing block development tooling
Using built-in directives does not require a build step and only requires a small runtime. A build step is necessary only when creating custom directives that return JSX. For such use cases, the API works out of the box with common block-building tools like wp-scripts.
Client-side navigation
The Interactivity API comes with built-in primitives for adding client-side navigation to your site. This functionality is completely optional, but it opens the possibility to create these user experiences without having to opt out of the WordPress rendering system.
It also pairs very well with the View Transitions API allowing developers to animate page transitions easily.
Why a standard?
Blocks using the Interactivity API and interactive blocks using other approaches like jQuery can coexist, and everything will work as expected. However, the Interactivity API comes with some benefits for your interactive blocks:
Blocks can communicate with each other easily. With a standard, this communication is handled by default. When different blocks use different approaches to frontend interactivity, inter-block communication becomes more complex and almost impossible when separate developers create blocks.
Composability and compatibility: You can combine interactive blocks, and nest them in structures with defined behaviors. Thanks to following the same standard, they are fully cross-compatible. If each block used a different approach to interactivity, they would likely break.
Fewer KBs will be sent to the browser. If each plugin author uses a different JS framework, more code will be loaded in the frontend. If all the blocks use the same one, the code is reused.
If all the blocks on a page use this standard, site-wide features like client-side navigation can be enabled.
Additionally, with a standard, WordPress can absorb the maximum amount of complexity from the developer because it will handle most of what’s needed to create an interactive block.
Complexities absorbed by the standard
With this absorption, less knowledge is required to create interactive blocks, and developers have fewer decisions to worry about.
Additionally, if the community adopts a standard, learning from other interactive blocks would be simpler, which fosters collaboration and code reusability. This should simplify the development process and make it friendlier to less experienced developers.
How to create interactive blocks using the API
It’s important to highlight that the block creation workflow doesn’t change.
Until now, WordPress has been intentionally unopinionated about the different solutions used on the frontend of blocks. The Interactivity API changes that. It adds a new standard way to easily add frontend interactivity to blocks while the APIs handling the Block Editor remain the same.
To add interactivity to blocks using the Interactivity API, developers would need to:
Add directives to the markup to add specific behavior to the block.
If needed, create a store with the logic (state, actions, or effects) needed for interactivity. Blocks using only directives with self-sufficient logic like data-wp-link, don’t need this step.
Before explaining each step in more detail, let’s return to our example: a button that shows and hides some text. We’ll also add logic to send a message in the console whenever the button is hidden/revealed.
Add directives
Directives are added to the markup of your block. In the render.php file (for dynamic blocks) or the save.js file (for static blocks).
<div
data-wp-context='{ "isOpen": false }'
data-wp-effect="effects.logIsOpen"
>
<button data-wp-on.click="actions.toggle">
Toggle
</button>
<p data-wp-show="context.isOpen">
This element is visible!
</p>
</div>
In this example, the directive data-wp-context is used to define some local state ("isOpen": false) that will be available to that HTML node and all its children. All the actions and effects used in those nodes can access that data. Knowing that, other directives like data-wp-on.click can trigger actions and effects reading that context.
Create the store
In this part, the logic (actions and effects) called by the directives is defined.
The store is created in the view.js file of each block. Although it works at a block level right now, the possibility of sharing code that multiple blocks need will be investigated as well.
// view.js
import { store } from "@wordpress/interactivity";
store({
actions: {
toggle: ({ context }) => {
context.isOpen = !context.isOpen;
},
},
effects: {
logIsOpen: ({ context }) => {
// Log the value of `isOpen` each time it changes.
console.log(`Is open: ${context.isOpen}`);
},
},
});
For those familiar with ReactReactReact is a JavaScript library that makes it easy to reason about, construct, and maintain stateless and stateful user interfaces. https://reactjs.org/., this would be an equivalent React component:
const Comp = () => {
const [isOpen, setIsOpen] = useState(false);
useEffect(() => {
// Log the value of `isOpen` each time it changes.
console.log(`Is Open: ${isOpen}`);
}, [isOpen]);
const toggle = () => {
setIsOpen(!isOpen);
};
return (
<div>
<button onClick={toggle}>Toggle Element</button>
{isOpen && <p>This element is visible!</p>}
</div>
);
};
Let’s take a look at each step in detail:
1. Add the directives
Directives are custom HTML attributes whose value can contain options or references to the store.
Let’s return to our previous example:
Dynamic block example
// render.php
<div
<?php echo get_block_wrapper_attributes(); ?>
data-wp-context='{ "isOpen": false }'
data-wp-effect="effects.logIsOpen"
>
<button data-wp-on.click="actions.toggle">
Toggle
</button>
<p data-wp-show="context.isOpen">
This element is visible!
</p>
</div>
This is how it would work in a static block:
Static block example
// save.js
const save = () => {
return `
<div
{...useBlockProps()}
data-wp-context='{ "isOpen": true }'
data-wp-effect="effects.logIsOpen"
>
<button data-wp-on.click="actions.toggle">Toggle</button>
<p data-wp-show="context.isOpen">
This element is visible!
</p>
</div>
`;
};
The example above uses directives like wp-show and wp-on to add interactivity to the HTML. Below is the initial list of core directives planned, which aims to cover the most common use cases for adding interactivity. It has been inspired by other frameworks like Alpine, VueVueVue (pronounced /vjuː/, like view) is a progressive framework for building user interfaces. https://vuejs.org/., or Svelte:
wp-context provides local state available to a specific HTML node and its children.
wp-on runs code on dispatched DOM events like click or keyup. The format of this directive is data-wp-on.[event], like data-wp-on.click or data-wp-on.keyup.
wp-show shows and hides elements depending on the state or context.
wp-each creates DOM elements by iterating through a list.
wp-bind allows setting HTML attributes on elements.
wp-class adds or removes a class to an HTML element, depending on its value.
wp-style adds or removes inline style to an HTML element, depending on its value.
wp-text sets the inner content of an HTML element.
wp-html sets the innerHTML property of an HTML element.
wp-slot / wp-fill moves snippets of HTML from one place (fills) to another (slots).
wp-effect runs an expression when the node is created and runs it again when the state or context changes.
wp-init runs an expression only when the node is created.
wp-error captures errors in other interactive blocks.
Please bear in mind that this list may vary, and not all these core directives have been implemented yet. Additionally, the API is extensible: anyone can create their own directives if needed.
An important feature is that, when needed, directives support server-side rendering in PHP. This results in a better user experience and better SEO. This is usually taken for granted with WordPress but, when using modern frameworks like React to add interactivity to blocks, it is common to show empty content until client-side JavaScript updates the HTML.
2. Create the store
The store contains the reactive state and the actions and effects that modify it.
State: Defines data available to the HTML nodes of the page. It is important to differentiate between two ways to define the data:
Global state: It is defined using the store() function, and the data is available to all the HTML nodes of the page.
Context/Local State: It is defined using the data-wp-context directive in an HTML node, and the data is available to that HTML node and its children.
Actions: Usually triggered by the data-wp-on directive (using event listeners) or other actions.
Effects: Automatically react to state changes. Usually triggered by data-wp-effect or data-wp-init directives.
Returning to our example, this could be a simple store in one block:
// view.js
import { store } from "@wordpress/interactivity";
store({
actions: {
toggle: ({ context }) => {
context.isOpen = !context.isOpen;
},
},
effects: {
logIsOpen: ({ context }) => {
// Log the value of `isOpen` each time it changes.
console.log(`Is open: ${context.isOpen}`);
},
},
});
In this specific case, only actions and effects are defined, but some state could also be included. For example, you could define the state in another block to create a list with your “Favorite movies”. It might look something like this:
// view.js - A favorite movies block
import { store } from '@wordpress/interactivity';
store({
state: {
favoriteMovies: [],
},
actions: {
addMovie: ({ state, context }) => {
// We assume that there is a `wp-context` directive
// on the block which provides the item ID.
state.favoriteMovies.push(context.item.id);
},
clearFavoriteMovies: ({ state }) => {
state.favoriteMovies = [];
},
},
});
Note: The store function will automatically merge the store definitions from all the blocks using store into a single reactive object. This way, you can use the global state defined in other blocks.
Initializing the store on the server with wp_store()
The store can also be initialized on the server using the wp_store() function. You would typically do this in the render.php file of your block (the render.php templates were introduced in WordPress 6.1). Initializing your store on the server allows you to populate it with some data from the server without worrying about serializing that data or making additional API requests.
The store defined on the server with wp_store() gets merged with the stores defined in the view.js files. For example, the “Favorite movies” block from above could initialize its store on the server like this:
And then its `view.js` file would be simplified to:
// view.js - A favorite movies block
import { store } from '@wordpress/interactivity';
store({
actions: {
addMovie: ({ state, context }) => {
// We assume that there is a `wp-context` directive
// on the block which provides the item ID.
state.favoriteMovies.push(context.item.id);
},
clearFavoriteMovies: ({ state }) => {
state.favoriteMovies = [];
},
},
});
Initializing the store in the server also allows you to use any WordPress API. For example, you could use the Core Translation API to translate part of your state:
When creating a directive, you might notice that its value is a string pointing to a specific state, an action, or an effect. For instance, in the example that we’ve been using in this post, the value of the data-wp-on.click directive was actions.toggle, and the value of data-wp-effect was effects.logIsOpen.
Those values are references to a particular property in the store. They are wired to the directives automatically so that each directive “knows” what actions.toggle refers to without any additional configuration.
When a directive is evaluated, the reference callback receives an object with:
The store containing the state, actions and effects.
The context (an object containing the context defined in all the wp-context ancestors).
The reference to the DOM element on which the directive was defined (a ref).
Other properties relevant to the directive. For example, the data-wp-on.click directive also receives the instance of the MouseEvent triggered by the user.
import { store } from "@wordpress/interactivity"
store({
state: {
theme: false,
},
actions: {
toggle: ({
state,
context,
ref,
event,
className,
}) => {
console.log(state);
// `{ "theme": false }`
console.log(context);
// `{ "isOpen": true }`
console.log(ref);
// The DOM element
console.log(event);
// The Event object if using the `data-wp-on`
console.log(className);
// The class name if using the `data-wp-class`
}
}
})
This approach enables some functionalities that make directives flexible and powerful:
Actions and effects can read and modify the state and the context.
Actions and effects can do anything a regular JavaScript function can do, like access the DOM or make API requests.
Effects automatically react to state changes.
How can users learn more and keep track of the API?
If you are interested in this proposal, let us know in the comments or the Interactivity API GitHub repo. Your feedback is highly appreciated. If you want to learn more about the Interactivity API, here is a list of relevant links with more information:
GitHub repo: This is where most aspects are discussed and a way to follow the development process. Feel free to open any issue, discussion, or pull request.
Movies demo repo: An example with some interactive blocks and user experiences. If you are interested in the code or even reproducing it locally, the information is gathered here.
There will be more resources in the future, including technical documentation, to explain everything in more detail.
Next steps
There will be two sessions on April 17th, 2023 (one at 08:00UTC and another at 17:00UTC) featuring a live product demo followed by a Q&A. The specifics for each session will be announced on the Make Core blogblog(versus network, site). If you’re interested in the Interactivity API, have any related questions, or want to provide feedback, feel free to join us. For those who cannot attend or prefer to share feedback in writing, comment on this post. Additionally, the session will be recorded and posted it here.
With this in mind, these are the next steps for the Interactivity API:
Gather and address the feedback received in the live session and this post.
Keep developing the API, incorporating the feedback.
Work on more technical documentation to explain in detail how the Interactivity API works.
Once there is enough feedback and the API feels confident enough, the intent is to add the API as an experimental feature to Gutenberg so block authors can start building with it (with the eventual goal of including it in Core).
FAQ
How does the Interactivity API work under the hood?
Its three main components are:
Preact combined with Preact Signals for hydration, client logic, and client-side navigation.
HTML Directives that can be understood by both the client and server.
There will be more technical documentation to explain the API in more detail in the future. In the meantime, please share any questions in the comments or on the GitHub repo.
Why did you choose Preact to build the directives system? Why not React or another JavaScript framework?
Preact has a number of advantages over React and other JavaScript frameworks like Vue, Svelte, or Solid in the context of the frontend (which is the focus of the Interactivity API):
It’s performant (even more when used with signals).
It’s compatible with React (through preact/compat, useful to share the same Editor components for some use cases where SSR is not important, and the components are very complex, like an e-commerce cart and checkout, for example).
It’s HTML-friendly (unlike React).
It gives us DOM diffing out of the box.
It’s extremely extensible through their Option Hooks. They use that extensibility for the hooks (preact/hooks), compatibility with React (preact/compat) and their signals (@preact/signals). Basically, everything but the DOM diffing algorithm.
Its core team has been great and very helpful. They are also interested in enhancing this “island-based” usage of Preact.
Is Gutenberg going to move from React to Preact since the Interactivity API uses it?
No. At the moment, there are no plans to make that transition. The requirements and advantages of the editor, as a fully interactive application, are quite different. Preact does have a @preact/compat package that enables full compatibility with the React ecosystem, and many large web applications use it. However, using Preact in the block editor would not offer advantages like it does on the frontend in the Interactivity API.
What approaches have been considered instead of using directives?
Many alternative approaches were considered. Here’s a brief summary of some of them:
React and other JavaScript frameworks
React was considered first because Gutenberg developers are familiar with it. Other popular JS frameworks like Svelte, Vue.js, or Angular were also considered, but none of them (including React) are PHP-friendly or compatible with WordPress hooks or internationalization. See above for a longer explanation.
Alpine.js
Alpine.js is a great framework, and it inspired a lot of functionality in the Interactivity API. However, it doesn’t support server-side rendering of its directives, and having a similar system tailored for WordPress blocks has many benefits.
The possibility of creating a DSL for writing interactive templates was also researched. The code written in that Template DSL would then be compiled into both JavaScript and PHP. However, creating a production-grade Template compiler is complex and would be a large and risky investment of effort. This approach is still being considered for the future, with the directives serving as a compilation target.
Why should I, as a block developer, use the Interactivity API rather than React?
Using React on the frontend doesn’t work smoothly with server rendering in PHP. Every approach that uses React to render blocks has to load content using client-side JavaScript. If you only render your blocks on the client, it typically results in a poor user experience because the user stares at empty placeholders and spinners while waiting for content to load.
Now, it’s possible to server-render a block in PHP and use React to render the same block on the frontend. However, this results in a poor developer experience because the logic has to be duplicated across the PHP and React parts. Not only that, but you have now exposed yourself to subtle bugs caused by WordPress hooks!
Imagine installing a third-party plugin with a hook (filterFilterFilters are one of the two types of Hooks https://codex.wordpress.org/Plugin_API/Hooks. They provide a way for functions to modify data of other functions. They are the counterpart to Actions. Unlike Actions, filters are meant to work in an isolated manner, and should never have side effects such as affecting global variables and output.) that modifies the server-rendered HTML. Let’s say this filter adds a single CSSCSSCascading Style Sheets. class to your block’s HTML. That CSS class will be present in the server-rendered markup. On the frontend, your block will render again in React, but now the content will not include that CSS class because there is no way to apply WordPress hooks to React-rendered content!
On the other hand, the Interactivity API is designed to work perfectly with WordPress hooks because directives enhance the server-rendered HTML with behaviors. This also means it works out of the box with WordPress backend APIs like i18ni18nInternationalization, or the act of writing and preparing code to be fully translatable into other languages. Also see localization. Often written with a lowercase i so it is not confused with a lowercase L or the numeral 1. Often an acquired skill..
To summarize, using the Interactivity API rather than just using React comes with these benefits:
If you use React, your interactive blocks must generate the same markup on the client as they do on the server in PHP. Using the Interactivity API, there is no such requirement as directives are added to server-rendered HTML.
The Interactivity API is PHP-friendlier. It works out of the box with WordPress hooks or other server functionalities such as internationalization. For example, with React, you can’t know which hooks are applied on the server, and their modifications would be overwritten after hydration.
What are the benefits of Interactivity API over just using jQuery or vanilla JavaScript?
The main difference is that the Interactivity API is declarative and reactive, so writing and maintaining complex interactive experiences should become way easier. Additionally, it has been specially designed to work with blocks, providing a standard that comes with the benefits mentioned above, like inter-block communication, compatibility, or site-wide features such as client-side navigation.
Finally, comparing it with jQuery, the Interactivity API runtime is ~10kb, which is much more lightweight. Actually, there is an ongoing effort to remove heavy frameworks like jQuery across the WordPress ecosystem, and this would help in this regard.
Do I need to know React, PHP, and this new Interactivity API?
If you want to add frontend interactivity to your blocks using this API, the short answer is yes. If your block is not interactive, the block creation workflow will remain exactly the same.
As mentioned in the post, this API only adds a new standard way to easily add frontend interactivity to blocks, which didn’t exist until now. This means that you will still need to use React to handle the editor part of your blocks.
In the future, we’d like to explore the possibility of expanding the usage of directives to unify the developer experience among the Editor as well.
On the other hand, if you want to create an interactive block, with the Interactivity API you don’t have to deal with complex topics like tooling, integration with WordPress, inter-block communication, or the server-side rendering of the interactive parts.
Does this mean I must migrate all my interactive blocks to use this API?
No. Blocks outside the Interactivity API can coexist with blocks using it. However, as explained above, keep in mind that there are some benefits for blocks that use the API:
Blocks can communicate with each other easily. With a standard, this communication is handled by default. When different blocks use different approaches to frontend interactivity, inter-block communication becomes more complex and gets almost impossible when separate developers create blocks.
Composability and compatibility: You can combine interactive blocks, nest them in structures with defined behaviors, and, thanks to following the same standard, they are fully cross-compatible. If each block were to use a different approach to interactivity, they would likely break.
Fewer KBs will be sent to the browser. If each plugin author uses a different JS framework, more code will be loaded in the frontend. If all the blocks use the same one, the code is reused.
If all the blocks on a page use this standard, site-wide features like client-side navigation can be enabled.
What are the performance implications of using this API? Is it worth loading the Interactivity API for very simple use cases?
The API has been designed with performance in mind, so it shouldn’t be a problem:
The runtime code needed for the directives is just ~10 KB, and it only needs to be loaded once for all the blocks.
It only loads the directives needed by the blocks present on the page. For example, if no blocks use data-wp-show, that directive won’t be loaded.
All the scripts that belong to the Interactivity API (including the `view.js` files) will load without blocking the page rendering.
There are ongoing explorations about the possibility of delaying the scripts loading once the block is in the viewport. This way, the initial load would be optimized without affecting the user experience.
Can I use directives in the block editor?
No. Right now, directives only work in the frontend of blocks. However, it’ll be investigated whether some directives (and also your custom directives) could be reused across the frontend and the editor. It’s worth emphasizing that the realities of the editor application and the frontend of a website are very different, particularly around the interactivity they afford. It needs to be ensured that the right tools are built for the right context. An interesting area to explore further would be to expose directives in the editor so users and builders can use them to attach behaviors to their sites on demand.
Does it work with the Core Translation API?
It does! As the Interactivity API works perfectly with server-side rendering, you can use all the WordPress APIs including __() and _e(). You can use it to translate the text in the HTML (as you normally would) and even use it inside the store when using wp_store() on the server side. It might look something like this:
Before testing, bear in mind that the Interactivity API is still experimental and very likely to change before an official release. There are still missing functionalities that may break your site, and the API hasn’t been documented yet properly. If you plan to use it, do so at your own risk.
If you want to test the Interactivity API, you can install the latest version of the plugin on your site. Note that it requires the latest version of Gutenberg to work. Once installed, you can start creating interactive blocks using the API.
If you prefer to test the Interactivity API in a demo site with some interactive blocks already in place, you can look at the WP Movies demo.
How can interactive blocks update/save the state on the server?
It is still an active area of research, but is on the roadmap for the Interactivity API. For example, there’s an ongoing experiment to create an interactive version of the Comments Form block that can persist comments on the site and refresh itself without a full page reload.
Is it going to be a plugin? Or will it be part of Gutenberg/Core?
Although it is now distributed as a plugin, it aims to be added as an experimental feature to Gutenberg. The goal is to include it in Core once enough feedback has been gathered, and it’s clear that it’s the right direction.
I’m concerned about XSS; can JavaScript be injected into directives?
No. The Interactivity API only allows for References to be passed as values to the directives. This way, there is no need to eval() full JavaScript expressions, so it’s not possible to perform XSS attacks.
Does this work with CSP?
Yes. The Interactivity API does not use eval() or the Function() constructor, so it doesn’t violate the unsafe-eval content security policy. It is also designed to work with any custom content security policy.
Can you use directives to make AJAX/REST-API requests?
Sure. Actions and effects called by directives can do anything a JavaScript function can, including making API requests.
As mentioned during the post, it’d be great to hear your thoughts and new ideas in the GitHub repo.
Special props to @czapla , who coauthored this blog post with me from the start, and to @kristastevens for her invaluable help in shaping the document and ensuring everything was cohesive.
Gutenberg 15.4.0 is the latest release of the PluginPluginA plugin is a piece of software containing a group of functions that can be added to a WordPress website. They can extend functionality or add new features to your WordPress websites. WordPress plugins are written in the PHP programming language and integrate seamlessly with WordPress. These can be free in the WordPress.org Plugin Directory https://wordpress.org/plugins/ or can be cost-based plugin from a third-party with the RCrelease candidateOne of the final stages in the version release cycle, this version signals the potential to be a final release to the public. Also see alpha (beta). of 15.5.0 due today. @welcher and @greenshady will lead this one.
Updates based on updated scope for site editing projects
I’ve been focussing a lot on this PR (Refactor and stabilize selectors API) and the followup from it. The change there has quite far reaching consequences so it’s a good one to be aware of.
Working mostly on improving the fallback handling in the Nav blockBlockBlock is the abstract term used to describe units of markup that, composed together, form the content or layout of a webpage using the WordPress editor. The idea combines concepts of what in the past may have achieved with shortcodes, custom HTML, and embed discovery into a single consistent API and user experience.. It’s not quite ready for review yet but it should improve the stability.
I’m also seeking opinions on whether folks are interested in being able to give custom labels to group blocks in the list view? If you are then please +1 on this comment.
There were some regressions with the update to only render duotone filters on the page, and the selectors block.jsonJSONJSON, or JavaScript Object Notation, is a minimal, readable format for structuring data. It is used primarily to transmit data between a server and web application, as an alternative to XML.APIAPIAn API or Application Programming Interface is a software intermediary that allows programs to interact with each other and share data in limited, clearly defined ways. has been stabilized, so I’m also working on updating the duotone block supports to use that new API.
Using GithubGitHubGitHub is a website that offers online implementation of git repositories that can easily be shared, copied and modified by other developers. Public repositories are free to host, private repositories require a paid subscription. GitHub introduced the concept of the ‘pull request’ where code changes done in branches by contributors can be reviewed and discussed before being merged be the repository owner. https://github.com/ CoPilot on PR descriptions in GutenbergGutenbergThe Gutenberg project is the new Editor Interface for WordPress. The editor improves the process and experience of creating new content, making writing rich content much simpler. It uses ‘blocks’ to add richness rather than shortcodes, custom HTML etc. https://wordpress.org/gutenberg/
Folks were asked to leave their input on the Discussion in Github.
Concerns about AI in Gutenberg and WordPress
@chopinbach raised concerns about usage of AI within WordPress and Gutenberg.
@get_dave reflected that it was a valid concern but he was unaware of anywhere where AI or Deep Learning was currently in use within CoreCoreCore is the set of software required to run WordPress. The Core Development Team builds WordPress..
@get_dave asked whether leadership had previously provided any direction on the usage of AI within the WP project. No one was able to think of anything.
As this is a very large topic, @get_dave advised creating a Discussion on Github to allowed this to be discussed in a more considered manner outside of a chat-based format.
@get_dave wondered whether regularly contributors could take a moment to update the file as per their own preferences and current focus areas.
@get_dave also noted that becoming a CODEOWNER shoulld not mean that individual becomes solely responsible for a given area. The right to disconnect is important.
@fabiankaegy noted there is some fear around adding oneself to the CODEOWNERS file and suggested adding documentation to explain the purpose of the file to make it more open to changes.
@wildworks agreed to consider opening a PR to update the docs to include a section on CODEOWNERS.
So even though the intent is not that they are “guardians” of that section of the code, to new contributors submitting code it can appear as though they are fulfilling that role.
After a regressionregressionA software bug that breaks or degrades something that previously worked. Regressions are often treated as critical bugs or blockers. Recent regressions may be given higher priorities. A "3.6 regression" would be a bug in 3.6 that worked as intended in 3.5. with date formats prompted a new code freeze and the delay of the 6.2 release, the release leads decided to cancel this week’s Dev Chat.
Why?
Release parties for major versions tend to run three or more hours. So it’s likely that the 6.2 release won’t have finished by the time dev chat normally starts. Plus, if the release does finish early, lots of usual dev chat attendees will be pretty tired.
We are seeking basic workflow feedback for the Plugin Dependencies feature. Testing should be very straightforward.
The testing pluginPluginA plugin is a piece of software containing a group of functions that can be added to a WordPress website. They can extend functionality or add new features to your WordPress websites. WordPress plugins are written in the PHP programming language and integrate seamlessly with WordPress. These can be free in the WordPress.org Plugin Directory https://wordpress.org/plugins/ or can be cost-based plugin from a third-party was chosen because it fulfilled the following criteria:
Plugin is in the plugin repository.
Plugin has the required Requires PluginsheaderHeaderThe header of your site is typically the first thing people will experience. The masthead or header art located across the top of your page is part of the look and feel of your website. It can influence a visitor’s opinion about your content and you/ your organization’s brand. It may also look different on different screen sizes. for Plugin Dependencies.
Install and activate The Events Calendar CategoryCategoryThe 'category' taxonomy lets you group posts / content together that share a common bond. Categories are pre-defined and broad ranging. Colors plugin.
The goal is to see how intuitive the process is or might become.
Feedback
What did you do?
Did you get stuck? Where?
Were you able to figure out the path forward?
What did you do?
Did the experience feel “natural” to WordPress?
Thanks for testing. Testing should last for 3 weeks.
There is currently a large number of outstanding issues in the GutenbergGutenbergThe Gutenberg project is the new Editor Interface for WordPress. The editor improves the process and experience of creating new content, making writing rich content much simpler. It uses ‘blocks’ to add richness rather than shortcodes, custom HTML etc. https://wordpress.org/gutenberg/ repository with the [Type] Developer Documentation label. We think that it would help to bring the BlockBlockBlock is the abstract term used to describe units of markup that, composed together, form the content or layout of a webpage using the WordPress editor. The idea combines concepts of what in the past may have achieved with shortcodes, custom HTML, and embed discovery into a single consistent API and user experience. Editor handbook more up-to-date and correct any errors and/or omissions that may exist if some of the backlog of issues were addressed.
Starting Thursday, March 30, 2023, at 13:00, we will begin holding a weekly meeting to review and triagetriageThe act of evaluating and sorting bug reports, in order to decide priority, severity, and other factors. developer documentation issues in the Gutenberg repository. These meetings will take place every Thursday at 13:00 UTC in the #core-editor room.
The WordPress 6.2 release was due today, March 28, 2023. However, a regression with date formats has been spotted during the 24-hour freeze. Release leads have agreed to revert the ticketticketCreated for both bug reports and feature development on the bug tracker. that introduced the regressionregressionA software bug that breaks or degrades something that previously worked. Regressions are often treated as critical bugs or blockers. Recent regressions may be given higher priorities. A "3.6 regression" would be a bug in 3.6 that worked as intended in 3.5., which will require another Release Candidaterelease candidateOne of the final stages in the version release cycle, this version signals the potential to be a final release to the public. Also see alpha (beta). version, restarting the 24-hour freeze timer, and a new release date on March 29th.
Ensuring the newest version of WordPress meets the best quality standards and doesn’t introduce a regression that can impact many popular business-oriented plugins is essential.
WordPress 6.2 Release Candidate 5 has been shipped, reverting the following changeset:
Following this RCrelease candidateOne of the final stages in the version release cycle, this version signals the potential to be a final release to the public. Also see alpha (beta). release, the 24-hour code freeze timer has been restarted, and the current target release date is 2023-03-29 at 17:00 UTC.
My two focuses, get lazy loading metaMetaMeta is a term that refers to the inside workings of a group. For us, this is the team that works on internal WordPress sites like WordCamp Central and Make WordPress. across the line for term meta (working on comment meta) and implementing wp_cache_get_multiple in more places in coreCoreCore is the set of software required to run WordPress. The Core Development Team builds WordPress.
@aristath work continues in the SQLite project – as well as the php autoloader for wp-core
@joemcgill I’m just wrapping up an initial round of profiling observations, and plan to have something written up to share soon. Some highlights are that there are lots of places where we could try to reduce the use of file system reads associated with blockBlockBlock is the abstract term used to describe units of markup that, composed together, form the content or layout of a webpage using the WordPress editor. The idea combines concepts of what in the past may have achieved with shortcodes, custom HTML, and embed discovery into a single consistent API and user experience. registration and template rendering that we wanna look into. There is also a potential opportunity for some improvements to the way translations are being handled and classic seems that we also want to review.
@spacedmonkey already has some fixes in the works for some issues we discovered while comparing notes. I continue to be somewhat hampered by only being able to use one arm, but I’m working through it.
@rmccue As an aside, I noticed that the method of merging translationtranslationThe process (or result) of changing text, words, and display formatting to support another language. Also see localization, internationalization. files in memory is probably suboptimal and we might be able to avoid that. (I’ve been reimplementing pomo in native code, and noticed it there)
@olliejones Work continues on SQLite, next is to load woocommerce and beat on it.
Future project: identify as many places in core where the SQL is non-portable MySQLMySQLMySQL is a relational database management system. A database is a structured collection of data where content, configuration and other options are stored. https://www.mysql.com/. specific stuff and work on making it standard. Should that be a TRACTracAn open source project by Edgewall Software that serves as a bug tracker and project management tool for WordPress.ticketticketCreated for both bug reports and feature development on the bug tracker.?
@joemcgill I definitely think that having trac tickets that describe any improvements you’d like to see made would be useful.
JavaScriptJavaScriptJavaScript or JS is an object-oriented computer programming language commonly used to create interactive effects within web browsers. WordPress makes extensive use of JS for a better user experience. While PHP is executed on the server, JS executes within a user’s browser. https://www.javascript.com/. & CSSCSSCascading Style Sheets.
@10upsimon We are addressing the issue(s) around script concatenation, work is in progress and in the final stages of review, with minor iterations ongoing. Unit tests are being implemented to validate the approach and should be ready for final review today or tomorrow.
We are entering into a more holistic/overall code review of work done to date, essentially a code review of all work done thus far as part of the epic. Minor iteration is anticipated as part of this review process and will be executed as required.
@flixos90 I have been continuing on the lazy-loading exploration and am getting close to opening Trac tickets for the individual pieces of work
To clarify, this is about avoiding to lazy-load LCP images, or rather in-viewport images in general
@flixos90 I have also been thinking a bit about the fetchpriority="high" feature for which we already have a module. One thing that we may need to iterate on there is that it just adds the attribute to whichever first image doesn’t have loading="lazy". This is not terrible, but it’s also probably not the best way to go about it, since the two attributes should not simply be mutually exclusive. The guidance is rather:
fetchpriority="high" should be only on the LCP image.
loading="lazy" should be omitted on images above the fold (i.e. potentially more images than just the LCP image).
@joemcgill I am in the very early stages of looking into ways we can improve the way WordPress calculates the sizes attribute.
@joegrainger We have 2 tasks remaining for the PluginPluginA plugin is a piece of software containing a group of functions that can be added to a WordPress website. They can extend functionality or add new features to your WordPress websites. WordPress plugins are written in the PHP programming language and integrate seamlessly with WordPress. These can be free in the WordPress.org Plugin Directory https://wordpress.org/plugins/ or can be cost-based plugin from a third-party Checker infrastructure with plans to complete this week. Once done, we will start performing initial testing and review the infrastructure holistically before working on the additional checks. Progress can be seen on the GitHub repo here. As always, feel free to take a look and leave any thoughts/ideas you may have in the repo. Thanks!
@spacedmonkey Just flagging, I want to get the core unit tests running against redis. In my research, more hosts are using redis then memcache, so we could test against this and change our thinking of object caching in WP space from memcache to redis https://core.trac.wordpress.org/ticket/58000
@olliejones fwiw the SQlite Object Cache plugin has extensive perf. instrumentation built in.
Open Floor
@rmccue Re SQLite, I’m moderately concerned about the potential performance impact that introducing another layer of abstraction may introduce there. A traditional reason that WP hasn’t been DB-independent is because of (theoretical) performance gains by tightly coupling the two and taking advantage of that. (Which are assumptions I think do need to be tested.) I realise I’m coming in late to this, but I guess I’m just not seeing how the SQLite work ties into performance specifically. (I see a clear case for the non-performance benefits.)
@aristath Well, I admit that the tie between SQLite and performance is a bit weird… but the way I see it, it comes down to this: on a small, lower-end server, the server’s resources are shared between a php server, apacheApacheApache is the most widely used web server software. Developed and maintained by Apache Software Foundation. Apache is an Open Source software available for free., and a MySQL server. By using SQLite, the server can allocate its limited resources to php and therefore achieve better performance. It’s better for sustainability mostly, and for performance on smaller sites (that usually are hosted on cheap servers) the performance gains will be there
@rmccue I can see how eliminating the latency and translation between two separate servers for PHPPHPThe web scripting language in which WordPress is primarily architected. WordPress requires PHP 5.6.20 or higher and MySQL could help performance, not sure of the overhead if it’s on the same server; that said, it feels like the primary goals of the project are not performance related
@olliejones It might ??? be a good idea sometime to spin off a team to do dbms-independence work, the target of which would be support for SQL Server, postgreSQL, SQLite, and, gag, Oracle. Having those would help scale up WordPress sites. postgreSQL especially because it can do wildcard searches with indexes. But that imaginary project’s connection to this team is a bit tenuous, as you mention.
Discussions here continued beyond the end of the meeting
@thomasdevisser has created a discussion around restructuring the CoreCoreCore is the set of software required to run WordPress. The Core Development Team builds WordPress. Editor documentation. Please chime in with your thoughts here: https://github.com/WordPress/gutenberg/discussions/48998
Joshua de Lange shared that they are looking into a fix for a longstanding issue where the Image blockBlockBlock is the abstract term used to describe units of markup that, composed together, form the content or layout of a webpage using the WordPress editor. The idea combines concepts of what in the past may have achieved with shortcodes, custom HTML, and embed discovery into a single consistent API and user experience. doesn’t have the height/width attribute defined unless it was specifically added. https://github.com/WordPress/gutenberg/issues/23244#issuecomment-1448431121
Open Floor
@cbirdsong ran into an issue where a strict content security policy prevented a site from outputting any inline styles / style tags on the page. This directly clashes with the current approach of the block editor with the style engine. A discussion around this topic should get started on GithubGitHubGitHub is a website that offers online implementation of git repositories that can easily be shared, copied and modified by other developers. Public repositories are free to host, private repositories require a paid subscription. GitHub introduced the concept of the ‘pull request’ where code changes done in branches by contributors can be reviewed and discussed before being merged be the repository owner. https://github.com/.
GutenbergGutenbergThe Gutenberg project is the new Editor Interface for WordPress. The editor improves the process and experience of creating new content, making writing rich content much simpler. It uses ‘blocks’ to add richness rather than shortcodes, custom HTML etc. https://wordpress.org/gutenberg/ 15.5 RCrelease candidateOne of the final stages in the version release cycle, this version signals the potential to be a final release to the public. Also see alpha (beta)..
You must be logged in to post a comment.