@@ -41,7 +41,7 @@ value and then a User object is created::
4141 // $apiKey = $request->headers->get('apikey');
4242
4343 if (!$apiKey) {
44- throw new BadCredentialsException('No API key found' );
44+ throw new BadCredentialsException();
4545
4646 // or to just skip api key authentication
4747 // return null;
@@ -54,6 +54,11 @@ value and then a User object is created::
5454 );
5555 }
5656
57+ public function supportsToken(TokenInterface $token, $providerKey)
58+ {
59+ return $token instanceof PreAuthenticatedToken && $token->getProviderKey() === $providerKey;
60+ }
61+
5762 public function authenticateToken(TokenInterface $token, UserProviderInterface $userProvider, $providerKey)
5863 {
5964 if (!$userProvider instanceof ApiKeyUserProvider) {
@@ -83,16 +88,11 @@ value and then a User object is created::
8388 $user->getRoles()
8489 );
8590 }
86-
87- public function supportsToken(TokenInterface $token, $providerKey)
88- {
89- return $token instanceof PreAuthenticatedToken && $token->getProviderKey() === $providerKey;
90- }
9191 }
9292
9393Once you've :ref: `configured <cookbook-security-api-key-config >` everything,
9494you'll be able to authenticate by adding an apikey parameter to the query
95- string, like ``http://example.com/admin /foo?apikey=37b51d194a7513e45b56f6524f2d51f2 ``.
95+ string, like ``http://example.com/api /foo?apikey=37b51d194a7513e45b56f6524f2d51f2 ``.
9696
9797The authentication process has several steps, and your implementation will
9898probably differ:
@@ -177,7 +177,7 @@ The ``$userProvider`` might look something like this::
177177 null,
178178 // the roles for the user - you may choose to determine
179179 // these dynamically somehow based on the user
180- array('ROLE_USER ')
180+ array('ROLE_API ')
181181 );
182182 }
183183
@@ -249,6 +249,7 @@ would allow you to have custom data on the ``User`` object.
249249
250250Finally, just make sure that ``supportsClass() `` returns ``true `` for User
251251objects with the same class as whatever user you return in ``loadUserByUsername() ``.
252+
252253If your authentication is stateless like in this example (i.e. you expect
253254the user to send the API key with every request and so you don't save the
254255login to the session), then you can simply throw the ``UnsupportedUserException ``
@@ -262,7 +263,7 @@ exception in ``refreshUser()``.
262263Handling Authentication Failure
263264-------------------------------
264265
265- In order for your ``ApiKeyAuthenticator `` to correctly display a 403
266+ In order for your ``ApiKeyAuthenticator `` to correctly display a 401
266267http status when either bad credentials or authentication fails you will
267268need to implement the :class: `Symfony\\ Component\\ Security\\ Http\\ Authentication\\ AuthenticationFailureHandlerInterface ` on your
268269Authenticator. This will provide a method ``onAuthenticationFailure `` which
@@ -285,7 +286,7 @@ you can use to create an error ``Response``.
285286
286287 public function onAuthenticationFailure(Request $request, AuthenticationException $exception)
287288 {
288- return new Response("Authentication Failed.", 403 );
289+ return new Response("Authentication Failed.", 401 );
289290 }
290291 }
291292
@@ -353,7 +354,7 @@ using the ``simple_preauth`` and ``provider`` keys respectively:
353354
354355 firewalls :
355356 secured_area :
356- pattern : ^/admin
357+ pattern : ^/api
357358 stateless : true
358359 simple_preauth :
359360 authenticator : apikey_authenticator
@@ -376,7 +377,7 @@ using the ``simple_preauth`` and ``provider`` keys respectively:
376377 <!-- ... -->
377378
378379 <firewall name =" secured_area"
379- pattern =" ^/admin "
380+ pattern =" ^/api "
380381 stateless =" true"
381382 provider =" api_key_user_provider"
382383 >
@@ -396,7 +397,7 @@ using the ``simple_preauth`` and ``provider`` keys respectively:
396397 $container->loadFromExtension('security', array(
397398 'firewalls' => array(
398399 'secured_area' => array(
399- 'pattern' => '^/admin ',
400+ 'pattern' => '^/api ',
400401 'stateless' => true,
401402 'simple_preauth' => array(
402403 'authenticator' => 'apikey_authenticator',
@@ -411,6 +412,44 @@ using the ``simple_preauth`` and ``provider`` keys respectively:
411412 ),
412413 ));
413414
415+ If you have defined ``access_control ``, make sure to add a new entry:
416+
417+ .. configuration-block ::
418+
419+ .. code-block :: yaml
420+
421+ # app/config/security.yml
422+ security :
423+ # ...
424+
425+ access_control :
426+ - { path: ^/api, roles: ROLE_API }
427+
428+ .. code-block :: xml
429+
430+ <!-- app/config/security.xml -->
431+ <?xml version =" 1.0" encoding =" UTF-8" ?>
432+ <srv : container xmlns =" http://symfony.com/schema/dic/security"
433+ xmlns : xsi =" http://www.w3.org/2001/XMLSchema-instance"
434+ xmlns : srv =" http://symfony.com/schema/dic/services"
435+ xsi : schemaLocation =" http://symfony.com/schema/dic/services
436+ http://symfony.com/schema/dic/services/services-1.0.xsd" >
437+
438+ <rule path =" ^/api" role =" ROLE_API" />
439+ </srv : container >
440+
441+ .. code-block :: php
442+
443+ // app/config/security.php
444+ $container->loadFromExtension('security', array(
445+ 'access_control' => array(
446+ array(
447+ 'path' => '^/api',
448+ 'role' => 'ROLE_API',
449+ ),
450+ ),
451+ ));
452+
414453 That's it! Now, your ``ApiKeyAuthenticator `` should be called at the beginning
415454of each request and your authentication process will take place.
416455
@@ -443,7 +482,7 @@ configuration or set it to ``false``:
443482
444483 firewalls :
445484 secured_area :
446- pattern : ^/admin
485+ pattern : ^/api
447486 stateless : false
448487 simple_preauth :
449488 authenticator : apikey_authenticator
@@ -466,7 +505,7 @@ configuration or set it to ``false``:
466505 <!-- ... -->
467506
468507 <firewall name =" secured_area"
469- pattern =" ^/admin "
508+ pattern =" ^/api "
470509 stateless =" false"
471510 provider =" api_key_user_provider"
472511 >
@@ -485,7 +524,7 @@ configuration or set it to ``false``:
485524 $container->loadFromExtension('security', array(
486525 'firewalls' => array(
487526 'secured_area' => array(
488- 'pattern' => '^/admin ',
527+ 'pattern' => '^/api ',
489528 'stateless' => false,
490529 'simple_preauth' => array(
491530 'authenticator' => 'apikey_authenticator',
0 commit comments