divineniiquaye/php-invoker

一个库,以通用和可扩展的方式提供调用具有命名参数的可调用项的能力。

v0.9.12 2021-03-14 20:42 UTC

This package is auto-updated.

Last update: 2024-09-06 10:24:05 UTC


README

Latest Version Software License Workflow Status Code Maintainability Coverage Status Quality Score Sponsor development of this project

divineniiquaye/php-invoker 是一个 PHP 库,允许以通用和可扩展的方式调用具有命名参数的可调用项,基于由 PHP-DI Invoker 创建的引用实现,由 Matthieu Napoli 构建。此库提供了清晰的扩展点,以便框架/项目实现他们想要的任何类型的依赖注入支持,但不仅限于依赖注入。再次强调,任何符合 PSR-11 的容器都可以提供。

📦 安装与基本用法

此项目需要 PHP 7.1 或更高版本。推荐的安装方式是通过 Composer。只需运行

$ composer require divineniiquaye/php-invoker

假设你在做项目,并想在可调用项中调用一些命名参数,但这些参数的顺序可以是任意的,但应按名称或实例匹配。那么我们就需要一个过度设计的 call_user_func()

简而言之,这个库旨在成为一个调用带命名参数的函数的基础构建块,并支持依赖注入。

使用 DivineNii\Invoker\Invoker 类的 call 方法

$invoker = new DivineNii\Invoker\Invoker;

$invoker->call(function () {
    echo 'Hello world!';
});

// Simple parameter array
$invoker->call(function ($name) {
    echo 'Hello ' . $name;
}, ['John']);

// Named parameters
$invoker->call(function ($name) {
    echo 'Hello ' . $name;
}, [
    'name' => 'John'
]);

// Typehint parameters
$invoker->call(function (string $name) {
    echo 'Hello ' . $name;
}, [
    'name' => 'John'
]);

// Use the default value
$invoker->call(function ($name = 'world') {
    echo 'Hello ' . $name;
});

// Invoke any PHP callable
$invoker->call(['MyClass', 'myStaticMethod']);

// Using Class::method syntax
$invoker->call('MyClass::myStaticMethod');

// Using ":" pattern syntax
$invoker->call('MyClass:myMethod');

// Using "@" pattern syntax
$invoker->call('MyClass@myMethod');

使用 DivineNii\Invoker\ArgumentResolver 类在 DivineNii\Invoker\Invoker 类中

扩展 DivineNii\Invoker\Invoker 的行为很容易,只需将可调用项添加到 ArgumentResolver 类中即可

use ReflectionParameter;
use DivineNii\Invoker\Interfaces\ArgumentValueResolverInterface;

class MyParameterValueResolver implements ArgumentValueResolverInterface
{
    /**
     * {@inheritdoc}
     */
    public function resolve(ReflectionParameter $parameter, array $providedParameters)
    {
        //....
    }
}
  • $providedParameters 包含用户在调用 $invoker->call($callable, $parameters) 时提供的参数

DivineNii\Invoker\Invoker 可以连接多个参数解析器以混合行为,例如,您可以混合“命名参数”支持与“依赖注入”支持。

以下是一个实现示例,用于创建由类型提示指定的类的新实例的简单依赖注入

use {ReflectionClass, ReflectionException};
use DivineNii\Invoker\Interfaces\ArgumentValueResolverInterface;

class MyParameterValueResolver implements ArgumentValueResolverInterface
{
    /**
     * {@inheritdoc}
     */
    public function resolve(ReflectionParameter $parameter, array $providedParameters)
    {
        $parameterClass = $parameter->getClass();

        if ($parameterClass instanceof ReflectionClass) {
            try {
                return $class->newInstance();
            } catch (ReflectionExcetion $e) {
                // ...
            }
        }
    }
}

要使用它

$invoker = new DivineNii\Invoker\Invoker([new MyParameterValueResolver()]);

$invoker->call(function (ArticleManager $articleManager) {
    $articleManager->publishArticle('Hello world', 'This is the article content.');
});

我们的参数解析器将创建一个 ArticleManager 的新实例。当我们要添加对许多事物的支持时,乐趣就开始了

  • 命名参数
  • 类型提示参数的依赖注入
  • ...

它甚至支持最奇怪的使用案例,例如

$parameters = [];

// First parameter will receive "Welcome"
$parameters[] = 'Welcome';

// Parameter named "content" will receive "Hello world!"
$parameters['content'] = 'Hello world!';

// $published is not defined so it will use its default value
$invoker->call(function ($title, $content, $published = true) {
    // ...
}, $parameters);

而不是每次都重新实现支持不同容器的依赖注入,此包附带两个可选解析器

  • 此解析器将通过使用类型提示搜索类名来注入容器条目

    $invoker->call(function (Psr\Logger\LoggerInterface $logger) {
        // ...
    });

    在这个例子中,它将从容器中注入 ->get('Psr\Logger\LoggerInterface'),但如果接口的实例存在于 $providedParameters 中,它也将被注入。

  • 此解析器将通过搜索参数的名称来注入容器条目

    $invoker->call(function ($twig) {
        // ...
    });

    在这个例子中,它将从容器中注入 ->get('twig') 或从 $providedParameters 中注入。

DivineNii\Invoker\Invoker 可以连接到您的 DI 容器以解析可调用项,但可以解析所有可调用项,包括可调用类或对象。

例如,对于可调用的类

class MyHandler
{
    public function __invoke()
    {
        // ...
    }
}

// By default this work
$invoker->call('MyHandler');

// If we set up the container to use
$invoker = new Invoker\Invoker([], $container);
// Now 'MyHandler' parameters is resolved using the container if any!
$invoker->call('MyHandler');

对于类方法,效果相同

class WelcomeController
{
    public function home()
    {
        // ...
    }
}

// By default this doesn't work: home() is not a static method
$invoker->call(['WelcomeController', 'home']);

// If we set up the container to use
$invoker = new Invoker\Invoker([], $container);
// Now 'WelcomeController' is resolved using the container!
$invoker->call(['WelcomeController', 'home']);
// Alternatively we can use the Class::method syntax
$invoker->call('WelcomeController::home');

📓 文档

在使用此库之前,请查看深度文档。有关高级使用、配置和定制的完整文档,请访问docs.biurad.com

⏫ 升级

有关如何升级到此库的新版本的说明,请参阅UPGRADE

🏷️ 更新日志

严格遵守SemVer。次要版本和补丁版本不应引入对代码库的破坏性更改;有关最近更改的更多信息,请参阅CHANGELOG

任何标记为@internal的类或方法都不是为了在库外使用,并且可能会随时进行破坏性更改,因此请避免使用它们。

🛠️ 维护与支持

当发布一个新的主要版本(如1.02.0等)时,上一个版本(如0.19.x)将在新版本发布后至少3个月内收到错误修复,并在之后的6个月内收到安全更新。

(此政策可能在未来发生变化,并且可能会根据具体情况做出例外。)

专业支持,包括通知新版本和安全更新,可在Biurad Commits处获得。

👷‍♀️ 贡献

要报告安全漏洞,请使用Biurad Security。我们将协调修复,并最终在此项目中提交解决方案。

欢迎对此库的贡献,特别是以下贡献:

  • 在不违反PSR-12编码标准的情况下,提高可用性或灵活性。
  • 优化性能
  • 修复与PSR-11支持和向后兼容性相关的问题。

有关详细信息,请参阅CONTRIBUTING

🧪 测试

$ composer test

这将测试divineniiquaye/php-invoker是否可在PHP 7.2版本或更高版本上运行。

👥 信用与鸣谢

🙌 赞助商

您有兴趣赞助此项目的发展吗?请与我们联系,在Patreon上支持我们,或查看https://biurad.com/sponsor上的赞助方式。

📄 许可证

divineniiquaye/php-invoker遵循BSD-3许可证。有关更多详细信息,请参阅LICENSE文件。

🏛️ 治理

此项目主要由Divine Niiquaye Ibok维护。Biurad Lap领导团队的一些成员有时会协助这些职责。

🗺️ 使用者

您可以自由使用此包,但如果它进入了您的生产环境,我们非常欢迎您发送一封电子邮件消息,提及此库。我们将在https://patreons.biurad.com上发布所有收到的请求。

查看人们用 divineniiquaye/php-invoker 做的其他酷炫事情:https://packagist.org.cn/packages/divineniiquaye/php-invoker/dependents