From 19f746c5882686bae8c5f245fef4b9e071b2a3a5 Mon Sep 17 00:00:00 2001 From: Claudiu Pintiuta Date: Mon, 8 Jul 2024 16:18:54 +0300 Subject: [PATCH] fix content type, special case for multipart/form-data Signed-off-by: Claudiu Pintiuta --- .../autoload/content-negotiation.global.php | 24 +++++++++++++++---- .../ContentNegotiationMiddleware.php | 7 ++++-- 2 files changed, 25 insertions(+), 6 deletions(-) diff --git a/config/autoload/content-negotiation.global.php b/config/autoload/content-negotiation.global.php index fc70428a..b464f768 100644 --- a/config/autoload/content-negotiation.global.php +++ b/config/autoload/content-negotiation.global.php @@ -4,19 +4,35 @@ return [ 'content-negotiation' => [ - 'default' => [ // default to any route if not configured above - 'Accept' => [ + 'default' => [ // default to any route if not configured above + 'Accept' => [ // the Accept is what format the server can send back 'application/json', 'application/hal+json', ], - 'Content-Type' => [ + 'Content-Type' => [ // the Content-Type is what format the server can process 'application/json', 'application/hal+json', ], ], - 'your.route.name' => [ + 'your.route.name' => [ 'Accept' => [], 'Content-Type' => [], ], + 'user.avatar.create' => [ + 'Accept' => [ + 'application/json', + 'application/hal+json', + ], + 'Content-Type' => [ + 'multipart/form-data', + ], + ], + 'user.my-avatar.create' => [ + 'Accept' => [ + 'application/json', + 'application/hal+json', + ], + 'Content-Type' => 'multipart/form-data', + ], ], ]; diff --git a/src/App/src/Middleware/ContentNegotiationMiddleware.php b/src/App/src/Middleware/ContentNegotiationMiddleware.php index f56a1924..7d51390b 100644 --- a/src/App/src/Middleware/ContentNegotiationMiddleware.php +++ b/src/App/src/Middleware/ContentNegotiationMiddleware.php @@ -58,6 +58,7 @@ public function process( $response = $handler->handle($request); $responseContentType = $response->getHeaderLine('Content-Type'); + if (! $this->validateResponseContentType($responseContentType, $accept)) { return $this->notAcceptableResponse('Unable to resolve Accept header to a representation'); } @@ -98,15 +99,17 @@ public function checkContentType(string $routeName, string $contentType): bool return true; } + $contentType = explode(';', $contentType); + $acceptList = $this->config['default']['Content-Type'] ?? []; if (! empty($this->config[$routeName]['Content-Type'])) { $acceptList = $this->config[$routeName]['Content-Type'] ?? []; } if (is_array($acceptList)) { - return in_array($contentType, $acceptList, true); + return ! empty(array_intersect($contentType, $acceptList)); } else { - return $contentType === $acceptList; + return in_array($acceptList, $contentType, true); } }