class MediaLibraryFieldWidgetOpener

Same name in other branches
  1. 9 core/modules/media_library/src/MediaLibraryFieldWidgetOpener.php \Drupal\media_library\MediaLibraryFieldWidgetOpener
  2. 8.9.x core/modules/media_library/src/MediaLibraryFieldWidgetOpener.php \Drupal\media_library\MediaLibraryFieldWidgetOpener
  3. 10 core/modules/media_library/src/MediaLibraryFieldWidgetOpener.php \Drupal\media_library\MediaLibraryFieldWidgetOpener

The media library opener for field widgets.

@internal This service is an internal part of Media Library's field widget.

Hierarchy

Expanded class hierarchy of MediaLibraryFieldWidgetOpener

1 string reference to 'MediaLibraryFieldWidgetOpener'
media_library.services.yml in core/modules/media_library/media_library.services.yml
core/modules/media_library/media_library.services.yml
1 service uses MediaLibraryFieldWidgetOpener
media_library.opener.field_widget in core/modules/media_library/media_library.services.yml
Drupal\media_library\MediaLibraryFieldWidgetOpener

File

core/modules/media_library/src/MediaLibraryFieldWidgetOpener.php, line 20

Namespace

Drupal\media_library
View source
class MediaLibraryFieldWidgetOpener implements MediaLibraryOpenerInterface {
    
    /**
     * The entity type manager.
     *
     * @var \Drupal\Core\Entity\EntityTypeManagerInterface
     */
    protected $entityTypeManager;
    
    /**
     * MediaLibraryFieldWidgetOpener constructor.
     *
     * @param \Drupal\Core\Entity\EntityTypeManagerInterface $entity_type_manager
     *   The entity type manager.
     */
    public function __construct(EntityTypeManagerInterface $entity_type_manager) {
        $this->entityTypeManager = $entity_type_manager;
    }
    
    /**
     * {@inheritdoc}
     */
    public function checkAccess(MediaLibraryState $state, AccountInterface $account) {
        $parameters = $state->getOpenerParameters() + [
            'entity_id' => NULL,
        ];
        // Forbid access if any of the required parameters are missing.
        foreach ([
            'entity_type_id',
            'bundle',
            'field_name',
        ] as $key) {
            if (empty($parameters[$key])) {
                return AccessResult::forbidden("{$key} parameter is missing.")->addCacheableDependency($state);
            }
        }
        $entity_type_id = $parameters['entity_type_id'];
        $bundle = $parameters['bundle'];
        $field_name = $parameters['field_name'];
        // Since we defer to a field to determine access, ensure we are dealing with
        // a fieldable entity type.
        $entity_type = $this->entityTypeManager
            ->getDefinition($entity_type_id);
        if (!$entity_type->entityClassImplements(FieldableEntityInterface::class)) {
            throw new \LogicException("The media library can only be opened by fieldable entities.");
        }
        
        /** @var \Drupal\Core\Entity\RevisionableStorageInterface $storage */
        $storage = $this->entityTypeManager
            ->getStorage($entity_type_id);
        $access_handler = $this->entityTypeManager
            ->getAccessControlHandler($entity_type_id);
        if (!empty($parameters['revision_id'])) {
            $entity = $storage->loadRevision($parameters['revision_id']);
            $entity_access = $access_handler->access($entity, 'update', $account, TRUE);
        }
        elseif ($parameters['entity_id']) {
            $entity = $storage->load($parameters['entity_id']);
            $entity_access = $access_handler->access($entity, 'update', $account, TRUE);
        }
        else {
            $entity_access = $access_handler->createAccess($bundle, $account, [], TRUE);
        }
        // If entity-level access is denied, there's no point in continuing.
        if (!$entity_access->isAllowed()) {
            if ($entity_access instanceof RefinableCacheableDependencyInterface) {
                $entity_access->addCacheableDependency($state);
            }
            return $entity_access;
        }
        // If the entity has not been loaded, create it in memory now.
        if (!isset($entity)) {
            $values = [];
            if ($bundle_key = $entity_type->getKey('bundle')) {
                $values[$bundle_key] = $bundle;
            }
            
            /** @var \Drupal\Core\Entity\FieldableEntityInterface $entity */
            $entity = $storage->create($values);
        }
        $items = $entity->get($field_name);
        $field_definition = $items->getFieldDefinition();
        // Check that the field is an entity reference, or subclass of it, since we
        // need to check the target_type setting.
        if (!$items instanceof EntityReferenceFieldItemList) {
            throw new \LogicException('Expected the media library to be opened by an entity reference field.');
        }
        if ($field_definition->getFieldStorageDefinition()
            ->getSetting('target_type') !== 'media') {
            throw new \LogicException('Expected the media library to be opened by an entity reference field that target media items.');
        }
        $field_access = $access_handler->fieldAccess('edit', $field_definition, $account, $items, TRUE);
        $access = $entity_access->andIf($field_access);
        if ($access instanceof RefinableCacheableDependencyInterface) {
            $access->addCacheableDependency($state);
        }
        return $access;
    }
    
    /**
     * {@inheritdoc}
     */
    public function getSelectionResponse(MediaLibraryState $state, array $selected_ids) {
        $response = new AjaxResponse();
        $parameters = $state->getOpenerParameters();
        if (empty($parameters['field_widget_id'])) {
            throw new \InvalidArgumentException('field_widget_id parameter is missing.');
        }
        // Create a comma-separated list of media IDs, insert them in the hidden
        // field of the widget, and trigger the field update via the hidden submit
        // button.
        $widget_id = $parameters['field_widget_id'];
        $ids = implode(',', $selected_ids);
        $response->addCommand(new InvokeCommand("[data-media-library-widget-value=\"{$widget_id}\"]", 'val', [
            $ids,
        ]))
            ->addCommand(new InvokeCommand("[data-media-library-widget-update=\"{$widget_id}\"]", 'trigger', [
            'mousedown',
        ]));
        return $response;
    }

}

Members

Title Sort descending Modifiers Object type Summary Overriden Title
MediaLibraryFieldWidgetOpener::$entityTypeManager protected property The entity type manager.
MediaLibraryFieldWidgetOpener::checkAccess public function Checks media library access. Overrides MediaLibraryOpenerInterface::checkAccess
MediaLibraryFieldWidgetOpener::getSelectionResponse public function Generates a response after selecting media items in the media library. Overrides MediaLibraryOpenerInterface::getSelectionResponse
MediaLibraryFieldWidgetOpener::__construct public function MediaLibraryFieldWidgetOpener constructor.

Buggy or inaccurate documentation? Please file an issue. Need support? Need help programming? Connect with the Drupal community.