6

在我的应用程序中,只有管理员用户可以创建和理论上可以编辑用户。到目前为止,仅使用 Symfony 安全系统(没有 FOSUserBundle 管理 - 它的复杂性不是必需的),创建具有不同角色的用户就可以了。完全逃脱我的挑战是如何在不知道用户密码的情况下编辑用户。我一直遇到预期的验证错误

密码不能为空

. 如何完成编辑?我肯定在这里遗漏了一些非常基本的东西。

编辑动作:

    public function editAction($id) {
        $em = $this->getDoctrine()->getManager();
        $user = $em->getRepository('ManaClientBundle:User')->find($id);
        $form = $this->createForm(new UserType(), $user);
        return array(
            'form' => $form->createView(),
            'user' => $user,
            'title' => 'Edit user',
            );
   }

更新动作:

   public function updateAction(Request $request, $id) {
        $em = $this->getDoctrine()->getManager();
        $user = $em->getRepository('ManaClientBundle:User')->find($id);
        $originalPassword = $user->getPassword();
        $form = $this->createForm(new UserType(), $user);
        $form->bind($request);
        if ($form->isValid()) {
            $plainPassword = $form->get('password')->getData();
            if (!empty($plainPassword))  {  
                //encode the password   
                $encoder = $this->container->get('security.encoder_factory')->getEncoder($entity); //get encoder for hashing pwd later
                $tempPassword = $encoder->encodePassword($entity->getPassword(), $entity->getSalt()); 
                $user->setPassword($tempPassword);                
            }
            else {
                $user->setPassword($originalPassword);
            }
            $em->persist($user);
            $em->flush();
            return $this->redirect($this->generateUrl('user_main', array()));
        }        

用户表格:

public function buildForm(FormBuilderInterface $builder, array $options) {
    $builder
            ->add('enabled', 'choice', array(
                'choices' => array('Yes' => 'Yes', 'No' => 'No'),
                'expanded' => true,
                'multiple' => false,
                'label' => 'Enabled: ',
            ))
            ->add('fname')
            ->add('sname')
            ->add('email')
            ->add('username')
            ->add('password', 'repeated', array(
                'type' => 'password',
                'invalid_message' => 'Password fields do not match',
                'first_options' => array('label' => 'Password'),
                'second_options' => array('label' => 'Repeat Password'),
            ))
            ->add('role', 'choice', array(
                'choices' => array('ROLE_USER' => 'User', 'ROLE_ADMIN' => 'Admin'),
                'expanded' => true,
                'multiple' => false,
                'label' => 'Group: ',
            ))
    ;
}
4

4 回答 4

8

在我看到更优雅的解决方案之前,这就是我想出的:

  1. 创建一个包含除密码字段之外的所有字段的 UserEditType 表单类
  2. 将 UserEditType 分配给 Default 以外的验证组
  3. 为2中的验证组配置密码长度约束。
  4. 修改编辑和更新操作以使用 UserEditType

现在无需密码即可编辑用户!

用户编辑类型:

class UserEditType extends AbstractType {
    public function buildForm(FormBuilderInterface $builder, array $options) {
        $builder
                ->add('enabled', 'choice', array(
                    'choices' => array('Yes' => 'Yes', 'No' => 'No'),
                    'expanded' => true,
                    'multiple' => false,
                    'label' => 'Enabled: ',
                ))
                ->add('fname')
                ->add('sname')
                ->add('email')
                ->add('username')
                ->add('role', 'choice', array(
                    'choices' => array('ROLE_USER' => 'User', 'ROLE_ADMIN' => 'Admin'),
                    'expanded' => true,
                    'multiple' => false,
                    'label' => 'Group: ',
                ))
        ;
    }

    public function setDefaultOptions(OptionsResolverInterface $resolver) {
        $resolver->setDefaults(array(
            'data_class' => 'Mana\ClientBundle\Entity\User',
            'validation_groups' => array('edit'),
        ));
    }

用户实体中的密码:

 * @ORM\Column(name="userpass", type="string", length=100, nullable=false)
 * @Assert\NotBlank(message="Password may not be empty")
 * @Assert\Length(
 *      min = "5",
 *      max = "12",
 *      minMessage = "Password must be at least 5 characters long",
 *      maxMessage = "Password cannot be longer than than 12 characters",
 *      groups = {"Default"}
 * )

更新动作:

public function updateAction(Request $request, $id) {
    $em = $this->getDoctrine()->getManager();
    $user = $em->getRepository('ManaClientBundle:User')->find($id);

    $form = $this->createForm(new UserEditType(), $user);
    $form->bind($request);
    if ($form->isValid()) {
        $em->persist($user);
        $em->flush();
        return $this->redirect($this->generateUrl('user_main', array()));
    }
    return array(
        'form' => $form->createView(),
        'user' => $user,
        'title' => 'Edit user',
    );
}
于 2013-04-07T00:34:17.750 回答
6

我在我的项目中遇到了同样的问题。

我通过从表单中删除密码字段来解决它,只是为了我的编辑操作。

所以,在我的UserController,我改变了editAction

//find the line where the form is created
$editForm = $this->createForm(new UserType($this->container), $entity)
        ->remove('password'); //add this to remove the password field
于 2013-08-26T18:24:09.097 回答
0

如果您想使用该remove()功能,则也适用于表单设置。至少在 Symfony 3.3 中。这样,您将避免上述密码确认@pusle

        $form = $this->formFactory->createForm()->remove("current_password");
        $form->setData($user)->remove("current_password");

这里是 FOSUserBundle 的 ProfileController 中的整个方法。这个对我有用:


public function editDiffAction($id, Request $request)
    {
        $userManager = $this->get('fos_user.user_manager');
        $user = $userManager->findUserBy(['id' => $id]);

        $event = new GetResponseUserEvent($user, $request);

        if (null !== $event->getResponse()) {
            return $event->getResponse();
        }

        $form = $this->formFactory->createForm()->remove("current_password");
        $form->setData($user)->remove("current_password");

        $form->handleRequest($request);

        if ($form->isValid()) {
            $event = new FormEvent($form, $request);

            $userManager = $this->get('fos_user.user_manager');
            $userManager->updateUser($user);

            $url = $this->generateUrl('fos_user_profile_show_diff', array('id' => $user->getId() ));
            $response = new RedirectResponse($url);

            return $response;
        }

        return $this->render('@FOSUser/Profile/edit_diff.html.twig', array(
            'form' => $form->createView(),
            'user_id' => $user->getId(),
        ));
    }
于 2019-01-22T14:45:25.840 回答
-1

只需添加 'disabled' => 'disabled' 并不会考虑此字段。

于 2016-10-05T19:26:01.163 回答