diff --git a/reference/configuration/security.rst b/reference/configuration/security.rst index 902f60a921e..2392181cac5 100644 --- a/reference/configuration/security.rst +++ b/reference/configuration/security.rst @@ -538,9 +538,18 @@ The ``invalidate_session`` option allows to redefine this behavior. Set this option to ``false`` in every firewall and the user will only be logged out from the current firewall and not the other ones. +.. _reference-security-logout-success-handler: + success_handler ~~~~~~~~~~~~~~~ +.. deprecated:: 5.1 + + This option is deprecated since Symfony 5.1. Register an + :doc:`event listener ` on the + :class:`Symfony\\Component\\Security\\Http\\Event\\LogoutEvent` + instead. + **type**: ``string`` **default**: ``'security.logout.success_handler'`` The service ID used for handling a successful logout. The service must implement diff --git a/security.rst b/security.rst index 6eb068cb969..3c889251db5 100644 --- a/security.rst +++ b/security.rst @@ -899,11 +899,112 @@ Next, you'll need to create a route for this URL (but not a controller): And that's it! By sending a user to the ``app_logout`` route (i.e. to ``/logout``) Symfony will un-authenticate the current user and redirect them. +Customizing Logout +~~~~~~~~~~~~~~~~~~ + +.. versionadded:: 5.1 + + The ``LogoutEvent`` was introduced in Symfony 5.1. Prior to this + version, you had to use a + :ref:`logout success handler ` + to customize the logout. + +In some cases you need to execute extra logic upon logout (e.g. invalidate +some tokens) or want to customize what happends after a logout. During +logout, a :class:`Symfony\\Component\\Security\\Http\\Event\\LogoutEvent` +is dispatched. Register an :doc:`event listener or subscriber ` +to execute custom logic. The following information is available in the +event class: + +``getToken()`` + Returns the security token of the session that is about to be logged + out. +``getRequest()`` + Returns the current request. +``getResponse()`` + Returns a response, if it is already set by a custom listener. Use + ``setResponse()`` to configure a custom logout response. + + .. tip:: - Need more control of what happens after logout? Add a ``success_handler`` key - under ``logout`` and point it to a service id of a class that implements - :class:`Symfony\\Component\\Security\\Http\\Logout\\LogoutSuccessHandlerInterface`. + Every Security firewall has its own event dispatcher + (``security.event_dispatcher.FIREWALLNAME``). The logout event is + dispatched on both the global and firewall dispatcher. You can register + on the firewall dispatcher if you want your listener to only be + executed for a specific firewall. For instance, if you have an ``api`` + and ``main`` firewall, use this configuration to register only on the + logout event in the ``main`` firewall: + + .. configuration-block:: + + .. code-block:: yaml + + # config/services.yaml + services: + # ... + + App\EventListener\CutomLogoutListener: + tags: + - name: kernel.event_listener, + event: 'Symfony\Component\Security\Http\Event\LogoutEvent' + dispatcher: security.event_dispatcher.main + + App\EventListener\CustomLogoutSubscriber: + tags: + - name: kernel.event_subscriber + dispacher: security.event_dispatcher.main + + .. code-block:: xml + + + + + + + + + + + + + + + + + + + .. code-block:: php + + // config/services.php + namespace Symfony\Component\DependencyInjection\Loader\Configurator; + + use App\EventListener\CutomLogoutListener; + use App\EventListener\CutomLogoutSubscriber; + use Symfony\Component\Security\Http\Event\LogoutEvent; + + return function(ContainerConfigurator $configurator) { + $services = $configurator->services(); + + $services->set(CustomLogoutListener::class) + ->tag('kernel.event_listener', [ + 'event' => LogoutEvent::class, + 'dispatcher' => 'security.event_dispatcher.main', + ]); + + $services->set(CustomLogoutSubscriber::class) + ->tag('kernel.event_subscriber', [ + 'dispatcher' => 'security.event_dispatcher.main', + ]); + }; .. _security-role-hierarchy: