Внедрение конфигурации в макет объекта конфигурации


Я пытаюсь настроить модульный тест на основе UnitTestCase в Drupal 8, который использует некоторые переменные конфигурации. К сожалению, я не смог найти способ вставить эти переменные конфигурации в систему при настройке (поискал документацию Drupal и любой пример модульного тестирования Drupal, включающий конфигурацию), поэтому тестируемая функция всегда работает с нулевой конфигурацией и завершается неудачно. Я пытаюсь тестировать отдельные функции изолированно, поэтому тест браузера на самом деле не подходит для этот.

Я упростил проблему до минимального кода, необходимого для объяснения/воспроизведения проблемы. Вот три компонента. Где в макете/настройке я должен вставить array('bucketName' => 'test_bucket') и другие свойства, чтобы их можно было прочитать из тестируемой функции?

Функция:

public function example() {
    return \Drupal::config('my_module.job')->get('my_module.bucketName');
}

Тестовая функция:

public function testExample() {
    $myModuleHelper = new MyModuleHelper();
        $expected_config = array(
            'bucketName' => 'test_bucket',
        );

    $this->assertEquals($expected_config, $myModuleHelper->example());
}

Настройка теста:

public function setUp() {
    $this->config = $this->getMockBuilder('\Drupal\Core\Config\ImmutableConfig')
        ->disableOriginalConstructor()
        ->getMock();

    $this->configFactory = $this->getMockBuilder('\Drupal\Core\Config\ConfigFactory')
        ->disableOriginalConstructor()
        ->getMock();
    $this->configFactory->expects($this->any())
        ->method('get')
        ->with('my_module.job')
        ->willReturn($this->config);

    $this->container = new ContainerBuilder();
    $this->container->set('config.factory', $this->configFactory);
    \Drupal::setContainer($this->container);
}

Тестовый ответ:

Значение Null не соответствует ожидаемому типу "массив".

 6
Author: Ynhockey, 2017-11-23

2 answers

Ваш макет объекта конфигурации также должен иметь метод ::get и возвращать соответствующее значение с помощью вашего массива. Основной класс UnitTestCase предоставляет ::getConfigFactoryStub(array $configs), который выполняет все это автоматически.

В вашей настройке создайте фабрику конфигурации следующим образом:

$this->configFactory = $this->getConfigFactoryStub([
  'mymodule.job' => ['bucketName' => 'test_bucket'],
]);

К сожалению, издевательская конфигурация не совсем работает как реальный объект конфигурации; а именно, она не принимает пунктирные ключи, а только ключи верхнего уровня. Следующее не будет работать:

$this->configFactory = $this->getConfigFactoryStub([
  'mymodule.settings' => [
    'key' => [
      'subkey' => [
        'subsubkey' => 'value',
      ],
    ],
  ],
]);
$this->container = new ContainerBuilder();
$this->container->set('config.factory', $this->configFactory);
\Drupal::setContainer($this->container);

\Drupal::config('mymodule.settings')->get('key.subkey.subsubkey');

Это сообщение об ошибке показывает обходной путь: https://www.drupal.org/node/2862248

 4
Author: Christoph Burschka, 2017-11-23 16:41:54

Если вы используете KernelTestBase ( для "функциональных" тестов, которые выполняются на загрузочном Drupal и могут использовать службы), затем см. этот ответ для получения подробной информации о том, как использовать KernelTestBase::config() для установки значений конфигурации, доступных через внедренную службу config.factory.

Обратите внимание, что это не будет работать для тестов, расширяющих UnitTestCase, так как Drupal не полностью настроен.

 1
Author: Adam Franco, 2019-02-27 21:13:18