diff --git a/core/modules/jsonapi/src/Controller/EntityResource.php b/core/modules/jsonapi/src/Controller/EntityResource.php index 5c43d3ee24e75d97eb1363b5d2ed00f4b81d4615..8c0e027aa32d530ebc163acd90bff0cf3006acad 100644 --- a/core/modules/jsonapi/src/Controller/EntityResource.php +++ b/core/modules/jsonapi/src/Controller/EntityResource.php @@ -30,7 +30,6 @@ use Drupal\jsonapi\Entity\EntityValidationTrait; use Drupal\jsonapi\Access\TemporaryQueryGuard; use Drupal\jsonapi\Exception\EntityAccessDeniedHttpException; -use Drupal\jsonapi\Exception\UnprocessableHttpEntityException; use Drupal\jsonapi\IncludeResolver; use Drupal\jsonapi\JsonApiResource\IncludedData; use Drupal\jsonapi\JsonApiResource\LinkCollection; @@ -53,6 +52,7 @@ use Symfony\Component\HttpKernel\Exception\BadRequestHttpException; use Drupal\Core\Http\Exception\CacheableBadRequestHttpException; use Symfony\Component\HttpKernel\Exception\ConflictHttpException; +use Symfony\Component\HttpKernel\Exception\UnprocessableEntityHttpException; use Symfony\Component\Serializer\Exception\InvalidArgumentException; use Symfony\Component\Serializer\Exception\UnexpectedValueException; use Symfony\Component\Serializer\SerializerInterface; @@ -822,10 +822,10 @@ protected function deserialize(ResourceType $resource_type, Request $request, $c // These two serialization exception types mean there was a problem with // the structure of the decoded data and it's not valid. catch (UnexpectedValueException $e) { - throw new UnprocessableHttpEntityException($e->getMessage()); + throw new UnprocessableEntityHttpException($e->getMessage()); } catch (InvalidArgumentException $e) { - throw new UnprocessableHttpEntityException($e->getMessage()); + throw new UnprocessableEntityHttpException($e->getMessage()); } } diff --git a/core/modules/jsonapi/tests/src/Functional/JsonApiRegressionTest.php b/core/modules/jsonapi/tests/src/Functional/JsonApiRegressionTest.php index 636e8d141f33ea6ba7027593c5731a88d639e3af..3fc3c5a183d96bd7e551a8e7b59afd51c9cac288 100644 --- a/core/modules/jsonapi/tests/src/Functional/JsonApiRegressionTest.php +++ b/core/modules/jsonapi/tests/src/Functional/JsonApiRegressionTest.php @@ -1053,4 +1053,36 @@ public function testNonTranslatableEntityUpdatesFromIssue3043168() { $this->assertSame('Constantine', $response_document['data']['attributes']['name']); } + /** + * Ensure POSTing invalid data results in a 422 response, not a PHP error. + * + * @see https://www.drupal.org/project/drupal/issues/3052954 + */ + public function testInvalidDataTriggersUnprocessableEntityErrorFromIssue3052954() { + $this->config('jsonapi.settings')->set('read_only', FALSE)->save(TRUE); + + // Set up data model. + $user = $this->drupalCreateUser(['bypass node access']); + + // Test. + $request_options = [ + RequestOptions::HEADERS => [ + 'Content-Type' => 'application/vnd.api+json', + 'Accept' => 'application/vnd.api+json', + ], + RequestOptions::JSON => [ + 'data' => [ + 'type' => 'article', + 'attributes' => [ + 'title' => 'foobar', + 'created' => 'not_a_date', + ], + ], + ], + RequestOptions::AUTH => [$user->getAccountName(), $user->pass_raw], + ]; + $response = $this->request('POST', Url::fromUri('internal:/jsonapi/node/article'), $request_options); + $this->assertSame(422, $response->getStatusCode()); + } + }