elie29/zend-phpdi-config

PSR-11 PHP-DI 自动注入容器配置器,适用于 Laminas、Mezzio、ZF2、ZF3 和 Zend Expressive 应用程序

v9.0.1 2023-03-28 13:51 UTC

README

Build Status Coverage Status

简介

zend-phpdi-config 通过服务管理器配置,作为 PSR-11 兼容的 PHP-DI 容器配置的桥梁。从 v6.0.0 版本开始,它可以与 LaminasMezzio 一起使用

此库使用自动注入技术、缓存编译和缓存定义,这些定义均来自 PHP-DI

配置

服务管理器配置

要获取一个配置好的 PSR-11 PHP-DI 容器,请执行以下操作

<?php

use Elie\PHPDI\Config\Config;
use Elie\PHPDI\Config\ContainerFactory;

$factory = new ContainerFactory();

$container = $factory(
    new Config([
        'dependencies' => [
            'services'   => [],
            'invokables' => [],
            'autowires'  => [], // A new key added to support PHP-DI autowire technique
            'factories'  => [],
            'aliases'    => [],
            'delegators' => [],
        ],
        // ... other configuration

        // Enable compilation
        Config::DI_CACHE_PATH => __DIR__, // Folder path

        // Write proxies to file : cf. https://php-di.org/doc/lazy-injection.html
        Config::DI_PROXY_PATH => __DIR__, // Folder path

        // Disable autowire (enabled by default)
        Config::USE_AUTOWIRE => false

        // Enable cache
        Config::ENABLE_CACHE_DEFINITION => false, // boolean, true if APCu is activated
    ])
);

dependencies 子关联数组可以包含以下键

  • services:一个关联数组,将键映射到特定的服务实例或服务名称。
  • invokables:一个关联数组,将键映射到无构造函数的服务;即对于不需要构造函数参数的服务。键和服务名称通常相同;如果不相同,则键被视为别名。它也可以是一组服务。
  • autowires:一组服务 带或不带构造函数;PHP-DI 提供了一种自动注入技术,它将扫描代码并查看构造函数中需要的参数。任何需要的别名都应该在别名配置中创建。
  • factories:一个关联数组,将服务名称映射到工厂类名称,或任何可调用对象。工厂类必须可以在没有参数的情况下实例化,并且一旦实例化后必须可调用(即实现 __invoke() 方法)。
  • aliases:一个关联数组,将别名映射到服务名称(或另一个别名)。
  • delegators:一个关联数组,将服务名称映射到委托工厂键的列表,有关更多详细信息,请参阅 Expressive 委托文档

注意:整个配置(除非 dependencies)都合并到 $container 中的 config 键中

$config = $container->get('config');

CLI 命令添加新的自动注入条目

Configuration image

cli 命令 add-autowires-entry 如果不存在则创建配置文件,否则将条目添加到自动注入键中。

向 config.php 添加 ConsoleHelper 的示例

./vendor/bin/add-autowires-entry config.php "Laminas\\Stdlib\\ConsoleHelper"
[DONE] Changes written to config.php

与 Expressive 一起使用

config/container.php 的内容替换为以下内容

<?php

declare(strict_types = 1);

use Elie\PHPDI\Config\Config;
use Elie\PHPDI\Config\ContainerFactory;

// Protect variables from global scope
return call_user_func(function () {

    $config = require __DIR__ . '/config.php';

    $factory = new ContainerFactory();

    // Container
    return $factory(new Config($config));
});

配置提供者类的示例

<?php

class ConfigProvider
{

    /**
     * Returns the configuration array
     */
    public function __invoke(): array
    {
        return [
            'dependencies' => $this->getDependencies()
        ];
    }

    /**
     * Returns the container dependencies
     */
    public function getDependencies(): array
    {
        return [
            'autowires' => [
                UserManager::class
            ]
        ];
    }
}

用户管理器依赖于 Mailer,如下所示

class UserManager
{
    private $mailer;

    public function __construct(Mailer $mailer)
    {
        $this->mailer = $mailer;
    }

    public function register($email, $password)
    {
        $this->mailer->mail($email, 'Hello and welcome!');
    }
}

class Mailer
{
    public function mail($recipient, $content)
    {
    }
}

切换回另一个容器

切换回另一个容器非常简单

  1. 使用 __invoke 函数创建您的工厂
  2. 将 ConfigProvider 中的 autowires 键替换为 factories 键,然后为每个类名称附加其对应的工厂。

PSR 11 和 Interop\Container\ContainerInterface

V4.x 也支持 Interop\Container\ContainerInterface

迁移指南