From eeaf21bb98f02ed6a5c5eb2b09528c1a111a8c6d Mon Sep 17 00:00:00 2001 From: Reinier Kip Date: Wed, 5 Nov 2014 14:40:47 +0100 Subject: [PATCH 1/2] Prove that custom entry point isn't started with unknown credentials. --- .../FirewallEntryPointExtension.php | 26 ++++++++++ .../FirewallEntryPointBundle.php | 18 +++++++ .../Resources/config/services.xml | 10 ++++ .../Security/EntryPointStub.php | 27 ++++++++++ .../Functional/FirewallEntryPointTest.php | 51 +++++++++++++++++++ .../app/FirewallEntryPoint/bundles.php | 7 +++ .../app/FirewallEntryPoint/config.yml | 33 ++++++++++++ .../app/FirewallEntryPoint/routing.yml | 2 + 8 files changed, 174 insertions(+) create mode 100644 src/Symfony/Bundle/SecurityBundle/Tests/Functional/Bundle/FirewallEntryPointBundle/DependencyInjection/FirewallEntryPointExtension.php create mode 100644 src/Symfony/Bundle/SecurityBundle/Tests/Functional/Bundle/FirewallEntryPointBundle/FirewallEntryPointBundle.php create mode 100644 src/Symfony/Bundle/SecurityBundle/Tests/Functional/Bundle/FirewallEntryPointBundle/Resources/config/services.xml create mode 100644 src/Symfony/Bundle/SecurityBundle/Tests/Functional/Bundle/FirewallEntryPointBundle/Security/EntryPointStub.php create mode 100644 src/Symfony/Bundle/SecurityBundle/Tests/Functional/FirewallEntryPointTest.php create mode 100644 src/Symfony/Bundle/SecurityBundle/Tests/Functional/app/FirewallEntryPoint/bundles.php create mode 100644 src/Symfony/Bundle/SecurityBundle/Tests/Functional/app/FirewallEntryPoint/config.yml create mode 100644 src/Symfony/Bundle/SecurityBundle/Tests/Functional/app/FirewallEntryPoint/routing.yml diff --git a/src/Symfony/Bundle/SecurityBundle/Tests/Functional/Bundle/FirewallEntryPointBundle/DependencyInjection/FirewallEntryPointExtension.php b/src/Symfony/Bundle/SecurityBundle/Tests/Functional/Bundle/FirewallEntryPointBundle/DependencyInjection/FirewallEntryPointExtension.php new file mode 100644 index 0000000000000..e4d5bc30f39f9 --- /dev/null +++ b/src/Symfony/Bundle/SecurityBundle/Tests/Functional/Bundle/FirewallEntryPointBundle/DependencyInjection/FirewallEntryPointExtension.php @@ -0,0 +1,26 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Bundle\SecurityBundle\Tests\Functional\Bundle\FirewallEntryPointBundle\DependencyInjection; + +use Symfony\Component\Config\FileLocator; +use Symfony\Component\DependencyInjection\ContainerBuilder; +use Symfony\Component\DependencyInjection\Loader\XmlFileLoader; +use Symfony\Component\HttpKernel\DependencyInjection\Extension; + +class FirewallEntryPointExtension extends Extension +{ + public function load(array $config, ContainerBuilder $container) + { + $loader = new XmlFileLoader($container, new FileLocator(__DIR__.'/../Resources/config')); + $loader->load('services.xml'); + } +} diff --git a/src/Symfony/Bundle/SecurityBundle/Tests/Functional/Bundle/FirewallEntryPointBundle/FirewallEntryPointBundle.php b/src/Symfony/Bundle/SecurityBundle/Tests/Functional/Bundle/FirewallEntryPointBundle/FirewallEntryPointBundle.php new file mode 100644 index 0000000000000..f4247ad050db6 --- /dev/null +++ b/src/Symfony/Bundle/SecurityBundle/Tests/Functional/Bundle/FirewallEntryPointBundle/FirewallEntryPointBundle.php @@ -0,0 +1,18 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Bundle\SecurityBundle\Tests\Functional\Bundle\FirewallEntryPointBundle; + +use Symfony\Component\HttpKernel\Bundle\Bundle; + +class FirewallEntryPointBundle extends Bundle +{ +} diff --git a/src/Symfony/Bundle/SecurityBundle/Tests/Functional/Bundle/FirewallEntryPointBundle/Resources/config/services.xml b/src/Symfony/Bundle/SecurityBundle/Tests/Functional/Bundle/FirewallEntryPointBundle/Resources/config/services.xml new file mode 100644 index 0000000000000..76abc3d262e93 --- /dev/null +++ b/src/Symfony/Bundle/SecurityBundle/Tests/Functional/Bundle/FirewallEntryPointBundle/Resources/config/services.xml @@ -0,0 +1,10 @@ + + + + + + diff --git a/src/Symfony/Bundle/SecurityBundle/Tests/Functional/Bundle/FirewallEntryPointBundle/Security/EntryPointStub.php b/src/Symfony/Bundle/SecurityBundle/Tests/Functional/Bundle/FirewallEntryPointBundle/Security/EntryPointStub.php new file mode 100644 index 0000000000000..e1d3280570d88 --- /dev/null +++ b/src/Symfony/Bundle/SecurityBundle/Tests/Functional/Bundle/FirewallEntryPointBundle/Security/EntryPointStub.php @@ -0,0 +1,27 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Bundle\SecurityBundle\Tests\Functional\Bundle\FirewallEntryPointBundle\Security; + +use Symfony\Component\HttpFoundation\Request; +use Symfony\Component\HttpFoundation\Response; +use Symfony\Component\Security\Core\Exception\AuthenticationException; +use Symfony\Component\Security\Http\EntryPoint\AuthenticationEntryPointInterface; + +class EntryPointStub implements AuthenticationEntryPointInterface +{ + const RESPONSE_TEXT = '2be8e651259189d841a19eecdf37e771e2431741'; + + public function start(Request $request, AuthenticationException $authException = null) + { + return new Response(self::RESPONSE_TEXT); + } +} diff --git a/src/Symfony/Bundle/SecurityBundle/Tests/Functional/FirewallEntryPointTest.php b/src/Symfony/Bundle/SecurityBundle/Tests/Functional/FirewallEntryPointTest.php new file mode 100644 index 0000000000000..23acde45a5ff9 --- /dev/null +++ b/src/Symfony/Bundle/SecurityBundle/Tests/Functional/FirewallEntryPointTest.php @@ -0,0 +1,51 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Bundle\SecurityBundle\Tests\Functional; + +use Symfony\Bundle\SecurityBundle\Tests\Functional\Bundle\FirewallEntryPointBundle\Security\EntryPointStub; + +/** + * @group functional + */ +class FirewallEntryPointTest extends WebTestCase +{ + public function testItUsesTheConfiguredEntryPointWhenUsingUnknownCredentials() + { + $client = $this->createClient(array('test_case' => 'FirewallEntryPoint')); + $client->insulate(); + + $client->request('GET', '/secure/resource', array(), array(), array( + 'PHP_AUTH_USER' => 'unknown', + 'PHP_AUTH_PW' => 'credentials', + )); + + $this->assertEquals( + EntryPointStub::RESPONSE_TEXT, + $client->getResponse()->getContent(), + "Custom entry point wasn't started" + ); + } + + protected function setUp() + { + parent::setUp(); + + $this->deleteTmpDir('FirewallEntryPoint'); + } + + protected function tearDown() + { + parent::tearDown(); + + $this->deleteTmpDir('FirewallEntryPoint'); + } +} diff --git a/src/Symfony/Bundle/SecurityBundle/Tests/Functional/app/FirewallEntryPoint/bundles.php b/src/Symfony/Bundle/SecurityBundle/Tests/Functional/app/FirewallEntryPoint/bundles.php new file mode 100644 index 0000000000000..c6fd207dd1118 --- /dev/null +++ b/src/Symfony/Bundle/SecurityBundle/Tests/Functional/app/FirewallEntryPoint/bundles.php @@ -0,0 +1,7 @@ + Date: Thu, 23 Oct 2014 09:27:11 +0200 Subject: [PATCH 2/2] Ensure the configured entry point is used in the auth listeners I had configured a different firewall entry point for one firewall. However, when authentication had to be performed, it still called BasicAuthenticationEntryPoint::start() instead of my service's start(). My service was instantiated, yet never used. The issue appeared to be that the entry point is registered with the firewall's exception listener, but not with the BasicAuthenticationListener. This means that when the BasicAuthenticationListener determines the user has provided wrong credentials, BasicAuthenticationEntryPoint is still used. Only in case of an exception would my entry point service be used. See symfony/symfony#12261. --- .../DependencyInjection/SecurityExtension.php | 13 +++++-------- 1 file changed, 5 insertions(+), 8 deletions(-) diff --git a/src/Symfony/Bundle/SecurityBundle/DependencyInjection/SecurityExtension.php b/src/Symfony/Bundle/SecurityBundle/DependencyInjection/SecurityExtension.php index cc45d79c70d65..b270955ea3968 100644 --- a/src/Symfony/Bundle/SecurityBundle/DependencyInjection/SecurityExtension.php +++ b/src/Symfony/Bundle/SecurityBundle/DependencyInjection/SecurityExtension.php @@ -349,8 +349,11 @@ private function createFirewall(ContainerBuilder $container, $id, $firewall, &$a ; } + // Determine default entry point + $defaultEntryPoint = isset($firewall['entry_point']) ? $firewall['entry_point'] : null; + // Authentication listeners - list($authListeners, $defaultEntryPoint) = $this->createAuthenticationListeners($container, $id, $firewall, $authenticationProviders, $defaultProvider); + list($authListeners, $defaultEntryPoint) = $this->createAuthenticationListeners($container, $id, $firewall, $authenticationProviders, $defaultProvider, $defaultEntryPoint); $listeners = array_merge($listeners, $authListeners); @@ -362,11 +365,6 @@ private function createFirewall(ContainerBuilder $container, $id, $firewall, &$a // Access listener $listeners[] = new Reference('security.access_listener'); - // Determine default entry point - if (isset($firewall['entry_point'])) { - $defaultEntryPoint = $firewall['entry_point']; - } - // Exception listener $exceptionListener = new Reference($this->createExceptionListener($container, $firewall, $id, $defaultEntryPoint)); @@ -386,11 +384,10 @@ private function createContextListener($container, $contextKey) return $this->contextListeners[$contextKey] = $listenerId; } - private function createAuthenticationListeners($container, $id, $firewall, &$authenticationProviders, $defaultProvider) + private function createAuthenticationListeners($container, $id, $firewall, &$authenticationProviders, $defaultProvider, $defaultEntryPoint) { $listeners = array(); $hasListeners = false; - $defaultEntryPoint = null; foreach ($this->listenerPositions as $position) { foreach ($this->factories[$position] as $factory) {