【问题标题】:Behat 3 - how to retrieve custom extension in contextBehat 3 - 如何在上下文中检索自定义扩展
【发布时间】:2014-12-01 19:28:02
【问题描述】:

我需要添加并稍后从上下文中从 behat.yml 文件中检索额外的选项/配置。

Behat 不允许我在 behat.yml 文件中添加一些随机参数,因此我创建了新的自定义扩展。这个扩展允许我传递特定的配置值

extensions:
    App\Behat\DevToolsExtension:
        api_url: "https://api.example.com"

所以现在 behat 不会抱怨 behat.yml 文件中的新配置。

现在我被困住了。如何在运行时从我的扩展中检索此配置?

我在公共函数 load(ContainerBuilder $container, array $config) 方法中的扩展中设置现有参数,如下所示:

$container->setParameter($configKey . $key, $config[$key]);

同样,有没有办法在 Context 中检索这个 ContainerBuilder 对象或 DevToolsExtension 对象?

编辑

解决方案是创建服务容器并将行为 ContainerBuilder 传递给它,如下所示:

class AppExtension implements ExtensionInterface
{
    // ...
    public function load(ContainerBuilder $container, array $config)
    {
        $configKey = $this->getConfigKey() . '.';

        foreach ($this->keys as $key) {
            $keyValue = $configKey . $key;
            $container->setParameter($keyValue, $config[$key]);
        }

        $this->getServiceLocator()->setBehatContainer($container);
    }

然后使用服务定位器检索配置参数

$value = $this->getBehatContainer()->getParameter($key);

【问题讨论】:

    标签: php symfony behat


    【解决方案1】:

    我遇到了这个问题并为项目解决了这个问题:CLIPBOARD

    当然,正在开发 ~v3.0 可能正在开发 v2.5。

    在您的 Exntesion 类中,创建扩展后,您需要初始化系统中的任何上下文的初始化程序。为此,您需要使用 ContextExtension::INITIALIZER_TAG 在容器中创建服务,并取决于配置。我有

    $container->setParameter('dev_tools_extension.parameters', $config); 
    

    然后

    private function loadContextInitializer(ContainerBuilder $container)
    {
        $definition = new Definition(
            'App\Behat\DevToolsExtension\Context\Initializer\DevToolsExtensionInitializer', array(
                '%dev_tools_extension.parameters%'
            )
        );
        $definition->addTag(ContextExtension::INITIALIZER_TAG, array('priority' => 0));
        $container->setDefinition('dev_tools_extension.context_initializer', $definition);
    }
    

    Initializer 使用被调用的 Context 实现 Behat\Behat\Context\Initializer\ContextInitializer。接下来,您创建(例如接口)并在上下文中调用函数。我有:

        /**
     * Initializes provided context.
     *
     * @param Context $context
     */
    public function initializeContext(Context $context)
    {
        if (!$context instanceof ClipboardContextInterface) {
            return;
        }
        /** @var ClipboardContextInterface $context */
    
        $context->setClipboard($this->clipboard);
    }
    

    【讨论】:

      【解决方案2】:

      这是个好问题。基本上下文没有回到顶部的引用,因此您无法从那里真正找出加载了哪些扩展。扩展被初始化并连接到内部事件系统。当上下文被初始化时,它们会收到通知并可以将必要的参数传递给它们。知道了这一点,您就可以创建一个适当的扩展程序,该扩展程序连接到 Behat 事件系统并将配置传递到您的上下文中——这就是这样做的方法。

      Mink 扩展就是一个很好的例子,你可能找不到任何文档,但是你可以在你的 (Mink) 上下文之一中创建一个构造函数,在那里添加一个断点并跟踪跟踪以找出如何整个事情都有效。

      但是……在大多数情况下,这太过分了。可以(并且应该)使用可以从上下文加载的外部配置文件或通过将参数传递给上下文(与您现在使用扩展程序相同的方式)来实现相同的目标。如果您有许多需要该配置的上下文,则最后一个选项可能效果不佳。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2020-09-28
        • 2019-03-13
        • 1970-01-01
        相关资源
        最近更新 更多