Search code examples
symfonybackendsonata-admin

Avoid empty password field when edit a specific user with SonataAdminBundle


I have a problem when I want to edit an existing user from the Backend (using SonataAdminBundle and FOSUserBundle). In configureFormFields method of my UserAdmin class, the password field appears empty and this is a problem when I need to edit another fields (for example the lastname) keeping the same user password. This field (and the password verification field) must be filled again! (I do not want modify the user password)

In my UserAdmin class, I have:

public function configureFormFields(FormMapper $formMapper)
{
        $formMapper
            ->with('User Data')
                ->add('username')

                ->add('plainPassword', 'repeated', array(
                'type' => 'password',
                'options' => array('translation_domain' => 'FOSUserBundle'),
                'first_options' => array('label' => 'form.password'),
                'second_options' => array('label' => 'form.password_confirmation'),
                'invalid_message' => 'fos_user.password.mismatch',
                )) 

                ->add('firstname')
                ->add('lastname')
                ->add('email')
                ->add('user_roles')
                ->add('enabled', 'checkbox', array(
                      'label'     => 'Enable Account',
                      'required'  => false,
                ))
            ->end()
        ;
}

I tried to overwrite prePersist and preUpdate methods in my UserAdmin class, but these do not work. The password is encripted in the database following the FOS standard (with salt and sha512).

Any solution? Many thanks!


Solution

  • You can override your the preUpdate function in your admin class this is how i have done

    public function preUpdate($object)
        {
            $DM = $this->getConfigurationPool()->getContainer()->get('Doctrine')->getManager();
            $repository = $DM->getRepository('Namespace\YourBundle\Entity\User')->find($object->getId());
    
            $Password = $object->getPassword();
            if (!empty($Password)) {
                $salt = md5(time());
    
                $encoderservice = $this->getConfigurationPool()->getContainer()->get('security.encoder_factory');
                $encoder = $encoderservice->getEncoder($object);
                $encoded_pass = $encoder->encodePassword($object->getPassword(), $salt);
                $object->setSalt($salt);
                $object->setPassword($encoded_pass);
            } else {
                $object->setPassword($repository->getPassword());
            }
        }
    

    And my configureFormFields function

    protected function configureFormFields(FormMapper $formMapper)
    {
        $passwordoptions=array('type' => 'password','invalid_message' => 'The password fields must match.',
                   'options' => array('attr' => array('class' => 'password-field')),'first_options' => array('label' => 'Password'),
            'second_options' => array('label' => 'Confirm password'),'translation_domain' => 'FOSUserBundle'
               );
    
        $this->record_id = $this->request->get($this->getIdParameter());
         if (!empty($this->record_id)) {
             $passwordoptions['required'] = false;
             $passwordoptions['constraints'] = array(new Assert\Length(array('min' => 10))
                                 ,new Assert\Regex(array('pattern' => '/^(?=.*?[A-Z])(?=.*?[a-z])(?=.*?[0-9])(?=.*?[#?!@$%^&*-]).{10,}$/','match'=>true,'message'=>'Password must contain atleast 1 special character 1 upper case letter 1 number and 1 lower case letter !'))
                                 );
         } else {
            $passwordoptions['required'] = true;
            $passwordoptions['constraints'] = array(new Assert\Length(array('min' => 10))
                                ,new Assert\Regex(array('pattern' => '/^(?=.*?[A-Z])(?=.*?[a-z])(?=.*?[0-9])(?=.*?[#?!@$%^&*-]).{10,}$/','match'=>true,'message'=>'Password must contain atleast 1 special character 1 upper case letter 1 number and 1 lower case letter !'))
                                );
         }
      $formMapper->add('password', 'repeated', $passwordoptions); /*you can add your other fields*/
      }