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-stubspackage.
- 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@paramas 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-wordpressIf 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.neonNo 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 analyzethen 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. ifneeds a boolean), see Variable handling functions
- Avoid enabling exit_errorinWP_CLI::launchorWP_CLI::runcommandfor 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