symfonysymfony-2.1shibbolethsymfony-security

Symfony 2 Custom User Provider


I'm trying to get ShibbolethBundle (https://github.com/rmoreas/ShibbolethBundle) work. But stuck with creating a new user on login. I found out that the userProvider is not the correct class (the one that implements ShibbolethUserProviderInterface on here https://github.com/rmoreas/ShibbolethBundle/blob/master/Security/ShibbolethAuthProvider.php#L109

My custom provider is defined like this:

namespace Meot\FormBundle\Entity;
...
class UserRepository extends EntityRepository implements ShibbolethUserProviderInterface {
...
}

Security.xml

....
security:
     providers:
         main_provider:
             entity: { class: Meot\FormBundle\Entity\User }

     firewalls:
         dev:
             pattern:  ^/(_(profiler|wdt)|css|images|js)/
             security: false
         secured_area:
             pattern:    ^/
             shibboleth: ~
             logout:
                 path: /logout
                 target: /
                 success_handler: security.logout.handler.shibboleth

I found this cookbook (http://symfony.com/doc/current/cookbook/security/entity_provider.html) states

To finish the implementation, the configuration of the security layer must be changed to tell Symfony to use the new custom entity provider instead of the generic Doctrine entity provider. It's trivial to achieve by removing the property field in the security.providers.administrators.entity section of the security.yml file.

Tried it, didn't work. The class of user provider is still Symfony\Bridge\Doctrine\Security\User\EntityUserProvider.

I'm wondering by removing the property field, how Symfony is able to find my custom user provider?

Thanks.


Solution

  • I figured it out. It seems the DI container just create "EntityUserProvider" when specified "entity" in provider in security.xml. Then the AuthenticationProvider just call the methods in user provider. So I have to create a service for the user provider and specify ID in providers section in security.xml.

    src/Meot/FormBundle/Resources/config/services.xml

    <parameters>
        <parameter key="custom_user_provider.class">Meot\FormBundle\Entity\UserRepository</parameter>
        <parameter key="custom_user_entity">Meot\FormBundle\Entity\User</parameter>
    </parameters>
    <services>
        <service id="custom_user_provider" class="%custom_user_provider.class%"
            factory-service="doctrine" factory-method="getRepository">
            <argument>%custom_user_entity%</argument>
        </service>
    </services>