Skip to content

Simtel/phpstan-rules

Folders and files

NameName
Last commit message
Last commit date

Latest commit

Β 

History

41 Commits
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 

Repository files navigation

PHPStan Extended Rules

License PHP Version PHPStan

A collection of custom PHPStan rules that enforce coding standards and improve code quality in PHP projects. This extension provides additional static analysis rules focused on naming conventions, annotations, and PHPDoc consistency.

🎯 Features

This package includes three powerful rules that help maintain high code quality:

1. Command-Handler Relationship Rule

Rule: CommandClassShouldBeHelpCommandHandlerClass

Enforces that classes ending with "Command" must have a @see PHPDoc tag pointing to their corresponding CommandHandler class.

Example:

/**
 * @see CreateUserCommandHandler
 */
class CreateUserCommand
{
    // Command implementation
}

Exception: Classes with an __invoke method are exempt from this rule.

2. Event Listener Attribute Rule

Rule: EventListenerClassShouldBeIncludeAsListenerAttribute

Ensures that classes ending with "EventListener" are properly annotated with the #[AsEventListener] attribute.

Example:

use Symfony\Component\EventDispatcher\Attribute\AsEventListener;

#[AsEventListener]
class UserRegisteredEventListener
{
    // Event listener implementation
}

3. Redundant PHPDoc Return Type Rule

Rule: NotShouldPhpdocReturnIfExistTypeHint

Prevents redundant or conflicting @return PHPDoc annotations when native return type hints are already declared.

Good:

public function getUser(): User
{
    return $this->user;
}

Bad:

/**
 * @return User
 */
public function getUser(): User  // Redundant @return annotation
{
    return $this->user;
}

πŸ“¦ Installation

System Requirements

  • PHP: >8.3
  • PHPStan: ^2.0
  • PHPStan PHPDoc Parser: ^2.2

Install via Composer

Install the package as a development dependency:

composer require --dev simtel/phpstan-rules

βš™οΈ Configuration

Option 1: Include All Rules (Recommended)

Add the bundled configuration to your phpstan.neon or phpstan.dist.neon:

includes:
    - vendor/simtel/phpstan-rules/rules.neon

Option 2: Manual Rule Registration

For granular control, register specific rules:

parameters:
    rules:
        - Simtel\PHPStanRules\Rule\CommandClassShouldBeHelpCommandHandlerClass
        - Simtel\PHPStanRules\Rule\EventListenerClassShouldBeIncludeAsListenerAttribute
        - Simtel\PHPStanRules\Rule\NotShouldPhpdocReturnIfExistTypeHint

Complete Configuration Example

includes:
    - vendor/simtel/phpstan-rules/rules.neon

parameters:
    level: 8
    paths:
        - src/
    excludePaths:
        - tests/
    ignoreErrors:
        # Exclude specific patterns if needed
        - '#Command class should be include phpDoc with @see attribute#'
          path: src/Deprecated/

πŸ”§ Development

Setting Up Development Environment

  1. Clone the repository:

    git clone <repository-url> phpstan-rules
    cd phpstan-rules
  2. Install dependencies:

    composer install

Development Commands

Running Tests

# Run all tests
vendor/bin/phpunit

# Run specific test class
vendor/bin/phpunit tests/Rules/CommandClassShouldBeHelpCommandHandlerClassTest.php

Code Style

# Check coding standards
vendor/bin/ecs check

# Fix coding standards automatically
vendor/bin/ecs fix

Static Analysis

# Run PHPStan on the project itself
vendor/bin/phpstan analyse

Project Structure

.
β”œβ”€β”€ src/Rule/                          # Rule implementations
β”‚   β”œβ”€β”€ CommandClassShouldBeHelpCommandHandlerClass.php
β”‚   β”œβ”€β”€ EventListenerClassShouldBeIncludeAsListenerAttribute.php
β”‚   └── NotShouldPhpdocReturnIfExistTypeHint.php
β”œβ”€β”€ tests/
β”‚   β”œβ”€β”€ Fixture/                        # Test code samples
β”‚   β”‚   β”œβ”€β”€ EventListener/
β”‚   β”‚   └── Return/
β”‚   β”œβ”€β”€ Rules/                          # Unit tests for rules
β”‚   └── data/                           # Additional test data
β”œβ”€β”€ composer.json                       # Package configuration
β”œβ”€β”€ ecs.php                            # ECS configuration
└── README.md                          # This file

Creating New Rules

  1. Implement the Rule Interface:

    <?php
    
    namespace Simtel\PHPStanRules\Rule;
    
    use PHPStan\Rules\Rule;
    
    /**
     * @implements Rule<NodeType>
     */
    final class YourNewRule implements Rule
    {
        public function getNodeType(): string
        {
            return NodeType::class;
        }
    
        public function processNode(Node $node, Scope $scope): array
        {
            // Rule implementation
        }
    }
  2. Create Test Cases:

    <?php
    
    namespace Simtel\PHPStanRules\Tests\Rules;
    
    use PHPStan\Rules\Rule;
    use PHPStan\Testing\RuleTestCase;
    
    class YourNewRuleTest extends RuleTestCase
    {
        protected function getRule(): Rule
        {
            return new YourNewRule();
        }
    
        public function testValidCase(): void
        {
            $this->analyse([__DIR__ . '/../Fixture/Valid.php'], []);
        }
    }
  3. Add Fixture Files: Create test PHP files in tests/Fixture/ to validate rule behavior.

Testing Strategy

The project uses PHPUnit with PHPStan's RuleTestCase base class:

  • Fixture Files: Real PHP code examples in tests/Fixture/
  • Data Files: Additional test scenarios in tests/data/
  • Unit Tests: Each rule has corresponding test class in tests/Rules/

Contributing Guidelines

  1. Code Standards: Follow PSR-4 autoloading and use ECS for code style
  2. Testing: All rules must have comprehensive tests with both positive and negative cases
  3. Documentation: Update README.md and add inline documentation for new rules
  4. Performance: Ensure rules execute efficiently within PHPStan's analysis pipeline

πŸ› Troubleshooting

Common Issues

"Rule Not Found" Errors

Cause: Incorrect namespace or class name in phpstan.neon.

Solution: Verify the fully qualified class names and check for typos.

Rules Not Being Applied

Cause: Configuration file not included or rules not registered.

Solution: Ensure vendor/simtel/phpstan-rules/rules.neon is included in your PHPStan configuration.

Performance Issues

Cause: Rules may be analyzing too many files or performing expensive operations.

Solution: Use excludePaths to limit analysis scope or optimize rule logic.

πŸ“„ License

This project is licensed under the MIT License - see the LICENSE file for details.

🀝 Contributing

Contributions are welcome! Please feel free to submit a Pull Request.

πŸ“ž Support

If you encounter any issues or have questions, please open an issue on GitHub.

About

No description, website, or topics provided.

Resources

Stars

Watchers

Forks

Packages

No packages published

Languages