Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Understanding Symfony/FOSUserBundle Authentication - How is fos_user_security_check handled

Tags:

I am trying to understand the how authentication (user + password) is handled in Symfony 2.8 when using the FOSUserBundle. The setup was no problem and everything works fine, I just want to understand HOW it work.

The login form post username + password to the fos_user_security_check route (/login_check) which is defined in FOSUserBunde\Resources\config\routing\security.xml:

<route id="fos_user_security_check" path="/login_check" methods="POST">
    <default key="_controller">FOSUserBundle:Security:check</default>
</route>

So the FOSUserBundle:Security:check action is responsible for handling the request. However the implementation looks like this:

public function checkAction() {
    throw new \RuntimeException('You must configure the check path to be handled by the firewall using form_login in your security firewall configuration.');
}

So I looked at the firewall config in /app/config/security.yml:

security:
    ...
    firewalls:
        ...
        main:
            ...

            form_login:
                provider: fos_userbundle
                csrf_provider: security.csrf.token_manager
                login_path: fos_user_security_login
                check_path: fos_user_security_check

Here check_path also referes to fos_user_security_check... So, where is the authentication actually handeled?

like image 912
Andrei Herford Avatar asked Jul 10 '17 14:07

Andrei Herford


1 Answers

The authentication isn't handled inside the FOSUserBundle, it is just providing some basic parameters as well as a provider for how to retrieve the user from the database (fos_userbundle).

You'll want to look at Symfony\Component\Security\Http\Firewall\AbstractAuthenticationListener for some basics about what happens on authentication failure and success. You can look at Symfony\Component\Security\Http\Firewall\UsernamePasswordFormAuthenticationListener and the attemptAuthentication() method there, and follow along there to the authentication manager service that calls authenticate().

You will eventually get to Symfony\Component\Security\Core\Encoder\UserPasswordEncoder and the isPasswordValid() function, which checks whatever encoder you have (probably Symfony\Component\Security\Core\Encoder\BCryptPasswordEncoder) which eventually calls PHP's password_verify function.

The reason why you see that Controller action in the way that you do, is that you should never be calling login_check directly. Hence, if you got there, something has been mis-configured, which is why the exception is thrown. See the check_path variable in the documentation, and this Stackoverflow answer for more information about that.

like image 107
Jason Roman Avatar answered Oct 13 '22 11:10

Jason Roman