/mxdiModule

Configure dependency injection in Zend Framework 2 using annotations/yaml/xml

Primary LanguagePHPOtherNOASSERTION

mxdiModule

Build Status Build Status Scrutinizer Code Quality Code Coverage Dependency Status Latest Stable Version Total Downloads License

Configure dependency injection in Zend Framework 2 using annotations/yaml/xml.

Idea based on the JMSDiExtraBundle for the Symfony2 project.

  1. Installation
  2. Changing mapping driver
  3. Important notes
  4. Caching
  5. Debugging
  6. Console commands

Installation

  1. Install with Composer: composer require mikemix/mxdi-module:~3.0 (rules of semantic versioning apply).

  2. Enable the module via ZF2 config in appliation.config.php under modules key:

    return [
        //
        //
        'modules' => [
            'mxdiModule',
            // other modules
        ],
        //
        //
    ];

    This will enable the module and register the Abstract Factory in the ZF2's Service Manager.

  3. Copy the global config file cp vendor/mikemix/mxdi-module/resources/mxdimodule.global.php.dist config/autoload/mxdimodule.global.php if you want to override the default mapping driver.

  4. Copy the local config file cp vendor/mikemix/mxdi-module/resources/mxdimodule.local.php.dist config/autoload/mxdimodule.local.php if you want to override other settings, like caching etc.

Changing mapping driver

The default mapping driver is AnnotationExtractor as source of mapping information for the module. You can change it however to other. Available extractors are:

  • AnnotationExtractor (default) which uses annotations inside your classes. See the Annotation docs for annotations reference and examples.
  • YamlExtractor which uses a yml file. See the YAML docs for examples.
  • XmlExtractor which uses a xml file. See the XML docs for examples.

There's no difference between choosing annotation driver or YAML or XML driver, because the mapping information in the end is converted to plain php and stored inside the cache.

Important notes

Remember, the requested service must not be registered in the Service Manager. If you register it as factory or invokable, it won't go through the Abstract Factory and won't get injected. By the way, this allows you to create custom factory for the service in mention.

To speed up locate time you can request the service through the DiFactory invokable, for example:

/** @var \mxdiModule\Service\DiFactory @factory */ 
$factory = $this->getServiceLocator()->get(\mxdiModule\Service\DiFactory::class);

/** @var \YourApplication\Service\SomeService $service */
$service = $factory(\YourApplication\Service\SomeService::class);

Caching

Parsing mapping sources is very heavy. You should enable the cache on production servers.

You can set up caching easily with any custom or pre-existing ZF2 cache adapter. In the config/autoload/mxdimodule.local.php override the cache_adapter and cache_options keys for your needs. You can find more information about available out-of-the-box adapters at the ZF2 docs site.

Debugging

If you get ServiceNotCreated exception most probably one of your injections is not registered in the ZF2's Service Manager. In the exception stack you will see some more detailed information. For instance look for CannotGetValue exceptions.

Console commands

  • Clear generated proxy files: php public/index.php mxdimodule proxy clear

    Clear all generated proxy files from the proxy dir

  • Clear annotation parsing cache: php public/index.php mxdimodule cache clear [<fqcn>]

    Flush whole cache or only of a given service