Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

MapQueryString/MapRequestPayload skips validation when empty request is sent. #54617

Open
unixslayer opened this issue Apr 16, 2024 · 0 comments

Comments

@unixslayer
Copy link

Symfony version(s) affected

6.4.6

Description

It seems to be impossible to validate request properly when sent empty. For both query string and request payload mapper will return null and skip validation. Using default value makes callable being called with object which may be invalid.

How to reproduce

final class ApiDTO
{
    #[Assert\NotBlank]
    public string $foo = '';
}
class FooController extends AbstractController
{
    #[Route("/foo", methods: ["GET"])]
    public function __invoke(#[MapQueryString(validationFailedStatusCode: 400)] ApiDTO $dto = new ApiDTO()): JsonResponse {
        dd($dto);
    }
}
expected behavior
GET /foo?foo= -> 400

validation skipped
GET /foo -> ApiDTO {
    +foo: ""
}

Possible Solution

Possible solution would be to make mapper method return default value if defined instead of returning null

// symfony/http-kernel/Controller/ArgumentResolver/RequestPayloadValueResolver.php:162
private function mapQueryString(Request $request, string $type, MapQueryString $attribute): ?object
{
    if (!$data = $request->query->all()) {
        return $attribute->metadata->hasDefaultValue() ? $attribute->metadata->getDefaultValue() : null;
    }

    return $this->serializer->denormalize($data, $type, null, $attribute->serializationContext + self::CONTEXT_DENORMALIZE);
}

// symfony/http-kernel/Controller/ArgumentResolver/RequestPayloadValueResolver.php:185
if ('' === $data = $request->getContent()) {
    return $attribute->metadata->hasDefaultValue() ? $attribute->metadata->getDefaultValue() : null;
}
GET /foo?foo= -> 400
GET /foo -> 400

Additional Context

No response

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

3 participants