acquia_dam-1.0.0-rc1/src/Controller/EditorMediaController.php
src/Controller/EditorMediaController.php
<?php namespace Drupal\acquia_dam\Controller; use Drupal\Component\Datetime\TimeInterface; use Drupal\Core\Access\CsrfTokenGenerator; use Drupal\Core\DependencyInjection\ContainerInjectionInterface; use Drupal\Core\Entity\EntityRepositoryInterface; use Drupal\Core\Entity\EntityTypeManagerInterface; use Drupal\media\MediaInterface; use Symfony\Component\DependencyInjection\ContainerInterface; use Symfony\Component\HttpFoundation\JsonResponse; use Symfony\Component\HttpFoundation\Request; use Symfony\Component\HttpKernel\Exception\AccessDeniedHttpException; use Symfony\Component\HttpKernel\Exception\NotFoundHttpException; /** * Controller for the media revision CKEditor plugin. */ final class EditorMediaController implements ContainerInjectionInterface { /** * The CSRF token service. * * @var \Drupal\Core\Access\CsrfTokenGenerator */ private $csrfToken; /** * The entity type manager. * * @var \Drupal\Core\Entity\EntityTypeManagerInterface */ private $entityTypeManager; /** * The entity repository. * * @var \Drupal\Core\Entity\EntityRepositoryInterface */ private $entityRepository; /** * The time service. * * @var \Drupal\Component\Datetime\TimeInterface */ protected $time; /** * Constructs a new EditorMediaRevisionController object. * * @param \Drupal\Core\Access\CsrfTokenGenerator $csrfToken * The CSRF token service. * @param \Drupal\Core\Entity\EntityTypeManagerInterface $entityTypeManager * The entity type manager. * @param \Drupal\Core\Entity\EntityRepositoryInterface $entityRepository * The entity repository. * @param \Drupal\Component\Datetime\TimeInterface $time * The time object. */ public function __construct(CsrfTokenGenerator $csrfToken, EntityTypeManagerInterface $entityTypeManager, EntityRepositoryInterface $entityRepository, TimeInterface $time) { $this->csrfToken = $csrfToken; $this->entityTypeManager = $entityTypeManager; $this->entityRepository = $entityRepository; $this->time = $time; } /** * {@inheritdoc} */ public static function create(ContainerInterface $container) { return new self( $container->get('csrf_token'), $container->get('entity_type.manager'), $container->get('entity.repository'), $container->get('datetime.time') ); } /** * Returns JSON response to determine if a media embed is the latest revision. * * @param \Symfony\Component\HttpFoundation\Request $request * The request. * * @return \Symfony\Component\HttpFoundation\JsonResponse * The response. * * @throws \Drupal\Component\Plugin\Exception\InvalidPluginDefinitionException * @throws \Drupal\Component\Plugin\Exception\PluginNotFoundException * @throws \Drupal\Core\Entity\EntityStorageException */ public function isLatestRevision(Request $request): JsonResponse { $this->csrfCheck($request); $uuid = $request->query->get('uuid', ''); $revision_id = $request->query->get('revisionId', ''); if ($uuid === '' || $revision_id === '') { throw new NotFoundHttpException(); } $media = $this->entityRepository->loadEntityByUuid('media', $uuid); if (!$media instanceof MediaInterface) { throw new NotFoundHttpException(); } $revision = $this->entityTypeManager->getStorage('media')->loadRevision($revision_id); if (!$revision instanceof MediaInterface) { throw new NotFoundHttpException(); } if ($revision->uuid() !== $media->uuid()) { throw new NotFoundHttpException(); } $is_latest = $revision->isLatestRevision(); // If the media is expired then there is no need to show the update field. $expiry_date = $media->get('acquia_dam_expiry_date')->getValue(); if ($expiry_date && (int) $expiry_date[0]['value'] < $this->time->getCurrentTime()) { $is_latest = TRUE; } return (new JsonResponse([ 'isLatest' => $is_latest, ])) ->setPrivate() // Allow the end user to cache this response for 5 minutes. ->setMaxAge(300); } /** * Returns JSON response to determine if a media embed is the latest revision. * * @param \Symfony\Component\HttpFoundation\Request $request * The request. * * @return \Symfony\Component\HttpFoundation\JsonResponse * The response. * * @throws \Drupal\Component\Plugin\Exception\InvalidPluginDefinitionException * @throws \Drupal\Component\Plugin\Exception\PluginNotFoundException * @throws \Drupal\Core\Entity\EntityStorageException */ public function isExpired(Request $request): JsonResponse { $this->csrfCheck($request); $is_media_expired = FALSE; $uuid = $request->query->get('uuid', ''); if ($uuid === '') { throw new NotFoundHttpException(); } $media = $this->entityRepository->loadEntityByUuid('media', $uuid); if (!$media instanceof MediaInterface) { throw new NotFoundHttpException(); } // This not a DAM asset, it cannot be expired. if (!$media->hasField('acquia_dam_expiry_date')) { return (new JsonResponse([ 'isExpired' => FALSE, ])) ->setPrivate() // Allow the end user to cache this response for 5 minutes. ->setMaxAge(300); } $expiry_date = $media->get('acquia_dam_expiry_date')->getValue(); if ($expiry_date && (int) $expiry_date[0]['value'] < $this->time->getCurrentTime()) { $is_media_expired = TRUE; } return (new JsonResponse([ 'isExpired' => $is_media_expired, ])) ->setPrivate() // Allow the end user to cache this response for 5 minutes. ->setMaxAge(300); } /** * Performs CSRF check on the request. * * @param \Symfony\Component\HttpFoundation\Request $request * The request. */ private function csrfCheck(Request $request): void { $header = 'X-Drupal-AcquiaDam-CSRF-Token'; if (!$request->headers->has($header)) { throw new AccessDeniedHttpException("$header header is missing."); } $token = $request->headers->get($header); if ($token === NULL || !$this->csrfToken->validate($token, $header)) { throw new AccessDeniedHttpException("$header is invalid."); } } }