Skip to content

Instantly share code, notes, and snippets.

@jorislucius
Last active April 2, 2023 19:16
Show Gist options
  • Star 4 You must be signed in to star a gist
  • Fork 2 You must be signed in to fork a gist
  • Save jorislucius/8c524fb45e8a25657d474c0abe9ef48f to your computer and use it in GitHub Desktop.
Save jorislucius/8c524fb45e8a25657d474c0abe9ef48f to your computer and use it in GitHub Desktop.
Drupal 8 | Redirect all anonymous users to login page. With a few needed exceptions like /user/password
<?php
namespace Drupal\<yourmodulename>\EventSubscriber;
use Symfony\Component\EventDispatcher\EventSubscriberInterface;
use Symfony\Component\HttpFoundation\RedirectResponse;
use Symfony\Component\HttpKernel\Event\GetResponseEvent;
use Symfony\Component\HttpKernel\KernelEvents;
/**
* Event subscriber subscribing to KernelEvents::REQUEST.
*/
class RedirectAnonymousSubscriber implements EventSubscriberInterface {
public function checkAuthStatus(GetResponseEvent $event) {
global $base_url;
if (
\Drupal::currentUser()->isAnonymous() &&
\Drupal::routeMatch()->getRouteName() != 'user.login' &&
\Drupal::routeMatch()->getRouteName() != 'user.reset' &&
\Drupal::routeMatch()->getRouteName() != 'user.reset.form' &&
\Drupal::routeMatch()->getRouteName() != 'user.reset.login' &&
\Drupal::routeMatch()->getRouteName() != 'user.pass' ) {
// add logic to check other routes you want available to anonymous users,
// otherwise, redirect to login page.
$route_name = \Drupal::routeMatch()->getRouteName();
if (strpos($route_name, 'view') === 0 && strpos($route_name, 'rest_') !== FALSE) {
return;
}
$response = new RedirectResponse($base_url . '/user/login', 301);
$event->setResponse($response);
$event->stopPropagation();
return;
}
}
public static function getSubscribedEvents() {
$events[KernelEvents::REQUEST][] = array('checkAuthStatus');
return $events;
}
}
@rkhregar
Copy link

rkhregar commented Mar 4, 2021

@mogbril
i think you may have other redirection in your .htaccess or somewhere else that is creating loop

@lonalore
Copy link

lonalore commented Apr 2, 2023

My solution under Drupal v9.5.7:

<?php

namespace Drupal\[MODULE]\EventSubscriber;

use Drupal\Core\Session\AccountInterface;
use Drupal\Core\Url;
use Symfony\Component\EventDispatcher\EventSubscriberInterface;
use Symfony\Component\HttpFoundation\RedirectResponse;
use Symfony\Component\HttpKernel\Event\ExceptionEvent;
use Symfony\Component\HttpKernel\Exception\HttpExceptionInterface;
use Symfony\Component\HttpKernel\KernelEvents;

/**
 * Class EventSubscriber.
 */
class EventSubscriber implements EventSubscriberInterface {

  /**
   * The current user.
   *
   * @var \Drupal\Core\Session\AccountInterface
   */
  protected $account;

  /**
   * Constructor.
   *
   * @param \Drupal\Core\Session\AccountInterface $account
   *   The current user.
   */
  public function __construct(AccountInterface $account) {
    $this->account = $account;
  }

  /**
   * Redirects users when access is denied.
   *
   * @param \Symfony\Component\HttpKernel\Event\ExceptionEvent $event
   *   The event to process.
   */
  public function onException(ExceptionEvent $event) {
    $exception = $event->getThrowable();
    if ($exception instanceof HttpExceptionInterface && $exception->getStatusCode() === 403) {
      if (!$this->account->isAuthenticated()) {
        $url = Url::fromRoute('user.register');
        $response = new RedirectResponse($url->toString());
        $event->setResponse($response);
      }
    }
  }

  /**
   * Events.
   */
  public static function getSubscribedEvents(): array {
    return [
      KernelEvents::EXCEPTION                => [
        ['onException', 80],
      ],
    ];
  }

}

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment