[security] "security.authentication.success" event should be fired on every request? #21571

Open
MacDada opened this Issue Feb 8, 2017 · 3 comments

Projects

None yet

4 participants

@MacDada
Contributor
MacDada commented Feb 8, 2017

At least that's what the docs say: https://symfony.com/doc/2.8/components/security/authentication.html#authentication-success-and-failure-events

When a provider authenticates the user, a security.authentication.success event is dispatched. But beware - this event will fire, for example, on every request if you have session-based authentication.

The problem is, it doesn't fire for me (?) on Symfony 2.8.12.

Not sure if this is a problem with Symfony, with my code/configuration or just the documentation.

My config (I've cut off what I think are irrelevant parts):

#security.yml
security:

    providers:
        orm:
            entity:
                class: AppBundle:User
                property: username

    firewalls:
        # disables authentication for assets and the profiler, adapt it according to your needs
        dev:
            pattern:  ^/(_(profiler|wdt)|css|images|js)/
            security: false

        default:
            anonymous: ~
            provider: orm

            form_login:
                login_path: user_login
                check_path: user_login_check
                success_handler: security_login_success_handler
                target_path_parameter: relocate

            remember_me:
                lifetime: 604800 # 1 week in seconds
                always_remember_me: true

    access_control:
        #- { path: ^/login, roles: IS_AUTHENTICATED_ANONYMOUSLY, requires_channel: https }
#config.yml
framework:
    session:
        handler_id:  session.handler.memcached
        cookie_domain: '%auth_cookies_domain%'
@chalasr
Contributor
chalasr commented Feb 8, 2017

Actually this event is fired only when submitting credentials, no matter if the firewall is stateless or not.
Still not sure if it's a bug in the code or in the doc but, given InteractiveLoginEvent seems to be dispatched only when the authentication occurs because valid credentials are passed to the request, maybe AuthenticationSuccessEvent should indeed be triggered each time session is used?

Related to #20305.

@iltar
Contributor
iltar commented Feb 9, 2017

@MacDada in your config here you don't have any authorization enforcing authentication, not even an anonymous enforcer (commented out). If you add that, does it work?

@MacDada
Contributor
MacDada commented Feb 17, 2017 edited

in your config here you don't have any authorization enforcing authentication

@iltar So what? Authentication !== Authorization. Why would I need any "authorization" check for "security.authentication.success" event to work?

BTW, I actually do have authorization configured – but on the controller level, not on the firewall level.

not even an anonymous enforcer (commented out)

If I required ROLE_USER, ROLE_ADMIN, etc on every path, then I'd need to uncomment that for login form to work. But I don't.

https://symfony.com/doc/2.8/security/form_login_setup.html#be-sure-the-login-page-isn-t-secure-redirect-loop


Anyway, I did a bit more debugging. It really is "strange". Notice that I use memcached to store sessions and do testing while being authenticated from remember me cookie. I check if the event is fired with a breakpoint here.


Scenario one: no authorization requirements in firewall and controller.

  1. clear Symfony cache
  2. restart nginx+php+memcached
  3. fresh request: event gets fired
  4. next request: event does not get fired
  5. clear Symfony cache
  6. request: event does not get fired
  7. restart nginx+php+memcached
  8. request: event does not get fired

So… I need to dump both Symfony cache and sessions storage for the event to fire. But dumping one of them is not enough…


Scenario two: IS_AUTHENTICATED_ANONYMOUSLY role required in firewall authorization.

#security.yml
security:
    access_control:
        - { path: ^/, roles: IS_AUTHENTICATED_ANONYMOUSLY }

Test and result same as above.


Scenario three: IS_AUTHENTICATED_ANONYMOUSLY role required in controller authorization.

<?php

namespace AppBundle\Controller;

use Sensio\Bundle\FrameworkExtraBundle\Configuration\Route;
use Sensio\Bundle\FrameworkExtraBundle\Configuration\Security;
use Symfony\Bundle\FrameworkBundle\Controller\Controller;
use Symfony\Component\HttpFoundation\Request;

class HomepageController extends Controller
{
	/**
	 * @Route("/", name="homepage")
	 * @Security("is_granted('IS_AUTHENTICATED_ANONYMOUSLY')")
	 *
	 * @param Request $request
	 * @return \Symfony\Component\HttpFoundation\Response
	 */
	public function homepageAction(Request $request)
	{

Test and result same as above.


Scenario four: IS_AUTHENTICATED_ANONYMOUSLY role required both in firewall and controller authorization.

Test and result same as above.


???

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment