tl;dr Several official WordPress projects use PHPStan for static code analysis "...the analysis of computer software that is performed without actually executing programs, in contrast with dynamic analysis, which is analysis performed on programs while they are executing." - Wikipedia of PHP The web scripting language in which WordPress is primarily architected. WordPress requires PHP 7.4 or higher files as part of their development tooling and quality control. It’s used by thousands of WordPress plugins and themes to catch and prevent bugs before they’re committed. Let’s use it for WordPress core Core is the set of software required to run WordPress. The Core Development Team builds WordPress. too.
What is PHPStan?
PHPStan is a mature, popular, and well-maintained static code analysis tool for PHP. From the PHPStan website:
PHPStan scans your whole codebase and looks for both obvious & tricky bugs. Even in those rarely executed if
statements that certainly aren’t covered by tests.
You can run it on your machine and in CI to prevent those bugs ever reaching your customers in production.
PHPStan provides a means of scanning 100% of the PHP code in a project and identifying whole classes of bugs relating to code correctness within the context of the project as a whole, even before executing, testing, or writing tests for the code.
Another static code analysis tool that is already in wide use in WordPress is PHP_CodeSniffer (PHPCS PHP Code Sniffer, a popular tool for analyzing code quality. The WordPress Coding Standards rely on PHPCS.), which checks adherence to coding standards that primarily relate to code formatting (although the WordPress Coding Standards The Accessibility, PHP, JavaScript, CSS, HTML, etc. coding standards as published in the WordPress Coding Standards Handbook.
May also refer to The collection of PHP_CodeSniffer rules (sniffs) used to format and validate PHP code developed for WordPress according to the PHP coding standards. provides additional rules for security, performance, and internationalisation best practices). PHPStan doesn’t care about coding style, it is un-opinionated and only tests the validity and correctness of code using increasingly strict levels of rules which allow it to be gradually introduced into an existing code base, even one the size and age of WordPress. It is complementary to PHPCS, not a replacement.
What is being proposed?
On #61175, @westonruter notes that:
PHPStan is a vital static analysis tool for identifying bugs in code. Previously it has been used to identify problems in core by manually running PHPStan on the core codebase.
This post proposes that:
- PHPStan gets added as a development dependency to WordPress with the required settings and a configured baseline.
- PHPStan analysis runs as a required check during CI on GitHub GitHub 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/ Actions.
- Documentation on usage of PHPStan gets added to the core handbook.
- These changes are implemented during the WordPress 6.9 development cycle.
@justlevine has kindly been working on the bulk of the core implementation, the baseline, and the CI workflow in this pull request on GitHub. Work on a documentation page for the handbook is yet to start.
The advantage of implementing a baseline is that PHPStan analysis can be introduced without having to make sweeping changes to the core codebase in order to pass all of the PHPStan rules from day one. The analysis will apply to code changes going forward, and existing issues in the baseline can continue to be addressed just as they have been in recent releases.
Benefits of PHPStan
Adopting PHPStan improves our codebase and development workflows in several ways:
- Catch bugs in untested code: Unit, integration, and E2E tests only cover the code they execute. PHPStan can find bugs in code that isn’t explicitly tested, and make sure that code changes don’t introduce new bugs even in old code that has no tests.
- Prevent logic and type errors: Unlike the enforcement of code formatting in PHPCS, PHPStan can trace the flow of code execution and identify critical errors that would otherwise only be caught at runtime. This is increasingly important as we work to maintain compatibility with the increasingly strict type safety requirements of PHP.
- Improve contributor experience (for humans and 🤖): PHPStan provides immediate, automated feedback to contributors, helping new, veteran, and even agentic developers catch their mistakes and learn how to navigate the WordPress codebase. This reduces the burden on committers during code review and helps AI tooling use WordPress as accurately as possible.
- Incremental adoption: PHPStan provides levels of strictness that can be adopted incrementally, as well as ways to ignore rules and baseline errors in preexisting code without interrupting the codebase. This keeps in line with the policy against unnecessary code refactoring.
Taken together, using PHPStan will help the project maintain and improve the quality and correctness of the WordPress codebase, paving the way for faster development, fewer bugs, and the safe adoption of newer PHP features over time.
While not a part of this proposal, PHPStan also offers benefits such as type narrowing, IDE Integrated Development Environment. A software package that provides a full suite of functionality to software developers/programmers. Normally an IDE includes a source code editor, code-build tools and debugging functionality. hinting, documentation, and code validation features like generics, callable signatures, integer ranges, and lots more. These enhancements can be implemented as and when appropriate.
Concerns
When the implementation of native TypeScript in Gutenberg was proposed, there were some concerns raised:
- The use of TypeScript could raise the barrier to entry for contributors.
- TypeScript may not be here forever (ie. it could be outlasted by the underlying language).
If similar concerns are applied to the implementation of PHPStan:
- Like any tool, there is an element of learning involved and there is always a risk of raising the barrier to entry, however that should not be a reason to refrain from introducing new tooling that provides an overall benefit to the project. Contributors who have not used PHPStan before may not be familiar with its error messages and may need guidance addressing issues that it reports, but handbook documentation, guidance from others, and general familiarisation over time will help. We’ll likely also find that the new generation of PHP developers is familiar with PHPStan due to its wide usage in many other popular and newer projects.
- Unlike TypeScript, PHPStan isn’t a language itself that needs to be interpreted or transpiled in order to convert it to the PHP code that runs WordPress. If the PHPStan project were to disappear, WordPress would continue to work, the PHPStan checks could be removed, and another static analyzer could be implemented if necessary. That said, PHPStan is an active and well-maintained project so this shouldn’t be a concern.
You might have heard that PHPStan is only used to check type declarations, but this is not correct. In fact it only takes types into account when you start using it at level 3 or higher, and its scope is far beyond just type safety. Take a look through the PHPStan rule levels to see what it covers.
You might have heard that PHPStan only works for object-oriented codebases, this is also not correct. There is nothing inherent about PHPStan that restricts it to analyzing only OOP code. It works great with functional, procedural, and OOP code, with and without namespaces, and mostly whatever else you can throw at it, including excellent support for incomplete code.
There are two alternatives to PHPStan: Psalm and Phan. All three of these static code analysis tools are mature, popular, and well-maintained. PHPStan is being proposed because it’s the most popular out of these three tools (both inside and outside of the WordPress ecosystem), and because it’s the one that is most familiar to contributors to other official WordPress projects, and contributors and committers to WordPress core. Implementing PHPStan will not prevent developers using Psalm or Phan to scan their plugins, themes, or projects, or indeed to scan WordPress core using those tools too.
What about Gutenberg The 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/?
The Gutenberg repo does not use PHPStan, however it would benefit from doing so in the same way that WordPress core will. A proposal to implement PHPStan into the development of Gutenberg can be found here. It’s not strictly part of this proposal, but the teams do need to determine whether this is a prerequisite.
Does this affect end users?
End users and website owners are not directly affected by this change. PHPStan itself does not affect PHP at runtime in much the same way that TypeScript doesn’t affect JavaScript JavaScript 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/. at runtime. The purpose of this class of tooling is to allow developers to maintain code at a higher standard.
The effect this has on end users, consumers, developers, and web hosts is a higher quality application that is more maintainable, reliable, and correct, and will continue to be so over time.
Next steps
- This proposal can stay open for a couple of weeks as several northern hemispherical contributors and committers are enjoying well-earned holidays.
- Work needs to continue on the pull request that adds the configuration, baseline, and CI.
- Continued communication needs to happen with the Gutenberg team to determine whether PHPStan scanning in Gutenberg is a prerequisite.
- A documentation page for the handbook needs to be drafted.
The latest version of PHPStan will be used (currently 2.1.17). This requires PHP 7.4 or greater which means the implementation of PHPStan depends on the minimum supported version of PHP in WordPress being increased to 7.4, which is under consideration for WordPress 6.9. Therefore the 6.9 development cycle needs to be announced before this change can be implemented. In the meantime there is no need to be concerned about PHPStan failures on PHP 7.2 and 7.3 in the pull request.
Further technical details can be found on ticket Created for both bug reports and feature development on the bug tracker. #61175.
Elsewhere
If you’re curious about how other projects use PHPStan, here are some links.
PHPStan is used by thousands of WordPress plugins, themes, tools, and projects, and 25,000 packages across the PHP ecosystem.
It’s been in use for years by several other official WordPress projects, including:
It’s also been used previously by individual contributors to remediate many issues in WordPress core, most recently in #63268.
If you are interested in using PHPStan as part of the development tooling in your plugin 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, theme, or project, you should take a look at the phpstan-wordpress package by Viktor Szépe which provides WordPress-specific extensions for PHPStan.
Acknowledgements
Thanks to @justlevine @westonruter @swissspidy @sergeybiryukov and others for their work on PHPStan fixes in recent releases and for helping with this proposal.
#developer-experience, #php