From 1db494eae1ca3fe62330a8327fb2dc83c3578b7b Mon Sep 17 00:00:00 2001 From: Krystian Szymukowicz Date: Tue, 3 Nov 2026 16:46:24 +0100 Subject: [PATCH] [BUGFIX] Document 403 response of operations with security in OpenAPI --- .../OperationNotAllowedException.php | 4 +- .../Miscellaneous/Changelog/Index.rst | 1 + .../OpenApiSupportingExceptionTest.php | 53 +++++++++++++++++++ 3 files changed, 56 insertions(+), 2 deletions(-) create mode 100644 Tests/Unit/Exception/OpenApiSupportingExceptionTest.php diff --git a/Classes/Exception/OperationNotAllowedException.php b/Classes/Exception/OperationNotAllowedException.php index 097b6277..24a041a5 100644 --- a/Classes/Exception/OperationNotAllowedException.php +++ b/Classes/Exception/OperationNotAllowedException.php @@ -14,8 +14,8 @@ class OperationNotAllowedException extends AbstractException implements OpenApiS public static function getOpenApiResponse(): OpenApiResponse { return parent::getOpenApiResponse() - ->statusCode(SymfonyResponse::HTTP_NOT_FOUND) - ->description(self::translate('exception.resource_not_found.title')); + ->statusCode(SymfonyResponse::HTTP_FORBIDDEN) + ->description(self::translate('exception.operation_not_allowed.title')); } public function __construct(OperationInterface $operation, int $code) diff --git a/Documentation/Miscellaneous/Changelog/Index.rst b/Documentation/Miscellaneous/Changelog/Index.rst index 3d61a775..9978843e 100644 --- a/Documentation/Miscellaneous/Changelog/Index.rst +++ b/Documentation/Miscellaneous/Changelog/Index.rst @@ -6,6 +6,7 @@ Changelog 5.0.0 ===== +- OpenAPI specification documents ``403 Forbidden`` (instead of ``404 Not Found``) for operations with ``security`` or ``security_post_denormalize``, the same status as returned by the API. - [!!!] A new file reference created by ``uidLocal`` requires ``fileToken`` returned for the file by the API, otherwise ``400 Bad Request`` is returned. The same applies to a new file of a property of type ``File`` or a class extending it (``{"uid": 101, "fileToken": "..."}``). The token is returned in the response of upload endpoints and of operations with ``"fileTokens"=true`` in ``normalizationContext`` (files offered for selection, ``file.fileToken`` for file references). Pass ``fileToken`` when saving a reference. Custom upload code has to grant tokens with ``FileTokenService::grant()``. See :ref:`handling_file_upload_file_token`. - Invalid values of file and file reference properties (e.g. a text or a boolean instead of an identifier or an object) return ``400 Bad Request`` instead of HTTP 500 or clearing the property. - Files (classes extending Extbase's ``File``) nested in a response (e.g. members of a collection) are serialized like other objects, the same as in an item response, instead of the file reference output. diff --git a/Tests/Unit/Exception/OpenApiSupportingExceptionTest.php b/Tests/Unit/Exception/OpenApiSupportingExceptionTest.php new file mode 100644 index 00000000..a0361ac8 --- /dev/null +++ b/Tests/Unit/Exception/OpenApiSupportingExceptionTest.php @@ -0,0 +1,53 @@ +}> + */ + public static function exceptionClassDataProvider(): array + { + return [ + 'BadRequestException' => [BadRequestException::class], + 'InvalidPaginationParameterException' => [InvalidPaginationParameterException::class], + 'OperationNotAllowedException' => [OperationNotAllowedException::class], + 'OriginNotAllowedException' => [OriginNotAllowedException::class], + 'ResourceNotFoundException' => [ResourceNotFoundException::class], + 'UnsupportedMediaTypeException' => [UnsupportedMediaTypeException::class], + 'ValidationException' => [ValidationException::class], + ]; + } + + /** + * @param class-string $exceptionClass + */ + #[Test] + #[DataProvider('exceptionClassDataProvider')] + public function openApiResponseHasStatusCodeOfException(string $exceptionClass): void + { + // `getStatusCode()` does not depend on constructor arguments + $exception = (new \ReflectionClass($exceptionClass))->newInstanceWithoutConstructor(); + + self::assertSame($exception->getStatusCode(), $exceptionClass::getOpenApiResponse()->statusCode); + } +}