Important
Hello everyone! This is Viktor who runs this PHPStan extension. I am planning to stop contributing to the WordPress ecosystem because it is extremely difficult and no one asks me to join his team as I am a thinker, a devops person, a tool maker (not a builder).
Please support my work to avoid abandoning this package.
Thank you!
Static analysis for the WordPress ecosystem.
- Enables PHPStan to analyze WordPress plugins and themes.
- Loads the
php-stubs/wordpress-stubs
package. - Provides dynamic return type extensions for functions that are not covered in
php-stubs/wordpress-stubs
- Defines some WordPress core constants.
- Validates optional docblocks before
apply_filters()
anddo_action()
calls, treating the type of the first@param
as definitive.
- PHPStan 2.0 or higher
- PHP 7.4 or higher (tested up to PHP 8.3)
To use this extension, require it in Composer:
composer require --dev szepeviktor/phpstan-wordpress
If you also install phpstan/extension-installer then you're all set!
If you don't want to use phpstan/extension-installer
, include extension.neon
in your project's PHPStan config:
includes:
- vendor/szepeviktor/phpstan-wordpress/extension.neon
No additional setup is needed. 😃 Just configure PHPStan - for example - as shown below:
parameters:
level: 5
paths:
- plugin.php
- inc/
For more details, visit the PHPStan Config Reference.
💡 Use the Composer autoloader or a custom autoloader!
Run the analysis with:
vendor/bin/phpstan analyze
then fix an error and GOTO 10
!
You find further information in the examples
directory,
e.g. examples/phpstan.neon.dist
Refer to WooCommerce Stubs for specific guidance.
The WordPress ecosystem often uses PHPDoc docblocks in a non-standard way to
document parameters passed to apply_filters()
.
Here’s an example:
/**
* Filters the page title when creating an HTML drop-down list of pages.
*
* @param string $title Page title.
* @param WP_Post $page Page data object.
*/
$title = apply_filters( 'list_pages', $title, $page );
This extension reads these docblocks and instructs PHPStan to treat the filter’s
return type as certain, based on the first @param
tag. In this example,
PHPStan interprets $title
as string
.
For best results, ensure the first @param
tag in these docblocks is accurate.
- Write clean OOP code: 1 class per file, and no additional code outside
class Name { ... }
. - Use consistent class naming (WPCS or PSR-4) and store classes in a dedicated
inc/
directory. - Add precise PHPDoc blocks to classes, properties, methods, functions, and
apply_filters()
calls. - Choose your main plugin file parts.
- Avoid using core constants, use core functions.
- Avoid bad PHP practices, such as:
- functions:
eval
,extract
,compact
,list
- type juggling:
$a = '15'; if ($a) ...
- functions:
- If you need robust code try avoiding all kinds of type juggling (e.g.
if
needs a boolean), see Variable handling functions - Avoid enabling
exit_error
inWP_CLI::launch
orWP_CLI::runcommand
for improved testability.
WordPress uses conditional function and class definition to allow overrides.
Use sed
command to exclude function stubs when they are previously defined.
sed -i -e 's#function is_gd_image#function __is_gd_image#' vendor/php-stubs/wordpress-stubs/wordpress-stubs.php