summaryrefslogtreecommitdiffstats
path: root/Http
diff options
context:
space:
mode:
authorJeremy Mikola <jmikola@gmail.com>2011-12-30 00:08:04 -0500
committerJeremy Mikola <jmikola@gmail.com>2012-02-14 19:03:51 -0500
commit0924bcd2ebc4ec0ad510aea6df4034bb2e716c03 (patch)
treeb3a33dd65e5c9e834f41b892e98345e3088f4a7e /Http
parent5b01ebf19827e03e4f4a86efd3f69e4bb4be023a (diff)
downloadsymfony-security-0924bcd2ebc4ec0ad510aea6df4034bb2e716c03.zip
symfony-security-0924bcd2ebc4ec0ad510aea6df4034bb2e716c03.tar.gz
symfony-security-0924bcd2ebc4ec0ad510aea6df4034bb2e716c03.tar.bz2
[Security] Allow LogoutListener to validate CSRF tokens
This adds several new options to the logout listener, modeled after the form_login listener: * csrf_parameter * intention * csrf_provider The "csrf_parameter" and "intention" have default values if omitted. By default, "csrf_provider" is empty and CSRF validation is disabled in LogoutListener (preserving BC). If a service ID is given for "csrf_provider", CSRF validation will be enabled. Invalid tokens will result in an InvalidCsrfTokenException being thrown before any logout handlers are invoked.
Diffstat (limited to 'Http')
-rw-r--r--Http/Firewall/LogoutListener.php39
1 files changed, 29 insertions, 10 deletions
diff --git a/Http/Firewall/LogoutListener.php b/Http/Firewall/LogoutListener.php
index d794457..f4d0b2c 100644
--- a/Http/Firewall/LogoutListener.php
+++ b/Http/Firewall/LogoutListener.php
@@ -11,14 +11,15 @@
namespace Symfony\Component\Security\Http\Firewall;
-use Symfony\Component\Security\Http\Logout\LogoutSuccessHandlerInterface;
-
-use Symfony\Component\Security\Http\Logout\LogoutHandlerInterface;
-use Symfony\Component\Security\Core\SecurityContextInterface;
-use Symfony\Component\Security\Http\HttpUtils;
+use Symfony\Component\Form\Extension\Csrf\CsrfProvider\CsrfProviderInterface;
use Symfony\Component\HttpFoundation\Request;
use Symfony\Component\HttpFoundation\Response;
use Symfony\Component\HttpKernel\Event\GetResponseEvent;
+use Symfony\Component\Security\Core\SecurityContextInterface;
+use Symfony\Component\Security\Core\Exception\InvalidCsrfTokenException;
+use Symfony\Component\Security\Http\HttpUtils;
+use Symfony\Component\Security\Http\Logout\LogoutHandlerInterface;
+use Symfony\Component\Security\Http\Logout\LogoutSuccessHandlerInterface;
/**
* LogoutListener logout users.
@@ -32,24 +33,29 @@ class LogoutListener implements ListenerInterface
private $handlers;
private $successHandler;
private $httpUtils;
+ private $csrfProvider;
/**
* Constructor
*
* @param SecurityContextInterface $securityContext
* @param HttpUtils $httpUtils An HttpUtilsInterface instance
- * @param array $options An array of options for the processing of a logout attempt
- * @param LogoutSuccessHandlerInterface $successHandler
+ * @param array $options An array of options to process a logout attempt
+ * @param LogoutSuccessHandlerInterface $successHandler A LogoutSuccessHandlerInterface instance
+ * @param CsrfProviderInterface $csrfProvider A CsrfProviderInterface instance
*/
- public function __construct(SecurityContextInterface $securityContext, HttpUtils $httpUtils, array $options = array(), LogoutSuccessHandlerInterface $successHandler = null)
+ public function __construct(SecurityContextInterface $securityContext, HttpUtils $httpUtils, array $options = array(), LogoutSuccessHandlerInterface $successHandler = null, CsrfProviderInterface $csrfProvider = null)
{
$this->securityContext = $securityContext;
$this->httpUtils = $httpUtils;
$this->options = array_merge(array(
- 'logout_path' => '/logout',
- 'target_url' => '/',
+ 'csrf_parameter' => '_csrf_token',
+ 'intention' => 'logout',
+ 'logout_path' => '/logout',
+ 'target_url' => '/',
), $options);
$this->successHandler = $successHandler;
+ $this->csrfProvider = $csrfProvider;
$this->handlers = array();
}
@@ -66,7 +72,12 @@ class LogoutListener implements ListenerInterface
/**
* Performs the logout if requested
*
+ * If a CsrfProviderInterface instance is available, it will be used to
+ * validate the request.
+ *
* @param GetResponseEvent $event A GetResponseEvent instance
+ * @throws InvalidCsrfTokenException if the CSRF token is invalid
+ * @throws RuntimeException if the LogoutSuccessHandlerInterface instance does not return a response
*/
public function handle(GetResponseEvent $event)
{
@@ -76,6 +87,14 @@ class LogoutListener implements ListenerInterface
return;
}
+ if (null !== $this->csrfProvider) {
+ $csrfToken = $request->get($this->options['csrf_parameter'], null, true);
+
+ if (false === $this->csrfProvider->isCsrfTokenValid($this->options['intention'], $csrfToken)) {
+ throw new InvalidCsrfTokenException('Invalid CSRF token.');
+ }
+ }
+
if (null !== $this->successHandler) {
$response = $this->successHandler->onLogoutSuccess($request);