Skip to content

Commit

Permalink
bug #28100 [Security] Call AccessListener after LogoutListener (chalasr)
Browse files Browse the repository at this point in the history
This PR was merged into the 2.8 branch.

Discussion
----------

[Security] Call AccessListener after LogoutListener

| Q             | A
| ------------- | ---
| Branch?       | 2.8
| Bug fix?      | yes
| New feature?  | no
| BC breaks?    | no
| Deprecations? | no
| Tests pass?   | yes
| Fixed tickets | #28058
| License       | MIT
| Doc PR        | n/a

Commits
-------

44dbea6 [Security] Call AccessListener after LogoutListener
  • Loading branch information
Robin Chalas committed Aug 11, 2018
2 parents 30b24d2 + 44dbea6 commit ea0b508
Show file tree
Hide file tree
Showing 7 changed files with 74 additions and 2 deletions.
10 changes: 10 additions & 0 deletions src/Symfony/Bundle/SecurityBundle/Tests/Functional/LogoutTest.php
Expand Up @@ -49,4 +49,14 @@ public function testCsrfTokensAreClearedOnLogout()

$this->assertFalse($client->getContainer()->get('security.csrf.token_storage')->hasToken('foo'));
}

public function testAccessControlDoesNotApplyOnLogout()
{
$client = $this->createClient(array('test_case' => 'LogoutAccess', 'root_config' => 'config.yml'));

$client->request('POST', '/login', array('_username' => 'johannes', '_password' => 'test'));
$client->request('GET', '/logout');

$this->assertRedirect($client->getResponse(), '/');
}
}
@@ -0,0 +1,18 @@
<?php

/*
* This file is part of the Symfony package.
*
* (c) Fabien Potencier <fabien@symfony.com>
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/

use Symfony\Bundle\FrameworkBundle\FrameworkBundle;
use Symfony\Bundle\SecurityBundle\SecurityBundle;

return array(
new FrameworkBundle(),
new SecurityBundle(),
);
@@ -0,0 +1,26 @@
imports:
- { resource: ./../config/framework.yml }

security:
encoders:
Symfony\Component\Security\Core\User\User: plaintext

providers:
in_memory:
memory:
users:
johannes: { password: test, roles: [ROLE_USER] }

firewalls:
default:
form_login:
check_path: login
remember_me: true
require_previous_session: false
logout: ~
anonymous: ~
stateless: true

access_control:
- { path: ^/login$, roles: IS_AUTHENTICATED_ANONYMOUSLY }
- { path: .*, roles: IS_AUTHENTICATED_FULLY }
@@ -0,0 +1,5 @@
login:
path: /login

logout:
path: /logout
2 changes: 1 addition & 1 deletion src/Symfony/Bundle/SecurityBundle/composer.json
Expand Up @@ -18,7 +18,7 @@
"require": {
"php": ">=5.3.9",
"ext-xml": "*",
"symfony/security": "^2.8.42|^3.4.12",
"symfony/security": "^2.8.45|^3.4.15",
"symfony/security-acl": "~2.7|~3.0.0",
"symfony/http-kernel": "~2.7|~3.0.0",
"symfony/polyfill-php70": "~1.0"
Expand Down
13 changes: 13 additions & 0 deletions src/Symfony/Component/Security/Http/Firewall.php
Expand Up @@ -16,6 +16,7 @@
use Symfony\Component\HttpKernel\Event\FinishRequestEvent;
use Symfony\Component\HttpKernel\Event\GetResponseEvent;
use Symfony\Component\HttpKernel\KernelEvents;
use Symfony\Component\Security\Http\Firewall\AccessListener;

/**
* Firewall uses a FirewallMap to register security listeners for the given
Expand Down Expand Up @@ -58,8 +59,16 @@ public function onKernelRequest(GetResponseEvent $event)
$exceptionListener->register($this->dispatcher);
}

$accessListener = null;

// initiate the listener chain
foreach ($authenticationListeners as $listener) {
if ($listener instanceof AccessListener) {
$accessListener = $listener;

continue;
}

$listener->handle($event);

if ($event->hasResponse()) {
Expand All @@ -70,6 +79,10 @@ public function onKernelRequest(GetResponseEvent $event)
if (null !== $logoutListener) {
$logoutListener->handle($event);
}

if (!$event->hasResponse() && null !== $accessListener) {
$accessListener->handle($event);
}
}

public function onKernelFinishRequest(FinishRequestEvent $event)
Expand Down
2 changes: 1 addition & 1 deletion src/Symfony/Component/Security/Http/Tests/FirewallTest.php
Expand Up @@ -79,7 +79,7 @@ public function testOnKernelRequestStopsWhenThereIsAResponse()
->getMock()
;
$event
->expects($this->once())
->expects($this->at(0))
->method('hasResponse')
->will($this->returnValue(true))
;
Expand Down

0 comments on commit ea0b508

Please sign in to comment.