UPDATE: I have written a follow-up post: Generating sustainable development funding for phpstan-drupal
The drupal-check and phpstan-drupal projects are going into an indefinite development hiatus. I have spent some time contemplating this decision. They are not abandoned. But they will not receive any active development or maintenance until they receive funding. This blog serves as an announcement, a bit of history, and a plan forward to revitalize maintenance and development.
These two projects have been a labor of love over the past two years. The phpstan-drupal extension had its first commit on December 7th, 2018. I found PHPStan while researching Centarro for the Centarro Toolbox product as a "code insight" tool. Shortly after, I realized we could find deprecated code usages. This was huge given the major effort to prepare for Drupal 9 was underway. I took my personal time to begin creating the extension so that it could be leveraged for the Drupal 9 readiness initiative.
However, it had many technical challenges. PHPStan assumes your application fully leverages Composer's autoloader. You can provide a custom autoloader script; but, Drupal didn't make this great either. Drupal's namespaces and autoloading are dynamically generated and cached in a stateful manner. You can't dump them. The main task of PHPStan Drupal was to mimic the bootstrap and discovery of extensions in a Drupal site. It also provides conversion of service names to their classes. This way, you can detect deprecated usages of entity.manager or deprecated methods on a service.
PHPStan also has an aggressive release cycle and is under active development. This is great for most users, and I applaud Ondřej Mirtes for achieving and maintaining velocity. It is just miserable when your extension is doing "all of the wrong things" to make it work with a codebase.
Beyond just a PHPStan extension
The phpstan-drupal project is also not just a PHPStan extension. It's morphed into an integral part of the Drupal ecosystem.
After an email from Dries, drupal-check was created two months later as a wrapper around PHPStan and its configuration. In fact, he showed it off during his Driesnote at DrupalCon Seattle. Here's the recording, starting at the demo of finding deprecated code via drupal-check: https://youtu.be/Nf_aD3dTloY?t=5253
The projects quickly became a major part of the Drupal 9 readiness tooling. Gábor Hojtsy brought it to a whole new level by integrating it into the Upgrade Status module. The Upgrade Status module will execute PHPStan to find deprecated code calls and more stateful things – such as deprecated hooks and deprecated asset libraries.
There is even a job on Drupal.org, which runs PHPStan to find all contributed projects' overall upgrade status: https://dispatcher.drupalci.org/job/phpstan/. Acquia has amazingly turned these results into a browseable table: https://dev.acquia.com/drupal9/deprecation_status.
And now we are here. Drupal 9 is released. We're onto release Drupal 9.2. We're also preparing for Drupal 10. The need for PHPStan and the phpstan-drupal are here to stay.
Why is it so hard?
We have Drupal 8 that must remain supported. We also need to support Drupal 9. Luckily that's pretty easy to do, but it makes the testing infrastructure wonky. I have PHPUnit tests that verify the discovery of deprecated code. These always fail on D9. My planned workaround involves different test suites or groups that run based on the testing matrix.
But now, we have PHP 7 and PHP 8 support. A PR opened, but I haven't had time to review and add a PHP 8 testing pipeline.
The real icing on the cake and a summary of constant problems is the following story:
There was a recent bug that I solved that caused PHPStan to crash. It was a compatibility layer between PHPUnit versions. In fact, the bug wasn't in phpstan-drupal or PHPStan. It was in nikic/php-parser and how optional PHP 8 attributes were handled on traits. Yeah, it wasn't fun. The problem was first reported on Oct 8th and wasn't resolved until December 21st. I probably sunk 30 hours into the bug.
If you're interested, here is a retrospective of the bug: https://mglaman.dev/blog/phpstan-drupal-0127-released-latest-phpstan-no…. I also tackled the bug on a live stream as well: https://www.youtube.com/watch?v=6-WkQ0Gfwmc.
Why indefinitely pause development?
Okay, so I hope you understand the maintenance burden and the usefulness of this tool. Gábor pinged me in the Drupal slack about phpstan-drupal's missing PHP 8 support blocking the Drupal 9 support in Upgrade Status. Andrey Postnikov (andypost) has also been working on this and provided the PR to phpstan-drupal. I could merge it blindly. But there's a bigger problem, and this brought me here.
There aren't any tests for phpstan-drupal against Drupal 9. The testing matrix isn't ready, as I just said. I don't have the time or will to set on my weekend flushing this out. I spent two hours on it before a live stream (potato quality, sorry) and haven't gone back.
Let's talk funding
I set up GitHub Sponsors to try and receive funding for my open source work in the fall. I have six sponsors, coming in at roughly $62 a month (about 40 minutes of work a month.) I am beyond grateful to these individuals (yes, individuals.) They use their personal funds to ensure I work on my open source projects (phpstan-drupal, drupal-check, contribkanban.com, etc.)
In fact, I wrote about the emotional boost it gave a few months ago. However, these projects have moved beyond that.
I need to find a way to secure funding for the development of these projects. And, I would rather it not rely on individuals or Acquia. We need to face a few facts:
- Individual developers are funding way too much of open source in a roundabout way, not their organizations.
- Acquia supports so much Drupal development. Other organizations need to step up their share (let's face it, without Acquia putting a bunch of Drupal core contributors on the payroll, where would we be?)
I know organizations have drupal-check and phpstan-drupal in their build pipelines to prevent launching deprecated code. I had connected the projects to TideLift in hopes this might be a revenue source. But, in hindsight, I doubt any Drupal site is running through that service.
Gábor asked the big question: do I have any estimates on the funding needed for the PHP 8?
I have no idea. Because adding PHP 8 testing support means adding Drupal 9 testing support. A quick guess would be $2,000 for 20 hours of work. I also don't have the time to sit and make a full discovery to estimate each task. Maybe I would if I knew this generated revenue of the task (someone would actually pay if I estimated.)
GitHub Sponsors is now available to organizations to sponsor an organization, or an organization can be a sponsor. Maybe organizations need to become more aware of this.
I can make an Open Collective for phpstan-drupal, which would also support drupal-check. But I don't know if that's a viable solution.
I had thought about making a hosted version of drupal-check that runs as its own service. However, I do not see a market fit with how easy it is to add to your current CI workflow.
I have done some bounties on Gitcoin (I'd rather that than Bountysource.) However, I don't think any services where the maintainer sets a fee versus someone wanting the problem solved setting a fee.
Thanks for taking the time to read this. I am open to suggestions on how to develop and maintain drupal-check and phpstan-drupal sustainably. If your organization is worried about "getting their money's worth" out of a monthly contribution versus paying for specific work, ask them to evaluate how much they rely on the tool daily – whether it is working or not.
So, I realized that I didn't exactly say "what it means to be funded" beyond the fact I can pay for the hours I work. Since I published this blog post, I have received more sponsors on GitHub and now receive an estimated $177.00 a month ($115 increase!). I have a goal on GitHub Sponsors set to $500 a month. That would sustain 5 hours of development a month. This wouldn't help much for active feature development or integrating PHPStan into Drupal core more (see [META] Start running PHPStan on Drupal core (level 0).)