30820846cd534be9bc1b622f4a6a6f78a60990aa
[yaffs-website] / web / core / modules / layout_builder / tests / src / Unit / BlockComponentRenderArrayTest.php
1 <?php
2
3 namespace Drupal\Tests\layout_builder\Unit;
4
5 use Drupal\block_content\Access\RefinableDependentAccessInterface;
6 use Drupal\Component\Plugin\Context\ContextInterface;
7 use Drupal\Core\Access\AccessResult;
8 use Drupal\Core\Block\BlockManagerInterface;
9 use Drupal\Core\Block\BlockPluginInterface;
10 use Drupal\Core\Cache\Cache;
11 use Drupal\Core\DependencyInjection\ContainerBuilder;
12 use Drupal\Core\Entity\EntityInterface;
13 use Drupal\Core\Plugin\Context\ContextHandlerInterface;
14 use Drupal\Core\Session\AccountInterface;
15 use Drupal\layout_builder\Access\LayoutPreviewAccessAllowed;
16 use Drupal\layout_builder\Event\SectionComponentBuildRenderArrayEvent;
17 use Drupal\layout_builder\EventSubscriber\BlockComponentRenderArray;
18 use Drupal\layout_builder\SectionComponent;
19 use Drupal\Tests\UnitTestCase;
20
21 /**
22  * @coversDefaultClass \Drupal\layout_builder\EventSubscriber\BlockComponentRenderArray
23  * @group layout_builder
24  */
25 class BlockComponentRenderArrayTest extends UnitTestCase {
26
27   /**
28    * The current user.
29    *
30    * @var \Drupal\Core\Session\AccountInterface
31    */
32   protected $account;
33
34   /**
35    * The block plugin manager.
36    *
37    * @var \Drupal\Core\Block\BlockManagerInterface
38    */
39   protected $blockManager;
40
41   /**
42    * Dataprovider for test functions that should test block types.
43    */
44   public function providerBlockTypes() {
45     return [
46       [TRUE],
47       [FALSE],
48     ];
49   }
50
51   /**
52    * {@inheritdoc}
53    */
54   protected function setUp() {
55     parent::setUp();
56
57     $this->blockManager = $this->prophesize(BlockManagerInterface::class);
58     $this->account = $this->prophesize(AccountInterface::class);
59
60     $container = new ContainerBuilder();
61     $container->set('plugin.manager.block', $this->blockManager->reveal());
62     $container->set('context.handler', $this->prophesize(ContextHandlerInterface::class));
63     \Drupal::setContainer($container);
64   }
65
66   /**
67    * @covers ::onBuildRender
68    *
69    * @dataProvider providerBlockTypes
70    */
71   public function testOnBuildRender($refinable_dependent_access) {
72     $contexts = [];
73     if ($refinable_dependent_access) {
74       $block = $this->prophesize(TestBlockPluginWithRefinableDependentAccessInterface::class);
75       $layout_entity = $this->prophesize(EntityInterface::class);
76       $layout_entity = $layout_entity->reveal();
77       $context = $this->prophesize(ContextInterface::class);
78       $context->getContextValue()->willReturn($layout_entity);
79       $contexts['layout_builder.entity'] = $context->reveal();
80
81       $block->setAccessDependency($layout_entity)->shouldBeCalled();
82     }
83     else {
84       $block = $this->prophesize(BlockPluginInterface::class);
85     }
86     $access_result = AccessResult::allowed();
87     $block->access($this->account->reveal(), TRUE)->willReturn($access_result)->shouldBeCalled();
88     $block->getCacheContexts()->willReturn([]);
89     $block->getCacheTags()->willReturn(['test']);
90     $block->getCacheMaxAge()->willReturn(Cache::PERMANENT);
91     $block->getConfiguration()->willReturn([]);
92     $block->getPluginId()->willReturn('block_plugin_id');
93     $block->getBaseId()->willReturn('block_plugin_id');
94     $block->getDerivativeId()->willReturn(NULL);
95
96     $block_content = ['#markup' => 'The block content.'];
97     $block->build()->willReturn($block_content);
98     $this->blockManager->createInstance('some_block_id', ['id' => 'some_block_id'])->willReturn($block->reveal());
99
100     $component = new SectionComponent('some-uuid', 'some-region', ['id' => 'some_block_id']);
101     $in_preview = FALSE;
102     $event = new SectionComponentBuildRenderArrayEvent($component, $contexts, $in_preview);
103
104     $subscriber = new BlockComponentRenderArray($this->account->reveal());
105
106     $expected_build = [
107       '#theme' => 'block',
108       '#weight' => 0,
109       '#configuration' => [],
110       '#plugin_id' => 'block_plugin_id',
111       '#base_plugin_id' => 'block_plugin_id',
112       '#derivative_plugin_id' => NULL,
113       'content' => $block_content,
114     ];
115
116     $expected_cache = $expected_build + [
117       '#cache' => [
118         'contexts' => [],
119         'tags' => ['test'],
120         'max-age' => -1,
121       ],
122     ];
123
124     $subscriber->onBuildRender($event);
125     $result = $event->getBuild();
126     $this->assertEquals($expected_build, $result);
127     $event->getCacheableMetadata()->applyTo($result);
128     $this->assertEquals($expected_cache, $result);
129   }
130
131   /**
132    * @covers ::onBuildRender
133    *
134    * @dataProvider providerBlockTypes
135    */
136   public function testOnBuildRenderDenied($refinable_dependent_access) {
137     $contexts = [];
138     if ($refinable_dependent_access) {
139       $block = $this->prophesize(TestBlockPluginWithRefinableDependentAccessInterface::class);
140
141       $layout_entity = $this->prophesize(EntityInterface::class);
142       $layout_entity = $layout_entity->reveal();
143       $context = $this->prophesize(ContextInterface::class);
144       $context->getContextValue()->willReturn($layout_entity);
145       $contexts['layout_builder.entity'] = $context->reveal();
146
147       $block->setAccessDependency($layout_entity)->shouldBeCalled();
148     }
149     else {
150       $block = $this->prophesize(BlockPluginInterface::class);
151     }
152
153     $access_result = AccessResult::forbidden();
154     $block->access($this->account->reveal(), TRUE)->willReturn($access_result)->shouldBeCalled();
155     $block->getCacheContexts()->shouldNotBeCalled();
156     $block->getCacheTags()->shouldNotBeCalled();
157     $block->getCacheMaxAge()->shouldNotBeCalled();
158     $block->getConfiguration()->shouldNotBeCalled();
159     $block->getPluginId()->shouldNotBeCalled();
160     $block->getBaseId()->shouldNotBeCalled();
161     $block->getDerivativeId()->shouldNotBeCalled();
162
163     $block_content = ['#markup' => 'The block content.'];
164     $block->build()->willReturn($block_content);
165     $this->blockManager->createInstance('some_block_id', ['id' => 'some_block_id'])->willReturn($block->reveal());
166
167     $component = new SectionComponent('some-uuid', 'some-region', ['id' => 'some_block_id']);
168     $in_preview = FALSE;
169     $event = new SectionComponentBuildRenderArrayEvent($component, $contexts, $in_preview);
170
171     $subscriber = new BlockComponentRenderArray($this->account->reveal());
172
173     $expected_build = [];
174     $expected_cache = [
175       '#cache' => [
176         'contexts' => [],
177         'tags' => [],
178         'max-age' => -1,
179       ],
180     ];
181
182     $subscriber->onBuildRender($event);
183     $result = $event->getBuild();
184     $this->assertEquals($expected_build, $result);
185     $event->getCacheableMetadata()->applyTo($result);
186     $this->assertEquals($expected_cache, $result);
187   }
188
189   /**
190    * @covers ::onBuildRender
191    *
192    * @dataProvider providerBlockTypes
193    */
194   public function testOnBuildRenderInPreview($refinable_dependent_access) {
195     $contexts = [];
196     if ($refinable_dependent_access) {
197       $block = $this->prophesize(TestBlockPluginWithRefinableDependentAccessInterface::class);
198       $block->setAccessDependency(new LayoutPreviewAccessAllowed())->shouldBeCalled();
199
200       $layout_entity = $this->prophesize(EntityInterface::class);
201       $layout_entity = $layout_entity->reveal();
202       $layout_entity->in_preview = TRUE;
203       $context = $this->prophesize(ContextInterface::class);
204       $context->getContextValue()->willReturn($layout_entity);
205       $contexts['layout_builder.entity'] = $context->reveal();
206     }
207     else {
208       $block = $this->prophesize(BlockPluginInterface::class);
209     }
210
211     $block->access($this->account->reveal(), TRUE)->shouldNotBeCalled();
212     $block->getCacheContexts()->willReturn([]);
213     $block->getCacheTags()->willReturn(['test']);
214     $block->getCacheMaxAge()->willReturn(Cache::PERMANENT);
215     $block->getConfiguration()->willReturn([]);
216     $block->getPluginId()->willReturn('block_plugin_id');
217     $block->getBaseId()->willReturn('block_plugin_id');
218     $block->getDerivativeId()->willReturn(NULL);
219
220     $block_content = ['#markup' => 'The block content.'];
221     $block->build()->willReturn($block_content);
222     $this->blockManager->createInstance('some_block_id', ['id' => 'some_block_id'])->willReturn($block->reveal());
223
224     $component = new SectionComponent('some-uuid', 'some-region', ['id' => 'some_block_id']);
225     $in_preview = TRUE;
226     $event = new SectionComponentBuildRenderArrayEvent($component, $contexts, $in_preview);
227
228     $subscriber = new BlockComponentRenderArray($this->account->reveal());
229
230     $expected_build = [
231       '#theme' => 'block',
232       '#weight' => 0,
233       '#configuration' => [],
234       '#plugin_id' => 'block_plugin_id',
235       '#base_plugin_id' => 'block_plugin_id',
236       '#derivative_plugin_id' => NULL,
237       'content' => $block_content,
238     ];
239
240     $expected_cache = $expected_build + [
241       '#cache' => [
242         'contexts' => [],
243         'tags' => ['test'],
244         'max-age' => 0,
245       ],
246     ];
247
248     $subscriber->onBuildRender($event);
249     $result = $event->getBuild();
250     $this->assertEquals($expected_build, $result);
251     $event->getCacheableMetadata()->applyTo($result);
252     $this->assertEquals($expected_cache, $result);
253   }
254
255   /**
256    * @covers ::onBuildRender
257    */
258   public function testOnBuildRenderNoBlock() {
259     $this->blockManager->createInstance('some_block_id', ['id' => 'some_block_id'])->willReturn(NULL);
260
261     $component = new SectionComponent('some-uuid', 'some-region', ['id' => 'some_block_id']);
262     $contexts = [];
263     $in_preview = FALSE;
264     $event = new SectionComponentBuildRenderArrayEvent($component, $contexts, $in_preview);
265
266     $subscriber = new BlockComponentRenderArray($this->account->reveal());
267
268     $expected_build = [];
269     $expected_cache = [
270       '#cache' => [
271         'contexts' => [],
272         'tags' => [],
273         'max-age' => -1,
274       ],
275     ];
276
277     $subscriber->onBuildRender($event);
278     $result = $event->getBuild();
279     $this->assertEquals($expected_build, $result);
280     $event->getCacheableMetadata()->applyTo($result);
281     $this->assertEquals($expected_cache, $result);
282   }
283
284 }
285
286 /**
287  * Test interface for dependent access block plugins.
288  */
289 interface TestBlockPluginWithRefinableDependentAccessInterface extends BlockPluginInterface, RefinableDependentAccessInterface {
290
291 }