Roots Discourse

Composer mu-plugins

I’ve been trying to get muplugins working with composer and have yet to find the proper way to specify which packages should be using the muplugins custom installer path. My end goal is to supply a theme that may have plugin dependencies and I want to ensure front end users are unable to remove them.

When I supply a wpackagist/repository, the type (wordpress-plugin) is automatically chosen from the package definitions at wpackagist it would seem. Additionally when attempting to use the new method (wpackagist-theme/plugin) I’m also unable to supply the argument to specify wpackagist-muplugin to work the way I expect it.

How do I specify a wpackagist plugin to use the mu-plugin directory?

I do not want to create my own repository/installer to house the files so that I can still use the wildcard notation between minor versions just to specify the type “wordpress-muplugin” as it appears in the lockfile.

This will be complicated.

Unfortunately, mu-plugins and plugins are not always interchangeable.

  • Must-use plugins are initiated from the mu-plugins root. Every file in the root is included, but folders are not traversed.

  • Standard plugins are different and can be initiated from their own folder plugins/my-plugin-name/ or the root plugins/my-other-plugin-name.php.

This means that re-declaring the package type from plugin to mu-plugin will only work for one-file, no folder plugins (CPTs, taxonomies etc - the stuff you probably wouldn’t be getting from wpackagist).

To get around this limitation you would have to create your own must-use loader plugin that initiates the plugins you want to be treated as mu-plugins or hope that all the plugins you need use PSR-4 autoloading (hint: they won’t).

You would also need to re-order the installer-paths in Bedrock and add the package to the mu-plugin installer-path array:

"extra": {
    "installer-paths": {
      "web/app/mu-plugins/{$name}/": ["type:wordpress-muplugin", "wpackagist-plugin/my-plugin-name"],
      "web/app/plugins/{$name}/": ["type:wordpress-plugin"],
      "web/app/themes/{$name}/": ["type:wordpress-theme"]
    },
1 Like

Nick,

Thanks so much for your answer. I was extremely excited when I woke up and saw it. Your response instantly got the gears turning in my head, along with my first coffee, when it dawned on me that in searching for an answer to the mu-plugin/composer concept that I had already run across a solution to how to load the files from the subdirectories as well.

The first caveat in the must use plugins that I have not yet worked out is the fact that no activation hooks are run. This will essentially mean that any plugin that utilizes activation hooks that may create requisite DB fields are unlikely to work without another solution.

The second caveat that I see (yet have solved) is that composer will need to be run in a cron across the plugins to keep them updated between minor subversions. Further updates to the major and minor versions will need to be human verified. (testing, reading change logs)

I’m working out a package right now for the rest of the community!

Thanks again.

Just so you know, I started putting a plugin together too. It’s about 80% done and it doesn’t have the activation issue as it executes the activation hook when a new plugin is found.

I should have time to complete it over the weekend so we can compare notes then.

I notice you slipped (what I believe to be) this plugin into Bedrock 7 days ago. However, I’m not certain how to actually use it, and the readme does not mention it. Any usage suggestions?

More details are available in the Bedrock README.

If you have any questions after reading that, let me know.