Search code examples
symfonysonata-admin

SecurityToken null in Sonata Admin class


I have a problem with getting the logged in user in and Admin class. What I would like to do is to restrict a choice field to logged in users organization (so that he is not able to pick another organization when creating an event). Therefore I've injected TokenStorage into my CalendarAdmin, but $tokenStorage->getToken() is null even if I'm logged in. Here is my relevant code:

security.yml:

    providers:
    in_memory:
        memory: ~
    fos_userbundle:
        id: fos_user.user_manager

    admin:
        pattern:            /admin(.*)
        context:            user
        form_login:
            provider:       fos_userbundle
            login_path:     /admin/login
            use_forward:    false
            check_path:     /admin/login_check
            failure_path:   null
        logout:
            path:           /admin/logout
        anonymous:          true

services.yml:

    pozsonyba.calendar_bundle.admin.calendar:
    class: Pozsonyba\Bundle\CalendarBundle\Admin\CalendarAdmin
    arguments: [~, Pozsonyba\Bundle\CalendarBundle\Entity\Calendar, SonataAdminBundle:CRUD, @security.token_storage, @pozsonyba_organization.repository.organization_repository]
    tags:
        - {name: sonata.admin, manager_type: orm, group: admin, label: Calendar}

I read that this security.yml might have been set up wrong, that the firewall is missing something, I just can't figure out what.

Thank you for help. CalendarAdmin.php:

    public function __construct($code, $class, $baseControllerName, TokenStorage $tokenStorage, OrganizationRepository $organizationRepository)
    {
        parent::__construct($code, $class, $baseControllerName);

        VarDumper::dump($tokenStorage->getToken());die;
        $this->organizationRepository = $organizationRepository;
    }

Solution

  • Check out the \Sonata\AdminBundle\Admin\AbstractAdmin class. You can get access to the container and the token storage via the configuration pool:

    $this->getConfigurationPool()->getContainer()->get('security.token_storage')->getToken()->getUser()
    

    I guess, the token is not set when the admin object is created, so as an alternative way you can try to inject the TokenStorage via setter injection:

    # CalendarAdmin.php
    /** @var  TokenStorageInterface */
    private $tokenStorage;
    
    /**
     * @param TokenStorageInterface $tokenStorage
     */
    public function setTokenStorage($tokenStorage)
    {
        $this->tokenStorage = $tokenStorage;
    }
    

    update services definition

    # services.yml
    pozsonyba.calendar_bundle.admin.calendar:
        class: Pozsonyba\Bundle\CalendarBundle\Admin\CalendarAdmin
        arguments: [~, Pozsonyba\Bundle\CalendarBundle\Entity\Calendar, SonataAdminBundle:CRUD, @security.token_storage, @pozsonyba_organization.repository.organization_repository]
        calls: 
            - [setTokenStorage, ["@security.token_storage"]]
        tags:
            - {name: sonata.admin, manager_type: orm, group: admin, label: Calendar}