Skip to content

Commit 4fa6d3f

Browse files
committed
fix(laravel): groups with input/output
fixes #7338
1 parent a2867e9 commit 4fa6d3f

File tree

5 files changed

+143
-1
lines changed

5 files changed

+143
-1
lines changed

src/Laravel/ApiPlatformProvider.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -467,7 +467,7 @@ public function register(): void
467467
$config = $app['config'];
468468
$defaultContext = $config->get('api-platform.serializer', []);
469469

470-
return new ObjectNormalizer(defaultContext: $defaultContext);
470+
return new ObjectNormalizer($app->make(ClassMetadataFactoryInterface::class), defaultContext: $defaultContext);
471471
});
472472

473473
$this->app->singleton(DateTimeNormalizer::class, function (Application $app) {

src/Laravel/Tests/JsonLdTest.php

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -378,4 +378,23 @@ public function testCustomRelation(): void
378378
$this->assertArrayHasKey('id', $home['order']);
379379
$this->assertArrayHasKey('number', $home['order']);
380380
}
381+
382+
public function testPostIssue7338Input(): void
383+
{
384+
$data = [
385+
'title' => 'Test Title',
386+
'description' => 'Test Description', // description should not be denormalized because of serialization groups
387+
];
388+
389+
$response = $this->postJson('/api/issue7338_reproducers/input', $data, ['accept' => 'application/ld+json', 'content-type' => 'application/ld+json']);
390+
$response->assertStatus(201);
391+
$response->assertJson(['title' => 'Test Title']);
392+
}
393+
394+
public function testGetIssue7338Output(): void
395+
{
396+
$response = $this->getJson('/api/issue7338_reproducers/1/output', ['accept' => 'application/ld+json']);
397+
$response->assertStatus(200);
398+
$response->assertJson(['name' => 'Test Name']);
399+
}
381400
}
Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,32 @@
1+
<?php
2+
3+
/*
4+
* This file is part of the API Platform project.
5+
*
6+
* (c) Kévin Dunglas <dunglas@gmail.com>
7+
*
8+
* For the full copyright and license information, please view the LICENSE
9+
* file that was distributed with this source code.
10+
*/
11+
12+
declare(strict_types=1);
13+
14+
namespace Workbench\App\ApiResource;
15+
16+
use Symfony\Component\Serializer\Annotation\Groups;
17+
18+
class Issue7338Input
19+
{
20+
public ?int $id = null;
21+
22+
#[Groups(['issue7338:input:write'])]
23+
public ?string $title = null;
24+
25+
public ?string $description = null;
26+
27+
public function __construct(?string $title = null, ?string $description = null)
28+
{
29+
$this->title = $title;
30+
$this->description = $description;
31+
}
32+
}
Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,35 @@
1+
<?php
2+
3+
/*
4+
* This file is part of the API Platform project.
5+
*
6+
* (c) Kévin Dunglas <dunglas@gmail.com>
7+
*
8+
* For the full copyright and license information, please view the LICENSE
9+
* file that was distributed with this source code.
10+
*/
11+
12+
declare(strict_types=1);
13+
14+
namespace Workbench\App\ApiResource;
15+
16+
use ApiPlatform\Metadata\ApiProperty;
17+
use Symfony\Component\Serializer\Annotation\Groups;
18+
19+
class Issue7338Output
20+
{
21+
#[ApiProperty(identifier: true)]
22+
public int $id;
23+
24+
#[Groups(['issue7338:output:read'])]
25+
public string $name;
26+
27+
public \DateTimeImmutable $date;
28+
29+
public function __construct(int $id, string $name, \DateTimeImmutable $date)
30+
{
31+
$this->id = $id;
32+
$this->name = $name;
33+
$this->date = $date;
34+
}
35+
}
Lines changed: 56 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,56 @@
1+
<?php
2+
3+
/*
4+
* This file is part of the API Platform project.
5+
*
6+
* (c) Kévin Dunglas <dunglas@gmail.com>
7+
*
8+
* For the full copyright and license information, please view the LICENSE
9+
* file that was distributed with this source code.
10+
*/
11+
12+
declare(strict_types=1);
13+
14+
namespace Workbench\App\ApiResource;
15+
16+
use ApiPlatform\Metadata\ApiResource;
17+
use ApiPlatform\Metadata\Get;
18+
use ApiPlatform\Metadata\Operation;
19+
use ApiPlatform\Metadata\Post;
20+
21+
#[ApiResource(
22+
uriTemplate: '/issue7338_reproducers/{id}',
23+
operations: [
24+
new Get(
25+
output: Issue7338Output::class,
26+
uriTemplate: '/issue7338_reproducers/{id}/output',
27+
provider: [self::class, 'provide'],
28+
normalizationContext: ['groups' => ['issue7338:output:read']]
29+
),
30+
new Post(
31+
input: Issue7338Input::class,
32+
uriTemplate: '/issue7338_reproducers/input',
33+
processor: [self::class, 'process'],
34+
denormalizationContext: ['groups' => ['issue7338:input:write']],
35+
),
36+
]
37+
)]
38+
class Issue7338Reproducer
39+
{
40+
public function __construct(public ?int $id = null, public ?string $title = null)
41+
{
42+
$this->id = $id;
43+
}
44+
45+
public static function provide(Operation $operation, array $uriVariables = [], array $context = [])
46+
{
47+
return new Issue7338Output((int) $uriVariables['id'], 'Test Name', new \DateTimeImmutable());
48+
}
49+
50+
public static function process(mixed $data, Operation $operation, array $uriVariables = [], array $context = [])
51+
{
52+
\assert(null === $data->description);
53+
54+
return new self(1, $data->title);
55+
}
56+
}

0 commit comments

Comments
 (0)