VOOZH about

URL: https://deepwiki.com/MahoCommerce/maho-phpstan-plugin/3.1-plugin-configuration-system

⇱ Plugin Configuration System | MahoCommerce/maho-phpstan-plugin | DeepWiki


Loading...
Menu

Plugin Configuration System

This document explains how the maho-phpstan-plugin configures itself through NEON configuration files and integrates with PHPStan's extension discovery mechanism. It covers the structure of extension.neon, the parameter schema, service definitions, and the dependency injection pattern used throughout the plugin.

For information about user-facing configuration options and how to customize the plugin's behavior, see Configuration. For details on how services integrate with PHPStan through specific extension points, see PHPStan Extension Points.

Configuration File Discovery

PHPStan discovers the plugin automatically through the Composer package metadata. The discovery process follows a two-step mechanism defined by PHPStan's extension system.


The package is marked with type: "phpstan-extension" in composer.json4 which signals to PHPStan that this package provides extensions. The extra.phpstan.includes section in composer.json24-28 specifies the configuration file to load:


When PHPStan initializes, it automatically discovers and loads extension.neon, making all defined services and parameters available to the analysis process.

Sources: composer.json1-31 extension.neon1-71

Configuration File Structure

The extension.neon file is organized into three main sections: parameters schema, parameters, and services.


Sources: extension.neon1-71

Parameter Schema and Definitions

The plugin defines four parameters that control its behavior. Each parameter has a schema definition that PHPStan uses for validation.

Parameter Schema

The parametersSchema section in extension.neon1-4 defines type constraints for each parameter:

ParameterSchemaPurpose
magentoRootPathschema(string(), nullable())Deprecated parameter for Magento root path
enforceMagicMethodDocBlockbool()Controls whether magic methods require docblocks
useLocalXmlbool()Controls whether to use local.xml for configuration

Parameter Values

The parameters section in extension.neon5-11 provides default values:


Users can override these defaults in their project's phpstan.neon file. The scanDirectories parameter is automatically used by PHPStan to locate mock framework classes needed for type resolution.

Sources: extension.neon1-11

Service Definition Pattern

All services follow a consistent definition pattern using NEON syntax. The services section in extension.neon13-71 defines seven service instances that implement the plugin's functionality.

Service Definition Syntax

Services are defined using one of two syntaxes:

  1. Named service (for shared dependencies):

  1. Anonymous service (for multiple instances):

Named Service: MageCoreConfig

The mageCoreConfig service is defined in extension.neon14-17 as a named service because it is referenced by multiple other services:


This service receives the useLocalXml parameter via constructor injection. The %parameterName% syntax retrieves the parameter value from the parameters section.

Sources: extension.neon14-17

Anonymous Services: MageTypeExtension

Four instances of MageTypeExtension are defined in extension.neon19-47 each handling a different class context:


Each instance receives:

  • mageCoreConfig: Injected via @mageCoreConfig reference syntax
  • className: A literal string value identifying which class context to handle

The @serviceName syntax creates a reference to the named service, implementing dependency injection.

Sources: extension.neon19-47

Additional Services

Three additional services complete the configuration:

ServiceLinesPurposeConstructor Arguments
MageInvalidTypeRuleextension.neon49-55Validates resolved typesmageCoreConfig: @mageCoreConfig
VarienObjectReflectionExtensionextension.neon57-63Handles magic methodsenforceDocBlock: %enforceMagicMethodDocBlock%
BindThisScopeResolverExtensionextension.neon65-70Handles template scope(no arguments)

Sources: extension.neon49-70

Dependency Injection Flow

The configuration implements a dependency injection pattern where parameters flow from definition to service constructors.


This pattern creates a clear dependency graph:

  1. Parameters are defined with default values
  2. Parameters are injected into service constructors using %parameterName% syntax
  3. Services are injected into other services using @serviceName syntax
  4. The dependency injection container (provided by PHPStan) instantiates services in dependency order

Sources: extension.neon5-71

Service Tags and Registration

Each service includes a tags section that registers it with specific PHPStan extension points. Tags are the mechanism through which PHPStan discovers and invokes plugin functionality.

Tag Types Used

The plugin uses five different PHPStan extension tags:

TagService CountPurpose
phpstan.broker.dynamicStaticMethodReturnTypeExtension1Static method return type inference (e.g., Mage::getModel())
phpstan.broker.dynamicMethodReturnTypeExtension3Instance method return type inference
phpstan.rules.rule1Custom validation rules
phpstan.broker.methodsClassReflectionExtension1Magic method reflection
phpstan.parser.richParserNodeVisitor1AST transformation during parsing
phpstan.phpDoc.typeNodeResolverExtension1Custom type annotation resolution

The tag structure in NEON:


PHPStan scans all loaded configuration files for services with these tags and invokes them at appropriate points during analysis. For details on what each extension point does, see PHPStan Extension Points.

Sources: extension.neon25-70

Parameter Usage Patterns

The three active parameters serve distinct purposes in the plugin's behavior:

useLocalXml Parameter

Defined in extension.neon4 and extension.neon8 this boolean parameter controls whether MageCoreConfig attempts to load configuration from a local.xml file in the Magento root directory.


Flow:

  1. Default value is false in extension.neon8
  2. User can override in their phpstan.neon
  3. Value is injected into MageCoreConfig constructor in extension.neon17
  4. MageCoreConfig uses it to determine configuration loading strategy

enforceMagicMethodDocBlock Parameter

Defined in extension.neon3 and extension.neon7 this boolean controls whether VarienObjectReflectionExtension requires PHPDoc blocks for magic methods.

Flow:

  1. Default value is false in extension.neon7
  2. Value is injected into VarienObjectReflectionExtension constructor in extension.neon61
  3. When false: Magic methods like getFoo() are always recognized on Varien_Object descendants
  4. When true: Magic methods require explicit @method annotations in docblocks

scanDirectories Parameter

Defined in extension.neon9-11 this array parameter lists directories containing mock framework classes:


PHPStan automatically scans these directories to load class definitions needed for type resolution. These paths are relative to the plugin's installation directory.

Sources: extension.neon1-11 extension.neon14-70

Configuration Override Mechanism

Users can override plugin parameters in their project's phpstan.neon file. PHPStan merges configuration files in a specific order, with user configurations taking precedence.

Override Example

Project's phpstan.neon:


Merge order:

  1. PHPStan loads plugin's extension.neon (via auto-discovery)
  2. PHPStan loads project's phpstan.neon
  3. Parameters from step 2 override parameters from step 1
  4. Services use the merged parameter values

The magentoRootPath parameter is marked as deprecated in extension.neon6 and defaults to null. It is no longer used by any services but remains in the schema for backward compatibility.

Sources: extension.neon1-11 composer.json24-28

Service Instantiation Order

PHPStan's dependency injection container instantiates services in dependency order:


  1. Parameter Resolution: PHPStan resolves all parameters, merging defaults with user overrides
  2. Named Services: mageCoreConfig is instantiated first because other services depend on it
  3. Dependent Services: All other services are instantiated, receiving injected dependencies
  4. Registration: Each service is registered with PHPStan based on its tags

This order ensures that when a service constructor is called, all its dependencies are already available.

Sources: extension.neon13-71

Summary

The plugin configuration system provides a clean separation between:

  • Schema: Type definitions in parametersSchema
  • Defaults: Default values in parameters
  • Behavior: Service implementations in services
  • Integration: PHPStan tags for extension point registration

This structure allows users to customize plugin behavior without modifying plugin code, while maintaining type safety through parameter schema validation. The dependency injection pattern ensures services are instantiated with correct dependencies in the proper order.

Sources: extension.neon1-71 composer.json1-31