Skip to content

Commit 67d29a5

Browse files
committed
Fix id formatting
1 parent ccde693 commit 67d29a5

File tree

7 files changed

+38
-9
lines changed

7 files changed

+38
-9
lines changed

src/Turbo/src/Bridge/Mercure/Broadcaster.php

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -99,7 +99,9 @@ public function broadcast(object $entity, string $action, array $options): void
9999
throw new \InvalidArgumentException(sprintf('Cannot broadcast entity of class "%s": the option "topics" is empty and "id" is missing.', $entityClass));
100100
}
101101

102-
$options['topics'] = (array) sprintf(self::TOPIC_PATTERN, rawurlencode($entityClass), rawurlencode(implode('-', (array) $options['id'])));
102+
$id = $options['id_formatted'] ?? implode('-', (array) $options['id']);
103+
104+
$options['topics'] = (array) sprintf(self::TOPIC_PATTERN, rawurlencode($entityClass), rawurlencode($id));
103105
}
104106

105107
$update = new Update(

src/Turbo/src/Broadcaster/IdAccessor.php

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -34,6 +34,7 @@ public function getEntityId(object $entity): ?array
3434
$entityClass = $entity::class;
3535

3636
if ($this->doctrine && $em = $this->doctrine->getManagerForClass($entityClass)) {
37+
// @todo: Not sure how to use the same method like in the BroadcastListener without duplicating the code.
3738
return $em->getClassMetadata($entityClass)->getIdentifierValues($entity);
3839
}
3940

src/Turbo/src/Broadcaster/TwigBroadcaster.php

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -41,6 +41,7 @@ public function broadcast(object $entity, string $action, array $options): void
4141
{
4242
if (!isset($options['id']) && null !== $id = $this->idAccessor->getEntityId($entity)) {
4343
$options['id'] = $id;
44+
$options['id_formatted'] = $id;
4445
}
4546

4647
$class = ClassUtil::getEntityClass($entity);
@@ -63,7 +64,7 @@ public function broadcast(object $entity, string $action, array $options): void
6364
->renderBlock($action, [
6465
'entity' => $entity,
6566
'action' => $action,
66-
'id' => implode('-', (array) ($options['id'] ?? [])),
67+
'id' => $options['id_formatted'],
6768
] + $options);
6869

6970
$this->broadcaster->broadcast($entity, $action, $options);

src/Turbo/src/Doctrine/BroadcastListener.php

Lines changed: 27 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -94,9 +94,10 @@ public function postFlush(EventArgs $eventArgs): void
9494
try {
9595
foreach ($this->createdEntities as $entity) {
9696
$options = $this->createdEntities[$entity];
97-
$id = $em->getClassMetadata($entity::class)->getIdentifierValues($entity);
97+
$id = $this->getIdentifierValues($em, $entity);
9898
foreach ($options as $option) {
9999
$option['id'] = $id;
100+
$options['id_formatted'] = $this->formatId($id);
100101
$this->broadcaster->broadcast($entity, Broadcast::ACTION_CREATE, $option);
101102
}
102103
}
@@ -147,13 +148,37 @@ private function storeEntitiesToPublish(EntityManagerInterface $em, object $enti
147148

148149
if ($options = $this->broadcastedClasses[$class]) {
149150
if ('createdEntities' !== $property) {
150-
$id = $em->getClassMetadata($class)->getIdentifierValues($entity);
151+
$id = $this->getIdentifierValues($em, $entity);
151152
foreach ($options as $k => $option) {
152153
$options[$k]['id'] = $id;
154+
$options[$k]['id_formatted'] = $this->formatId($id);
153155
}
154156
}
155157

156158
$this->{$property}->attach($entity, $options);
157159
}
158160
}
161+
162+
private function getIdentifierValues(EntityManagerInterface $em, object $entity): array
163+
{
164+
$class = ClassUtil::getEntityClass($entity);
165+
166+
$values = $em->getClassMetadata($class)->getIdentifierValues($entity);
167+
168+
foreach ($values as $key => $value) {
169+
if (\is_object($value)) {
170+
$values[$key] = $this->getIdentifierValues($em, $value);
171+
}
172+
}
173+
174+
return $values;
175+
}
176+
177+
private function formatId(array $id): string
178+
{
179+
$flatten = [];
180+
array_walk_recursive($id, static function ($item) use (&$flatten) { $flatten[] = $item; });
181+
182+
return implode('-', $flatten);
183+
}
159184
}

src/Turbo/tests/BroadcastTest.php

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -111,12 +111,12 @@ public function testBroadcastWithCompositePrimaryKey(): void
111111

112112
// submit first to create the entities
113113
$client->submitForm('Submit', ['title' => 'product 1']);
114-
$this->assertSelectorWillContain('#cartProducts', 'product 1');
114+
$this->assertSelectorWillContain('#cart_products', 'product 1');
115115

116116
// submit again to update the quantity
117117
$client->submitForm('Submit');
118-
$this->assertSelectorWillContain('#cartProducts', '2x product 1');
118+
$this->assertSelectorWillContain('#cart_products', '2x product 1');
119119
// this part is from the stream template
120-
$this->assertSelectorWillContain('#cartProducts', ', updated)');
120+
$this->assertSelectorWillContain('#cart_products', ', updated)');
121121
}
122122
}

src/Turbo/tests/app/Kernel.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -336,7 +336,7 @@ public function cartProducts(Request $request, EntityManagerInterface $doctrine,
336336
$doctrine->persist($cartProduct);
337337
$doctrine->flush();
338338
} else {
339-
$cartProduct = $doctrine->find(CartProduct::class, [$cartId, $productId]);
339+
$cartProduct = $doctrine->find(CartProduct::class, ['cart' => $cartId, 'product' => $productId]);
340340

341341
if (!$cartProduct) {
342342
throw new NotFoundHttpException();

src/Turbo/tests/app/templates/cart_products.html.twig

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@
33
{% block body %}
44
<h1>Create Cart, Product and CartProduct, increase quantity on update</h1>
55

6-
<div id="cart_products" {{ turbo_stream_listen('App\\Entity\\CartProducts') }}></div>
6+
<div id="cart_products" {{ turbo_stream_listen('App\\Entity\\CartProduct') }}></div>
77

88
<turbo-frame id="api">
99
<form method="post" enctype="application/x-www-form-urlencoded">

0 commit comments

Comments
 (0)