diff --git a/core/modules/jsonapi/jsonapi.services.yml b/core/modules/jsonapi/jsonapi.services.yml index b5cf0ef1e9..4f652f3799 100644 --- a/core/modules/jsonapi/jsonapi.services.yml +++ b/core/modules/jsonapi/jsonapi.services.yml @@ -83,7 +83,7 @@ services: - { name: jsonapi_encoder, format: 'api_json' } jsonapi.resource_type.repository: class: Drupal\jsonapi\ResourceType\ResourceTypeRepository - arguments: ['@entity_type.manager', '@entity_type.bundle.info', '@entity_field.manager', '@cache.jsonapi_resource_types'] + arguments: ['@entity_type.manager', '@entity_type.bundle.info', '@entity_field.manager', '@cache.jsonapi_resource_types', '@event_dispatcher'] jsonapi.route_enhancer: class: Drupal\jsonapi\Routing\RouteEnhancer tags: diff --git a/core/modules/jsonapi/src/ResourceType/ResourceTypeBuildEvent.php b/core/modules/jsonapi/src/ResourceType/ResourceTypeBuildEvent.php new file mode 100644 index 0000000000..62868006a8 --- /dev/null +++ b/core/modules/jsonapi/src/ResourceType/ResourceTypeBuildEvent.php @@ -0,0 +1,79 @@ +resourceTypeName = $resource_type_name; + } + + /** + * Creates a new ResourceTypeBuildEvent. + * + * @param string $resource_type_name + * A JSON:API resource type name. + * + * @return \Drupal\jsonapi\ResourceType\ResourceTypeBuildEvent + * A new event. + */ + public static function create($resource_type_name) { + return new static($resource_type_name); + } + + /** + * Gets current resource type name of the resource type to be built. + * + * @return string + * The resource type name. + */ + public function getResourceTypeName() { + return $this->resourceTypeName; + } + + /** + * Disables the resource type to be built. + */ + public function disableResourceType() { + $this->disabled = TRUE; + } + + /** + * Whether the resource type to be built should be disabled. + * + * @return bool + * TRUE if the resource type should be disabled, FALSE otherwise. + */ + public function resourceTypeShouldBeDisabled() { + return $this->disabled; + } + +} diff --git a/core/modules/jsonapi/src/ResourceType/ResourceTypeBuildEvents.php b/core/modules/jsonapi/src/ResourceType/ResourceTypeBuildEvents.php new file mode 100644 index 0000000000..abfd066e3f --- /dev/null +++ b/core/modules/jsonapi/src/ResourceType/ResourceTypeBuildEvents.php @@ -0,0 +1,18 @@ +entityTypeManager = $entity_type_manager; $this->entityTypeBundleInfo = $entity_bundle_info; $this->entityFieldManager = $entity_field_manager; $this->cache = $cache; + $this->eventDispatcher = $dispatcher; } /** @@ -139,11 +150,13 @@ public function all() { */ protected function createResourceType(EntityTypeInterface $entity_type, $bundle) { $raw_fields = $this->getAllFieldNames($entity_type, $bundle); + $event = ResourceTypeBuildEvent::create(sprintf('%s--%s', $entity_type->id(), $bundle)); + $this->eventDispatcher->dispatch(ResourceTypeBuildEvents::BUILD, $event); return new ResourceType( $entity_type->id(), $bundle, $entity_type->getClass(), - $entity_type->isInternal(), + $entity_type->isInternal() || $event->resourceTypeShouldBeDisabled(), static::isLocatableResourceType($entity_type, $bundle), static::isMutableResourceType($entity_type, $bundle), static::isVersionableResourceType($entity_type), diff --git a/core/modules/jsonapi/tests/modules/jsonapi_test_resource_type_building/jsonapi_test_resource_type_building.info.yml b/core/modules/jsonapi/tests/modules/jsonapi_test_resource_type_building/jsonapi_test_resource_type_building.info.yml new file mode 100644 index 0000000000..43d9a83818 --- /dev/null +++ b/core/modules/jsonapi/tests/modules/jsonapi_test_resource_type_building/jsonapi_test_resource_type_building.info.yml @@ -0,0 +1,4 @@ +name: 'JSON:API test resource type building API' +type: module +package: Testing +core: 8.x diff --git a/core/modules/jsonapi/tests/modules/jsonapi_test_resource_type_building/jsonapi_test_resource_type_building.services.yml b/core/modules/jsonapi/tests/modules/jsonapi_test_resource_type_building/jsonapi_test_resource_type_building.services.yml new file mode 100644 index 0000000000..77dccb48bf --- /dev/null +++ b/core/modules/jsonapi/tests/modules/jsonapi_test_resource_type_building/jsonapi_test_resource_type_building.services.yml @@ -0,0 +1,5 @@ +services: + jsonapi_test_resource_type_building.build_subscriber: + class: Drupal\jsonapi_test_resource_type_building\EventSubscriber\ResourceTypeBuildEventSubscriber + tags: + - { name: event_subscriber } diff --git a/core/modules/jsonapi/tests/modules/jsonapi_test_resource_type_building/src/EventSubscriber/ResourceTypeBuildEventSubscriber.php b/core/modules/jsonapi/tests/modules/jsonapi_test_resource_type_building/src/EventSubscriber/ResourceTypeBuildEventSubscriber.php new file mode 100644 index 0000000000..252461032c --- /dev/null +++ b/core/modules/jsonapi/tests/modules/jsonapi_test_resource_type_building/src/EventSubscriber/ResourceTypeBuildEventSubscriber.php @@ -0,0 +1,36 @@ + 'disableResourceType']; + } + + /** + * Disables any resource types that have been disabled by a test. + * + * @param \Drupal\jsonapi\ResourceType\ResourceTypeBuildEvent $event + * The build event. + */ + public function disableResourceType(ResourceTypeBuildEvent $event) { + $disabled_resource_types = \Drupal::state()->get('jsonapi_test_resource_type_builder.disabled_resource_types', []); + if (in_array($event->getResourceTypeName(), $disabled_resource_types, TRUE)) { + $event->disableResourceType(); + } + } + +} diff --git a/core/modules/jsonapi/tests/src/Kernel/ResourceType/ResourceTypeRepositoryTest.php b/core/modules/jsonapi/tests/src/Kernel/ResourceType/ResourceTypeRepositoryTest.php index 011ef97c85..d4806976cb 100644 --- a/core/modules/jsonapi/tests/src/Kernel/ResourceType/ResourceTypeRepositoryTest.php +++ b/core/modules/jsonapi/tests/src/Kernel/ResourceType/ResourceTypeRepositoryTest.php @@ -2,6 +2,7 @@ namespace Drupal\Tests\jsonapi\Kernel\ResourceType; +use Drupal\Core\Cache\Cache; use Drupal\jsonapi\ResourceType\ResourceType; use Drupal\node\Entity\NodeType; use Drupal\Tests\jsonapi\Kernel\JsonapiKernelTestBase; @@ -23,6 +24,7 @@ class ResourceTypeRepositoryTest extends JsonapiKernelTestBase { 'serialization', 'system', 'user', + 'jsonapi_test_resource_type_building', ]; /** @@ -147,4 +149,22 @@ public function getFieldMappingProvider() { ]; } + /** + * Tests that resource types can be disabled by a build subscriber. + */ + public function testResourceTypeDisabling() { + $this->assertFalse($this->resourceTypeRepository->getByTypeName('node--article')->isInternal()); + $this->assertFalse($this->resourceTypeRepository->getByTypeName('node--page')->isInternal()); + $this->assertFalse($this->resourceTypeRepository->getByTypeName('user--user')->isInternal()); + $disabled_resource_types = [ + 'node--page', + 'user--user', + ]; + \Drupal::state()->set('jsonapi_test_resource_type_builder.disabled_resource_types', $disabled_resource_types); + Cache::invalidateTags(['jsonapi_resource_types']); + $this->assertFalse($this->resourceTypeRepository->getByTypeName('node--article')->isInternal()); + $this->assertTrue($this->resourceTypeRepository->getByTypeName('node--page')->isInternal()); + $this->assertTrue($this->resourceTypeRepository->getByTypeName('user--user')->isInternal()); + } + }