1<?php
2
3namespace Drupal\Tests\Core\Block;
4
5use Drupal\Component\Plugin\Discovery\DiscoveryInterface;
6use Drupal\Core\Block\BlockManager;
7use Drupal\Core\Block\Plugin\Block\Broken;
8use Drupal\Core\Cache\CacheBackendInterface;
9use Drupal\Core\Extension\ModuleHandlerInterface;
10use Drupal\Tests\UnitTestCase;
11use Psr\Log\LoggerInterface;
12
13/**
14 * @coversDefaultClass \Drupal\Core\Block\BlockManager
15 *
16 * @group block
17 */
18class BlockManagerTest extends UnitTestCase {
19
20  /**
21   * The block manager under test.
22   *
23   * @var \Drupal\Core\Block\BlockManager
24   */
25  protected $blockManager;
26
27  /**
28   * The logger.
29   *
30   * @var \Psr\Log\LoggerInterface
31   */
32  protected $logger;
33
34  /**
35   * {@inheritdoc}
36   */
37  protected function setUp() {
38    parent::setUp();
39
40    $cache_backend = $this->prophesize(CacheBackendInterface::class);
41    $module_handler = $this->prophesize(ModuleHandlerInterface::class);
42    $this->logger = $this->prophesize(LoggerInterface::class);
43    $this->blockManager = new BlockManager(new \ArrayObject(), $cache_backend->reveal(), $module_handler->reveal(), $this->logger->reveal());
44    $this->blockManager->setStringTranslation($this->getStringTranslationStub());
45
46    $discovery = $this->prophesize(DiscoveryInterface::class);
47    // Specify the 'broken' block, as well as 3 other blocks with admin labels
48    // that are purposefully not in alphabetical order.
49    $discovery->getDefinitions()->willReturn([
50      'broken' => [
51        'admin_label' => 'Broken/Missing',
52        'category' => 'Block',
53        'class' => Broken::class,
54        'provider' => 'core',
55      ],
56      'block1' => [
57        'admin_label' => 'Coconut',
58        'category' => 'Group 2',
59      ],
60      'block2' => [
61        'admin_label' => 'Apple',
62        'category' => 'Group 1',
63      ],
64      'block3' => [
65        'admin_label' => 'Banana',
66        'category' => 'Group 2',
67      ],
68    ]);
69    // Force the discovery object onto the block manager.
70    $property = new \ReflectionProperty(BlockManager::class, 'discovery');
71    $property->setAccessible(TRUE);
72    $property->setValue($this->blockManager, $discovery->reveal());
73  }
74
75  /**
76   * @covers ::getDefinitions
77   */
78  public function testDefinitions() {
79    $definitions = $this->blockManager->getDefinitions();
80    $this->assertSame(['broken', 'block1', 'block2', 'block3'], array_keys($definitions));
81  }
82
83  /**
84   * @covers ::getSortedDefinitions
85   */
86  public function testSortedDefinitions() {
87    $definitions = $this->blockManager->getSortedDefinitions();
88    $this->assertSame(['block2', 'block3', 'block1'], array_keys($definitions));
89  }
90
91  /**
92   * @covers ::getGroupedDefinitions
93   */
94  public function testGroupedDefinitions() {
95    $definitions = $this->blockManager->getGroupedDefinitions();
96    $this->assertSame(['Group 1', 'Group 2'], array_keys($definitions));
97    $this->assertSame(['block2'], array_keys($definitions['Group 1']));
98    $this->assertSame(['block3', 'block1'], array_keys($definitions['Group 2']));
99  }
100
101  /**
102   * @covers ::handlePluginNotFound
103   */
104  public function testHandlePluginNotFound() {
105    $this->logger->warning('The "%plugin_id" was not found', ['%plugin_id' => 'invalid'])->shouldBeCalled();
106    $plugin = $this->blockManager->createInstance('invalid');
107    $this->assertSame('broken', $plugin->getPluginId());
108  }
109
110}
111