8000 [SecurityBundle] Register the UsernamePasswordJsonAuthenticationListe… · symfony/symfony@653bebb · GitHub
[go: up one dir, main page]

Skip to content

Commit 653bebb

Browse files
committed
[SecurityBundle] Register the UsernamePasswordJsonAuthenticationListener class
1 parent f9ad5c9 commit 653bebb

File tree

12 files changed

+395
-50
lines changed

12 files changed

+395
-50
lines changed
Lines changed: 96 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,96 @@
1+
<?php
2+
3+
/*
4+
* This file is part of the Symfony package.
5+
*
6+
* (c) Fabien Potencier <fabien@symfony.com>
7+
*
8+
* For the full copyright and license information, please view the LICENSE
9+
* file that was distributed with this source code.
10+
*/
11+
12+
namespace Symfony\Bundle\SecurityBundle\DependencyInjection\Security\Factory;
13+
14+
use Symfony\Component\DependencyInjection\ContainerBuilder;
15+
use Symfony\Component\DependencyInjection\DefinitionDecorator;
16+
use Symfony\Component\DependencyInjection\Reference;
17+
18+
/**
19+
* JsonLoginFactory creates services for JSON login authentication.
20+
*
21+
* @author Kévin Dunglas <dunglas@gmail.com>
22+
*/
23+
class JsonLoginFactory extends AbstractFactory
24+
{
25+
public function __construct()
26+
{
27+
$this->addOption('username_path', 'username');
28+
$this->addOption('password_path', 'password');
29+
}
30+
31+
/**
32+
* {@inheritdoc}
33+
*/
34+
public function getPosition()
35+
{
36+
return 'form';
37+
}
38+
39+
/**
40+
* {@inheritdoc}
41+
*/
42+
public function getKey()
43+
{
44+
return 'json-login';
45+
}
46+
47+
/**
48+
* {@inheritdoc}
49+
*/
50+
protected function createAuthProvider(ContainerBuilder $container, $id, $config, $userProviderId)
51+
{
52+
$provider = 'security.authentication.provider.dao.'.$id;
53+
$container
54+
->setDefinition($provider, new DefinitionDecorator('security.authentication.provider.dao'))
55+
->replaceArgument(0, new Reference($userProviderId))
56+
->replaceArgument(1, new Reference('security.user_checker.'.$id))
57+
->replaceArgument(2, $id)
58+
;
59+
60+
return $provider;
61+
}
62+
63+
/**
64+
* {@inheritdoc}
65+
*/
66+
protected function getListenerId()
67+
{
68+
return 'security.authentication.listener.json';
69+
}
70+
71+
/**
72+
* {@inheritdoc}
73+
*/
74+
protected function isRememberMeAware($config)
75+
{
76+
return false;
77+
}
78+
79+
/**
80+
* {@inheritdoc}
81+
*/
82+
protected function createListener($container, $id, $config, $userProvider)
83+
{
84+
$listenerId = $this->getListenerId();
85+
$listener = new DefinitionDecorator($listenerId);
86+
$listener->replaceArgument(2, $id);
87+
$listener->replaceArgument(3, new Reference($this->createAuthenticationSuccessHandler($container, $id, $config)));
88+
$listener->replaceArgument(4, new Reference($this->createAuthenticationFailureHandler($container, $id, $config)));
89+
$listener->replaceArgument(5, array_intersect_key($config, $this->options));
90+
91+
$listenerId .= '.'.$id;
92+
$container->setDefinition($listenerId, $listener);
93+
94+
return $listenerId;
95+
}
96+
}

src/Symfony/Bundle/SecurityBundle/Resources/config/security_listeners.xml

Lines changed: 14 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -140,7 +140,20 @@
140140
<argument /> <!-- x509 user -->
141141
<argument /> <!-- x509 credentials -->
142142
<argument type="service" id="logger" on-invalid="null" />
143-
<argument type="service" id="event_dispatcher" on-invalid="null"/>
143+
<argument type="service" id="event_dispatcher" on-invalid="null" />
144+
</service>
145+
146+
<service id="security.authentication.listener.json" class="Symfony\Component\Security\Http\Firewall\UsernamePasswordJsonAuthenticationListener" public="false" abstract="true">
147+
<tag name="monolog.logger" channel="security" />
148+
<argument type="service" id="security.token_storage" />
149+
<argument type="service" id="security.authentication.manager" />
150+
<argument /> <!-- Provider-shared Key -->
151+
<argument type="service" id="security.authentication.success_handler" />
152+
<argument type="service" id="security.authentication.failure_handler" />
153+
<argument type="collection" /> <!-- Options -->
154+
<argument type="service" id="logger" on-invalid="null" />
155+
<argument type="service" id="event_dispatcher" on-invalid="null" />
156+
<argument type="service" id="property_accessor" on-invalid="null" />
144157
</service>
145158

146159
<service id="security.authentication.listener.remote_user" class="Symfony\Component\Security\Http\Firewall\RemoteUserAuthenticationListener" public="false" abstract="true">

src/Symfony/Bundle/SecurityBundle/SecurityBundle.php

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@
1111

1212
namespace Symfony\Bundle\SecurityBundle;
1313

14+
use Symfony\Bundle\SecurityBundle\DependencyInjection\Security\Factory\JsonLoginFactory;
1415
use Symfony\Component\HttpKernel\Bundle\Bundle;
1516
use Symfony\Component\DependencyInjection\ContainerBuilder;
1617
use Symfony\Bundle\SecurityBundle\DependencyInjection\Compiler\AddSecurityVotersPass;
@@ -42,6 +43,7 @@ public function build(ContainerBuilder $container)
4243
$extension = $container->getExtension('security');
4344
$extension->addSecurityListenerFactory(new FormLoginFactory());
4445
$extension->addSecurityListenerFactory(new FormLoginLdapFactory());
46+
$extension->addSecurityListenerFactory(new JsonLoginFactory());
4547
$extension->addSecurityListenerFactory(new HttpBasicFactory());
4648
$extension->addSecurityListenerFactory(new HttpBasicLdapFactory());
4749
$extension->addSecurityListenerFactory(new HttpDigestFactory());
Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
<?php
2+
3+
/*
4+
* This file is part of the Symfony package.
5+
*
6+
* (c) Fabien Potencier <fabien@symfony.com>
7+
*
8+
* For the full copyright and license information, please view the LICENSE
9+
* file that was distributed with this source code.
10+
*/
11+
12+
namespace Symfony\Bundle\SecurityBundle\Tests\Functional\Bundle\JsonLoginBundle\Controller;
13+
14+
/**
15+
* @author Kévin Dunglas <dunglas@gmail.com>
16+
*/
17+
class TestController
18+
{
19+
public function loginCheckAction()
20+
{
21+
throw new \RuntimeException(sprintf('%s should never be called.', __FUNCTION__));
22+
}
23+
}
Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
<?php
2+
3+
/*
4+
* This file is part of the Symfony package.
5+
*
6+
* (c) Fabien Potencier <fabien@symfony.com>
7+
*
8+
* For the full copyright and license information, please view the LICENSE
9+
* file that was distributed with this source code.
10+
*/
11+
12+
namespace Symfony\Bundle\SecurityBundle\Tests\Functional\Bundle\JsonLoginBundle;
13+
14+
use Symfony\Component\HttpKernel\Bundle\Bundle;
15+
16+
/**
17+
* @author Kévin Dunglas <dunglas@gmail.com>
18+
*/
19+
class JsonLoginBundle extends Bundle
20+
{
21+
}
Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,32 @@
1+
<?php
2+
3+
/*
4+
* This file is part of the Symfony package.
5+
*
6+
* (c) Fabien Potencier <fabien@symfony.com>
7+
*
8+
* For the full copyright and license information, please view the LICENSE
9+
* file that was distributed with this source code.
10+
*/
11+
12+
namespace Symfony\Bundle\SecurityBundle\Tests\Functional;
13+
14+
/**
15+
* @author Kévin Dunglas <dunglas@gmail.com>
16+
*/
17+
class JsonLoginTest extends WebTestCase
18+
{
19+
public function testJsonLoginSuccess()
20+
{
21+
$client = $this->createClient(array('test_case' => 'JsonLogin', 'root_config' => 'config.yml'));
22+
$client->request('POST', '/login_check', array(), array(), array(), '{"username": "dunglas", "password": "foo"}');
23+
$this->assertEquals('http://localhost/', $client->getResponse()->headers->get('location'));
24+
}
25+
26+
public function testJsonLoginFailure()
27+
{
28+
$client = $this->createClient(array('test_case' => 'JsonLogin', 'root_config' => 'config.yml'));
29+
$client->request('POST', '/login_check', array(), array(), array(), '{"username": "dunglas", "password": "bad"}');
30+
$this->assertEquals('http://localhost/login', $client->getResponse()->headers->get('location'));
31+
}
32+
}
Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
<?php
2+
3+
/*
4+
* This file is part of the Symfony package.
5+
*
6+
* (c) Fabien Potencier <fabien@symfony.com>
7+
*
8+
* For the full copyright and license information, please view the LICENSE
9+
* file that was distributed with this source code.
10+
*/
11+
12+
return array(
13+
new Symfony\Bundle\SecurityBundle\SecurityBundle(),
14+
new Symfony\Bundle\FrameworkBundle\FrameworkBundle(),
15+
new Symfony\Bundle\SecurityBundle\Tests\Functional\Bundle\JsonLoginBundle\JsonLoginBundle(),
16+
);
Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
imports:
2+
- { resource: ./../config/framework.yml }
3+
4+
security:
5+
encoders:
6+
Symfony\Component\Security\Core\User\User: plaintext
7+
8+
providers:
9+
in_memory:
10+
memory:
11+
users:
12+
dunglas: { password: foo, roles: [ROLE_USER] }
13+
14+
firewalls:
15+
main:
16+
pattern: ^/
17+
anonymous: true
18+
json_login: ~
19+
20+
access_control:
21+
- { path: ^/foo, roles: ROLE_USER }
Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
login_check:
2+
path: /login_check
3+
defaults: { _controller: JsonLoginBundle:Test:loginCheck }

src/Symfony/Bundle/SecurityBundle/composer.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,7 @@
1717
],
1818
"require": {
1919
"php": ">=5.5.9",
20-
"symfony/security": "~3.1,>=3.1.2",
20+
"symfony/security": "~3.2",
2121
"symfony/http-kernel": "~3.1",
2222
"symfony/polyfill-php70": "~1.0"
2323
},

0 commit comments

Comments
 (0)
0