photo_albums-1.0.2/src/EventSubscriber/ProtectedAlbumSubscriber.php
src/EventSubscriber/ProtectedAlbumSubscriber.php
<?php namespace Drupal\photo_albums\EventSubscriber; use Drupal\Core\PageCache\ResponsePolicy\KillSwitch; use Drupal\Core\Path\CurrentPathStack; use Drupal\Core\Routing\RedirectDestination; use Drupal\Core\Session\AccountProxy; use Drupal\Core\Url; use Drupal\path_alias\AliasManager; use Symfony\Component\EventDispatcher\EventSubscriberInterface; use Symfony\Component\HttpFoundation\RedirectResponse; use Symfony\Component\HttpFoundation\RequestStack; use Symfony\Component\HttpKernel\Event\FilterResponseEvent; use Symfony\Component\HttpKernel\KernelEvents; /** * Redirects user to protected page login screen. */ class ProtectedAlbumSubscriber implements EventSubscriberInterface { /** * The path alias manager. * * @var \Drupal\path_alias\AliasManager */ protected $aliasManager; /** * The account proxy service. * * @var \Drupal\Core\Session\AccountProxy */ protected $currentUser; /** * The current path stack service. * * @var \Drupal\Core\Path\CurrentPathStack */ protected $currentPath; /** * The redirect destination service. * * @var \Drupal\Core\Routing\RedirectDestination */ protected $destination; /** * The request stack service. * * @var \Symfony\Component\HttpFoundation\RequestStack */ protected $requestStack; /** * A policy evaluating to static::DENY when the kill switch was triggered. * * @var \Drupal\Core\PageCache\ResponsePolicy\KillSwitch */ protected $pageCacheKillSwitch; /** * Constructs a new ProtectedPagesSubscriber. * * @param \Drupal\path_alias\AliasManager $aliasManager * The path alias manager. * @param \Drupal\Core\Session\AccountProxy $currentUser * The account proxy service. * @param \Drupal\Core\Path\CurrentPathStack $currentPathStack * The current path stack service. * @param \Drupal\Core\Routing\RedirectDestination $destination * The redirect destination service. * @param \Symfony\Component\HttpFoundation\RequestStack $requestStack * The request stack service. * @param \Drupal\Core\PageCache\ResponsePolicy\KillSwitch $pageCacheKillSwitch * The cache kill switch service. */ public function __construct(AliasManager $aliasManager, AccountProxy $currentUser, CurrentPathStack $currentPathStack, RedirectDestination $destination, RequestStack $requestStack, KillSwitch $pageCacheKillSwitch) { $this->aliasManager = $aliasManager; $this->currentUser = $currentUser; $this->currentPath = $currentPathStack; $this->destination = $destination; $this->requestStack = $requestStack; $this->pageCacheKillSwitch = $pageCacheKillSwitch; } /** * Redirects user to protected page login screen. * * @param \Symfony\Component\HttpKernel\Event\FilterResponseEvent $event * The event to process. */ public function checkProtectedAlbum(FilterResponseEvent $event) { if ($this->currentUser->hasPermission('bypass album password protection')) { return; } // Get the current path and the internal path. $current_path = $this->aliasManager->getAliasByPath($this->currentPath->getPath()); $normal_path = mb_strtolower($this->aliasManager->getPathByAlias($current_path)); // Get the route parameters from the derived path. $url_object = \Drupal::service('path.validator')->getUrlIfValid($normal_path); if ($url_object !== FALSE) { $route_name = $url_object->getRouteName(); $route_parameters = $url_object->getrouteParameters(); } // If the path starts with "node" and the second element is numeric. if (isset($route_parameters['node']) && (isset($route_name) && $route_name !== 'entity.node.edit_form')) { // Check the user's session to see if they have already // authenticated this album. if (isset($_SESSION['_photo_albums_protected']['passwords'][$route_parameters['node']])) { // Get the password record for the album node. $pass = \Drupal::database()->select('photo_albums_protected', 'p') ->fields('p', ['pass']) ->condition('nid', $route_parameters['node'], '=') ->execute() ->fetchField(); // Compare the database hashed password with the cookie. if ($pass === $_SESSION['_photo_albums_protected']['passwords'][$route_parameters['node']]) { return; } } // Check to see if the node ID is in the protected // albums. $results = \Drupal::database()->select('photo_albums_protected', 'p') ->fields('p', ['nid']) ->condition('nid', $route_parameters['node'], '=') ->execute() ->fetchAll(); // If results are returned then the album is protected // so we redirect to the login page. if (count($results)) { $query = \Drupal::destination()->getAsArray(); $query['album_nid'] = $route_parameters['node']; $this->pageCacheKillSwitch->trigger(); $response = new RedirectResponse(Url::fromUri('internal:/albums/login', ['query' => $query])->toString()); $response->send(); } } } /** * {@inheritdoc} */ public static function getSubscribedEvents() { $events[KernelEvents::RESPONSE][] = ['checkProtectedAlbum']; return $events; } }