Skip to content

Commit

Permalink
feat(state): strict query parameters
Browse files Browse the repository at this point in the history
  • Loading branch information
soyuka committed Dec 13, 2024
1 parent c59e275 commit 03ffbee
Show file tree
Hide file tree
Showing 12 changed files with 83 additions and 0 deletions.
2 changes: 2 additions & 0 deletions src/Metadata/ApiResource.php
Original file line number Diff line number Diff line change
Expand Up @@ -963,6 +963,7 @@ public function __construct(
?string $policy = null,
array|string|null $middleware = null,
array|Parameters|null $parameters = null,
protected ?bool $strictQueryParameterValidation = null,
protected array $extraProperties = [],
) {
parent::__construct(
Expand Down Expand Up @@ -1007,6 +1008,7 @@ class: $class,
rules: $rules,
policy: $policy,
middleware: $middleware,
strictQueryParameterValidation: $strictQueryParameterValidation,
extraProperties: $extraProperties
);

Expand Down
2 changes: 2 additions & 0 deletions src/Metadata/Delete.php
Original file line number Diff line number Diff line change
Expand Up @@ -98,6 +98,7 @@ public function __construct(
mixed $rules = null,
?string $policy = null,
array|string|null $middleware = null,
?bool $strictQueryParameterValidation = null,
array $extraProperties = [],
) {
parent::__construct(
Expand Down Expand Up @@ -178,6 +179,7 @@ class: $class,
extraProperties: $extraProperties,
collectDenormalizationErrors: $collectDenormalizationErrors,
parameters: $parameters,
strictQueryParameterValidation: $strictQueryParameterValidation,
stateOptions: $stateOptions,
);
}
Expand Down
2 changes: 2 additions & 0 deletions src/Metadata/Get.php
Original file line number Diff line number Diff line change
Expand Up @@ -98,6 +98,7 @@ public function __construct(
mixed $rules = null,
?string $policy = null,
array|string|null $middleware = null,
?bool $strictQueryParameterValidation = null,
array $extraProperties = [],
) {
parent::__construct(
Expand Down Expand Up @@ -177,6 +178,7 @@ class: $class,
rules: $rules,
policy: $policy,
middleware: $middleware,
strictQueryParameterValidation: $strictQueryParameterValidation,
extraProperties: $extraProperties,
);
}
Expand Down
2 changes: 2 additions & 0 deletions src/Metadata/GetCollection.php
Original file line number Diff line number Diff line change
Expand Up @@ -98,6 +98,7 @@ public function __construct(
array|string|null $rules = null,
?string $policy = null,
array|string|null $middleware = null,
?bool $strictQueryParameterValidation = null,
array $extraProperties = [],
private ?string $itemUriTemplate = null,
) {
Expand Down Expand Up @@ -178,6 +179,7 @@ class: $class,
rules: $rules,
policy: $policy,
middleware: $middleware,
strictQueryParameterValidation: $strictQueryParameterValidation,
stateOptions: $stateOptions,
);
}
Expand Down
12 changes: 12 additions & 0 deletions src/Metadata/HttpOperation.php
Original file line number Diff line number Diff line change
Expand Up @@ -155,6 +155,7 @@ public function __construct(
protected ?array $exceptionToStatus = null,
protected ?array $links = null,
protected ?array $errors = null,
protected ?bool $strictQueryParameterValidation = null,

?string $shortName = null,
?string $class = null,
Expand Down Expand Up @@ -630,6 +631,17 @@ public function withErrors(array $errors): self
{
$self = clone $this;
$self->errors = $errors;

Check failure on line 633 in src/Metadata/HttpOperation.php

View workflow job for this annotation

GitHub Actions / PHPStan (PHP 8.3)

Method ApiPlatform\Metadata\HttpOperation::withErrors() should return ApiPlatform\Metadata\HttpOperation but return statement is missing.
}

public function getStrictQueryParameterValidation(): ?bool
{
return $this->strictQueryParameterValidation;
}

public function withStrictQueryParameterValidation(bool $strictQueryParameterValidation): self
{
$self = clone $this;
$self->strictQueryParameterValidation = $strictQueryParameterValidation;

return $self;
}
Expand Down
1 change: 1 addition & 0 deletions src/Metadata/Metadata.php
Original file line number Diff line number Diff line change
Expand Up @@ -81,6 +81,7 @@ public function __construct(
protected ?string $policy = null,
protected array|string|null $middleware = null,
protected ?bool $queryParameterValidationEnabled = null,
protected ?bool $strictQueryParameterValidation = null,
protected array $extraProperties = [],
) {
if (\is_array($parameters) && $parameters) {
Expand Down
1 change: 1 addition & 0 deletions src/Metadata/Operation.php
Original file line number Diff line number Diff line change
Expand Up @@ -811,6 +811,7 @@ public function __construct(
?string $policy = null,
array|string|null $middleware = null,
?bool $queryParameterValidationEnabled = null,
protected ?bool $strictQueryParameterValidation = null,
protected array $extraProperties = [],
) {
parent::__construct(
Expand Down
2 changes: 2 additions & 0 deletions src/Metadata/Patch.php
Original file line number Diff line number Diff line change
Expand Up @@ -98,6 +98,7 @@ public function __construct(
mixed $rules = null,
?string $policy = null,
array|string|null $middleware = null,
?bool $strictQueryParameterValidation = null,
array $extraProperties = [],
) {
parent::__construct(
Expand Down Expand Up @@ -178,6 +179,7 @@ class: $class,
rules: $rules,
policy: $policy,
middleware: $middleware,
strictQueryParameterValidation: $strictQueryParameterValidation,
extraProperties: $extraProperties
);
}
Expand Down
2 changes: 2 additions & 0 deletions src/Metadata/Post.php
Original file line number Diff line number Diff line change
Expand Up @@ -100,6 +100,7 @@ public function __construct(
array|string|null $middleware = null,
array $extraProperties = [],
private ?string $itemUriTemplate = null,
?bool $strictQueryParameterValidation = null,
) {
parent::__construct(
method: 'POST',
Expand Down Expand Up @@ -179,6 +180,7 @@ class: $class,
rules: $rules,
policy: $policy,
middleware: $middleware,
strictQueryParameterValidation: $strictQueryParameterValidation,
extraProperties: $extraProperties
);
}
Expand Down
2 changes: 2 additions & 0 deletions src/Metadata/Put.php
Original file line number Diff line number Diff line change
Expand Up @@ -99,6 +99,7 @@ public function __construct(
?string $policy = null,
array|string|null $middleware = null,
array $extraProperties = [],
?bool $strictQueryParameterValidation = null,
private ?bool $allowCreate = null,
) {
parent::__construct(
Expand Down Expand Up @@ -179,6 +180,7 @@ class: $class,
rules: $rules,
policy: $policy,
middleware: $middleware,
strictQueryParameterValidation: $strictQueryParameterValidation,
extraProperties: $extraProperties
);
}
Expand Down
38 changes: 38 additions & 0 deletions src/State/Exception/ParameterNotSupportedException.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
<?php

namespace ApiPlatform\State\Exception;

use ApiPlatform\Metadata\Exception\ProblemExceptionInterface;
use ApiPlatform\Metadata\Exception\RuntimeException;

final class ParameterNotSupportedException extends RuntimeException implements ProblemExceptionInterface
{
public function __construct(private readonly string $parameter, string $message = "Parameter not supported", int $code = 0, \Throwable|null $previous = null) {
parent::__construct($message, $code, $previous);
}

public function getType(): string
{
return '/error/400';
}

public function getTitle(): ?string
{
return $this->message;
}

public function getStatus(): ?int
{
return 400;
}

public function getDetail(): ?string
{
return sprintf('Parameter "%s" not supported', $this->parameter);
}

public function getInstance(): ?string
{
return $this->parameter;
}
}
17 changes: 17 additions & 0 deletions src/State/Provider/ParameterProvider.php
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,9 @@

namespace ApiPlatform\State\Provider;

use ApiPlatform\Metadata\HttpOperation;
use ApiPlatform\Metadata\Operation;
use ApiPlatform\State\Exception\ParameterNotSupportedException;
use ApiPlatform\State\Exception\ProviderNotFoundException;
use ApiPlatform\State\ParameterNotFound;
use ApiPlatform\State\ParameterProviderInterface;
Expand Down Expand Up @@ -50,6 +52,20 @@ public function provide(Operation $operation, array $uriVariables = [], array $c
}

$parameters = $operation->getParameters();

if ($operation instanceof HttpOperation && true === $operation->getStrictQueryParameterValidation()) {
$keys = [];
foreach($parameters as $parameter) {
$keys[] = $parameter->getKey();
}

foreach (array_keys($request->attributes->get('_api_query_parameters')) as $key) {
if (!in_array($key, $keys)) {
throw new ParameterNotSupportedException($key);
}
}
}

foreach ($parameters ?? [] as $parameter) {
$extraProperties = $parameter->getExtraProperties();
unset($extraProperties['_api_values']);
Expand Down Expand Up @@ -103,3 +119,4 @@ public function provide(Operation $operation, array $uriVariables = [], array $c
return $this->decorated?->provide($operation, $uriVariables, $context);
}
}

0 comments on commit 03ffbee

Please sign in to comment.