Skip to content

Commit ab74929

Browse files
committed
Refactor extraMetadata handling in MountedComponent and related classes
1 parent 0aaa5bf commit ab74929

File tree

4 files changed

+69
-48
lines changed

4 files changed

+69
-48
lines changed

src/LiveComponent/src/EventListener/DeferLiveComponentSubscriber.php

Lines changed: 34 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -5,62 +5,66 @@
55
namespace Symfony\UX\LiveComponent\EventListener;
66

77
use Symfony\Component\EventDispatcher\EventSubscriberInterface;
8-
use Symfony\UX\LiveComponent\Util\LiveControllerAttributesCreator;
9-
use Symfony\UX\TwigComponent\ComponentStack;
8+
use Symfony\UX\TwigComponent\Event\PostMountEvent;
109
use Symfony\UX\TwigComponent\Event\PreRenderEvent;
1110

1211
final class DeferLiveComponentSubscriber implements EventSubscriberInterface
1312
{
14-
private const PRIORITY = 16;
15-
1613
private const DEFAULT_LOADING_TAG = 'div';
1714

1815
private const DEFAULT_LOADING_TEMPLATE = null;
1916

20-
public function __construct(
21-
private ComponentStack $componentStack,
22-
private LiveControllerAttributesCreator $attributesCreator,
23-
) {
17+
public function onPostMount(PostMountEvent $event): void
18+
{
19+
$data = $event->getData();
20+
if (\array_key_exists('defer', $data)) {
21+
$event->addExtraMetadata('defer', true);
22+
unset($event->getData()['defer']);
23+
}
24+
25+
if (\array_key_exists('loading-template', $data)) {
26+
$event->addExtraMetadata('loading-template', $data['loading-template']);
27+
unset($event->getData()['loading-template']);
28+
}
29+
30+
if (\array_key_exists('loading-tag', $data)) {
31+
$event->addExtraMetadata('loading-tag', $data['loading-tag']);
32+
unset($event->getData()['loading-tag']);
33+
}
34+
35+
$event->setData($data);
2436
}
2537

2638
public function onPreRender(PreRenderEvent $event): void
2739
{
2840
$mountedComponent = $event->getMountedComponent();
29-
$inputProps = $mountedComponent->getInputProps();
30-
$isDeferred = $inputProps['defer'] ?? false;
3141

32-
if (!$isDeferred) {
42+
if (!$mountedComponent->hasExtraMetadata('defer')) {
3343
return;
3444
}
3545

36-
$metadata = $event->getMetadata();
37-
$variables = $event->getVariables();
38-
$attributesKey = $metadata->getAttributesVar();
39-
4046
$event->setTemplate('@LiveComponent/deferred.html.twig');
4147

42-
$originalAttributes = $variables[$attributesKey]->all();
43-
44-
$attributes = $originalAttributes;
45-
$attributes = array_filter(
46-
$attributes,
47-
fn ($key) => !\in_array($key, ['defer', 'loading-template', 'loading-tag'], true),
48-
\ARRAY_FILTER_USE_KEY,
49-
);
48+
$variables = $event->getVariables();
49+
$variables['loadingTemplate'] = self::DEFAULT_LOADING_TEMPLATE;
50+
$variables['loadingTag'] = self::DEFAULT_LOADING_TAG;
5051

51-
$variables[$attributesKey] = $attributes;
52-
$variables['loadingTag'] = $originalAttributes['loading-tag'] ?? self::DEFAULT_LOADING_TAG;
53-
$variables['loadingTemplate'] = $originalAttributes['loading-template'] ?? self::DEFAULT_LOADING_TEMPLATE;
52+
if ($mountedComponent->hasExtraMetadata('loading-template')) {
53+
$variables['loadingTemplate'] = $mountedComponent->getExtraMetadata('loading-template');
54+
}
5455

55-
$mountedComponent->setAttributes(
56-
$mountedComponent->getAttributes()->without('defer', 'loading-template', 'loading-tag'),
57-
);
56+
if ($mountedComponent->hasExtraMetadata('loading-tag')) {
57+
$variables['loadingTag'] = $mountedComponent->getExtraMetadata('loading-tag');
58+
}
5859

5960
$event->setVariables($variables);
6061
}
6162

6263
public static function getSubscribedEvents(): array
6364
{
64-
return [PreRenderEvent::class => ['onPreRender', self::PRIORITY]];
65+
return [
66+
PostMountEvent::class => ['onPostMount'],
67+
PreRenderEvent::class => ['onPreRender'],
68+
];
6569
}
6670
}

src/TwigComponent/src/ComponentFactory.php

Lines changed: 13 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -88,7 +88,9 @@ public function mountFromObject(object $component, array $data, ComponentMetadat
8888
}
8989
}
9090

91-
$data = $this->postMount($component, $data);
91+
$postMount = $this->postMount($component, $data);
92+
$data = $postMount['data'];
93+
$extraMetadata = $postMount['extraMetadata'];
9294

9395
// create attributes from "attributes" key if exists
9496
$attributesVar = $componentMetadata->getAttributesVar();
@@ -109,7 +111,8 @@ public function mountFromObject(object $component, array $data, ComponentMetadat
109111
$componentMetadata->getName(),
110112
$component,
111113
new ComponentAttributes(array_merge($attributes, $data)),
112-
$originalData
114+
$originalData,
115+
$extraMetadata,
113116
);
114117
}
115118

@@ -188,11 +191,15 @@ private function preMount(object $component, array $data): array
188191
return $data;
189192
}
190193

194+
/**
195+
* @return array{data: array<string, mixed>, extraMetadata: array<string, mixed>}
196+
*/
191197
private function postMount(object $component, array $data): array
192198
{
193199
$event = new PostMountEvent($component, $data);
194200
$this->eventDispatcher->dispatch($event);
195201
$data = $event->getData();
202+
$extraMetadata = $event->getExtraMetadata();
196203

197204
foreach (AsTwigComponent::postMountMethods($component) as $method) {
198205
$newData = $component->{$method->name}($data);
@@ -202,7 +209,10 @@ private function postMount(object $component, array $data): array
202209
}
203210
}
204211

205-
return $data;
212+
return [
213+
'data' => $data,
214+
'extraMetadata' => $extraMetadata,
215+
];
206216
}
207217

208218
private function isAnonymousComponent(string $name): bool

src/TwigComponent/src/Event/PostMountEvent.php

Lines changed: 20 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -18,8 +18,11 @@
1818
*/
1919
final class PostMountEvent extends Event
2020
{
21-
public function __construct(private object $component, private array $data)
22-
{
21+
public function __construct(
22+
private object $component,
23+
private array $data,
24+
private array $extraMetadata = [],
25+
) {
2326
}
2427

2528
public function getComponent(): object
@@ -36,4 +39,19 @@ public function setData(array $data): void
3639
{
3740
$this->data = $data;
3841
}
42+
43+
public function getExtraMetadata(): array
44+
{
45+
return $this->extraMetadata;
46+
}
47+
48+
public function addExtraMetadata(string $key, mixed $value): void
49+
{
50+
$this->extraMetadata[$key] = $value;
51+
}
52+
53+
public function removeExtraMetadata(string $key): void
54+
{
55+
unset($this->extraMetadata[$key]);
56+
}
3957
}

src/TwigComponent/src/MountedComponent.php

Lines changed: 2 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -18,13 +18,6 @@
1818
*/
1919
final class MountedComponent
2020
{
21-
/**
22-
* Any extra metadata that might be useful to set.
23-
*
24-
* @var array<string, mixed>
25-
*/
26-
private array $extraMetadata = [];
27-
2821
/**
2922
* @param array|null $inputProps if the component was just originally created,
3023
* (not hydrated from a request), this is the
@@ -34,7 +27,8 @@ public function __construct(
3427
private string $name,
3528
private object $component,
3629
private ComponentAttributes $attributes,
37-
private ?array $inputProps = []
30+
private ?array $inputProps = [],
31+
private array $extraMetadata = [],
3832
) {
3933
}
4034

@@ -53,11 +47,6 @@ public function getAttributes(): ComponentAttributes
5347
return $this->attributes;
5448
}
5549

56-
public function setAttributes(ComponentAttributes $attributes): void
57-
{
58-
$this->attributes = $attributes;
59-
}
60-
6150
public function getInputProps(): array
6251
{
6352
if (null === $this->inputProps) {

0 commit comments

Comments
 (0)