Introducing Plugin Dependencies in WordPress 6.5

Overview

#22316 introduces PluginPlugin A 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 Dependencies to WordPress.

Extensibility of WordPress through plugins and the HooksHooks In 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. APIAPI An 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. is one of its most beneficial features. There are many plugins that act purely as extensions of others, building functionality on top. The Plugin Dependencies feature aims to make the process of installing and activating addons (dependents) and the plugins they rely on (dependencies) consistent and easy.

New Plugin HeaderHeader The 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.

A new Requires Plugins header has been introduced.

This must contain a comma-separated list of WordPress.orgWordPress.org The community site where WordPress code is created and shared by the users. This is where you can download the source code for WordPress core, plugins and themes as well as the central location for community conversations and organization. https://wordpress.org/-formatted slugs for its dependencies, such as my-plugin (my-plugin/my-plugin.php is not supported). It does not support commas in plugin slugs.

How to use the new header

/**
* Plugin Name: Express Payment Gateway Checkout for Shop
* Requires Plugins: shop, payment-gateway
 */

Requirements

Dependent plugins

The following requirements are placed on dependent plugins:

  • Cannot be installed until its dependencies are installed.
  • Cannot be activated until its dependencies are activated.

Dependency plugins

The following requirements are placed on dependency plugins:

  • Cannot be deactivated while its dependents are activated.
  • Cannot be deleted while its dependents are installed.

What happens if a dependency is no longer met?

If a dependency plugin is deleted via FTPFTP FTP is an acronym for File Transfer Protocol which is a way of moving computer files from one computer to another via the Internet. You can use software, known as a FTP client, to upload files to a server for a WordPress website. https://codex.wordpress.org/FTP_Clients. or deployment, a notice will be displayed on the administration’s plugin screens, informing the user that there are missing dependencies to install and/or activate. Additionally, each dependent whose dependencies are no longer met will have an error notice in their plugin row.

What happens if a plugin update has a new dependency?

The update will be allowed for now, and the dependent will remain active. A notice will be displayed on the administration’s plugin screens, informing the user that there are missing dependencies to install and/or activate.

What happens if there are circular dependencies?

A circular dependency is when two or more plugins form a loopLoop The Loop is PHP code used by WordPress to display posts. Using The Loop, WordPress processes each post to be displayed on the current page, and formats it according to how it matches specified criteria within The Loop tags. Any HTML or PHP code in the Loop will be processed on each post. https://codex.wordpress.org/The_Loop. in their requirements.

For example: Plugin A requires Plugin B requires Plugin C requires Plugin A

Plugin Dependencies includes circular dependency detection, and will display a notice to inform users of plugins whose requirements are invalidinvalid A resolution on the bug tracker (and generally common in software development, sometimes also notabug) that indicates the ticket is not a bug, is a support request, or is generally invalid.. The plugins cannot be activated, and users should contact the plugin authors so that this circular reference can be broken where appropriate.

Is defensive coding still needed?

Yes. Plugin Dependencies makes it easier for the user to install and activate required plugins, and informs them when these are not met. This means plugin authors can safely remove checks and notices when their dependencies are not installed or activated.

However, at this time, Plugin Dependencies does not include minimum or maximum version support for dependencies, nor does it account for the loading order of plugins. Plugin authors should therefore continue to use function|class|interface_exists() and version checks where their plugin relies on specific functionality being available at a given time.

Does Plugin Dependencies affect WP-CLIWP-CLI WP-CLI is the Command Line Interface for WordPress, used to do administrative and development tasks in a programmatic way. The project page is http://wp-cli.org/ https://make.wordpress.org/cli/?

Plugin Dependencies does not prevent the installation of dependent plugins without their dependencies via WP-CLI, as it is assumed that those using WP-CLI are advanced users that are aware of their dependency stack. However, to avoid missing dependencies going unnoticed, dependent plugins cannot be activated using WP-CLI until their dependencies are activated.

This affects wp plugin activate --all, which may need to be run multiple times if a dependent appears alphabetically earlier than its dependencies. We plan to collaborate with WP-CLI maintainers on possible ways of easing this burden by exploring loading order in WordPress CoreCore Core is the set of software required to run WordPress. The Core Development Team builds WordPress., WP-CLI, or both, if appropriate.

Limitations

Plugins hosted on WordPress.org

Dependent plugins hosted on WordPress.org can only declare dependencies that are also hosted on WordPress.org. If your plugin hosted on WordPress.org requires plugins that are not hosted there, it is recommended that you do not use the Requires Plugins header in your plugin at this time.

Plugins not hosted on WordPress.org

Dependent plugins not hosted on WordPress.org can declare dependencies whether hosted on WordPress.org or elsewhere. However, the UIUI User interface will not provide an installation link for the third-party dependencies, and these must continue to be installed manually by the user.

Must-Use plugins as dependencies

Must-Use plugins as dependencies are not officially supported by WordPress Core at this time. Discussion will continue in #60504 and we will release further information when decisions about possible future support have been made.

Themes that require plugins

Themes that require plugins are not supported by Plugin Dependencies at this time, and theme authors should continue to use the checks and messaging that they have in place.

New FilterFilter Filters 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.

The wp_plugin_dependencies_slug filter hook has been introduced to allow for alterations to dependency slugs. For example, if a dependent plugin declares my-plugin as a dependency, and a premium version of my-plugin exists, the premium version can filter the slug and convert it to my-plugin-pro so that it can be detected by Plugin Dependencies.

  • Parameters
    string $slug – The slug.

Example usage

add_filter( 'wp_plugin_dependencies_slug', 'convert_myplugin_to_myplugin_pro' );

function convert_myplugin_to_myplugin_pro( $slug ) {
if ( 'my-plugin' === $slug ) {
$slug = 'my-plugin-pro';
}
return $slug;
}

UI Changes

Plugins > Installed plugins

The following changes are made:

  • Dependent plugin rows now contain a list of their dependencies, linked to the respective plugin modal to install and activate the dependency.
  • Dependency plugin rows now contain a list of their dependents.
  • If a plugin has dependencies that are not installed and active, the Activate link is disabled.
  • If a plugin has dependents that are active, the Deactivate and Delete links are disabled.
  • Bulk Actions are disabled for dependency plugins.

Before

Three plugin rows, with one plugin requiring the other two. However, there is no indication or enforcement of the requirements.
No dependents or dependencies are listed.

After

Three plugin rows, with one plugin requiring the other two. The requirements are listed under "Requires" and "Required by" sections. The Bulk Actions checkbox is disabled, as well as the Activate, Deactivate, or Delete actions, depending on the status of the plugins.
Dependents and dependencies are listed, and actions are enabled/disabled based on the status of requirements.

Plugins > Add New

The following changes are made:

  • If a plugin has unmet dependencies, the Install Now and Activate buttons are disabled, both in their plugin card and their plugin information modal.
  • Dependent plugin cards now contain a notice listing their dependencies, with a More Details link to the dependency’s information modal which contains Install Now or Activate buttons based on their current installation status.
  • Plugin information modals are now persistent after button clicks, and modal-based plugin installation and activation are now performed through AJAX directly within the modal.

Before

Plugin card with no dependencies listed and an active Install Now button despite unmet dependencies.

After

Plugin card with dependencies listed with modal links to install and activate each dependency, and the Install Now button disabled while dependencies are unmet.

Onboarding experiences

Due to the unified AJAX approach now used on the Plugins > Add New screen, activation of a plugin will no longer automatically redirect to the Plugins > Installed plugins screen, or to onboarding experiences implemented by plugin authors. This allows users to install and activate multiple plugins without leaving their current context.

Plugins with onboarding experiences usually incorporate checks so that if, for example, their plugin is installed and activated using WP-CLI, the onboarding experience will be triggered when the user enters one of the plugin’s settings screens. Such implementations will be unaffected by Plugin Dependencies, as will activation from the Plugins > Installed plugins screen Activate link.

New WP_Plugin_Dependencies Class

A new WP_Plugin_Dependencies class has been introduced.

The following public API methods are available:

static ::initialize()
Initializes Plugin Dependencies by reading dependencies from the Requires Plugins header, and fetching Plugins API data for dependencies. This runs only once per execution.

static ::has_dependents( $plugin_file )
Determines whether the plugin has plugins that depend on it.

  • Parameters
    string $plugin_file – The plugin file, relative to the plugins directory.
  • Return value
    bool Whether the plugin has plugins that depend on it.

static ::has_dependencies( $plugin_file )
Determines whether the plugin has plugin dependencies.

  • Parameters
    string $plugin_file – The plugin file, relative to the plugins directory.
  • Return value
    bool Whether the plugin has plugin dependencies.

static ::has_active_dependents( $plugin_file )
Determines whether the plugin has active dependents.

  • Parameters
    string $plugin_file – The plugin file, relative to the plugins directory.
  • Return value
    bool Whether the plugin has active dependents.

static ::get_dependents( $slug )
Gets filepaths of plugins that require the dependency.

  • Parameters
    string $slug – The dependency’s slug.
  • Return value
    array An array of dependent plugin filepaths, relative to the plugins directory.

static ::get_dependencies( $plugin_file )
Gets the slugs of plugins that the dependent requires.

  • Parameters
    string $plugin_file – The dependent plugin’s filepath, relative to the plugins directory.
  • Return value
    array An array of dependency plugin slugs.

static ::get_dependent_filepath( $slug )
Gets a dependent plugin’s filepath.

  • Parameters
    string $slug – The dependent plugin’s slug.
  • Return value
    string|false The dependent plugin’s filepath, relative to the plugins directory, or false if the plugin has no dependencies.

static ::get_dependency_filepath( $slug )
Gets the filepath for a dependency, relative to the plugin’s directory.

  • Parameters
    string $slug – The dependency’s slug.
  • Return value
    string|false If installed, the dependency’s filepath relative to the plugins directory, otherwise false.

static ::has_unmet_dependencies( $plugin_file )
Determines whether the plugin has unmet dependencies.

  • Parameters
    string $plugin_file – The plugin’s filepath, relative to the plugins directory.
  • Return value
    bool Whether the plugin has unmet dependencies.

static ::has_circular_dependency( $plugin_file )
Determines whether the plugin has a circular dependency.

  • Parameters
    string $plugin_file – The plugin’s filepath, relative to the plugins directory.
  • Return value
    bool Whether the plugin has a circular dependency.

static ::get_dependent_names( $plugin_file )
Gets the names of plugins that require the plugin.

  • Parameters
    string $plugin_file – The plugin’s filepath, relative to the plugins directory.
  • Return value
    array An array of dependent names.

static ::get_dependency_names( $plugin_file )
Gets the names of plugins required by the plugin.

  • Parameters
    string $plugin_file – The dependent plugin’s filepath, relative to the plugins directory.
  • Return value
    array An array of dependency names.

static ::get_dependency_data( $slug )
Returns API data for the dependency.

  • Parameters
    string $slug – The dependency’s slug.
  • Return value
    array|false The dependency’s API data on success, otherwise false.

FAQs

Where can I stay updated on the future development of Plugin Dependencies?

The Plugin Dependencies feature plugin will no longer receive updates now that the Plugin Dependencies feature has been merged into WordPress Core. The feature will be primarily maintained by contributors to the Upgrade/Install and Plugins components. You can stay updated on Plugin Dependencies and other developments by subscribing to the blog.

How can I get involved in the future development of Plugin Dependencies?

You can join us in the #core-upgrade-install channel on Slack. Our weekly meetings are held every Wednesday at 18:00 UTC. Tickets will be opened on WordPress Core Trac.

How can I report an issue?

You can search for an existing ticket or create a new ticket with the type of defect (bugbug A 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.) on WordPress Core TracTrac An open source project by Edgewall Software that serves as a bug tracker and project management tool for WordPress..

How can I request an enhancementenhancement Enhancements are simple improvements to WordPress, such as the addition of a hook, a new feature, or an improvement to an existing feature.?

You can search for an existing ticket or create a new ticket with the type of enhancement on WordPress Core Trac.

Props to @afragen and @swissspidy for technical review, and @stevenlinx for copy review.

In memory of Alex Mills and Alex King.
WordPress Remembers.

#6-5, #dev-notes, #dev-notes-6-5