【问题标题】:Symfony how to change user password with SonataAdmin?Symfony 如何使用 SonataAdmin 更改用户密码?
【发布时间】:2019-08-23 07:56:48
【问题描述】:

我有一个用于登录管理员页面的 Admin 类,它实现了UserInterface

**
 * @ORM\Entity(repositoryClass="App\Repository\AdminRepository")
 */
class Admin implements UserInterface
{
...
}

security.yaml中作为用户提供者的实体:

security:
    providers:
        app_user_provider:
            entity:
                class: App\Entity\Admin
                property: username

此管理员提供程序用于在不使用 FOSUserBundle 的情况下登录 SonataAdmin 页面

我创建了一个AdminAdmin 类,用于在 SonataAdmin 中更新/创建管理员用户:

final class AdminAdmin extends AbstractAdmin
{

}

但是在 SonataAdmin 中没有关于如何更新用户密码的教程,所以我决定更改 Admin 实体中的setPassword

/**
 * @ORM\Entity(repositoryClass="App\Repository\AdminRepository")
 */
class Admin implements UserInterface

{
    public function __construct(UserPasswordEncoderInterface $passwordEncoder)
    {
        $this->passwordEncoder = $passwordEncoder;
    }

    public function setPassword(string $password): self
    {
        dd($this->passwordEncoder);
        $this->password = $this->passwordEncoder->encodePassword($this, $password);

        return $this;
    }
}

如上所示,我尝试使用 UserPasswordEncoderInterface 来编码密码,但问题是passwordEncoder 为空,无法将 UserPasswordEncoderInterface 服务注入到 Admin 实体。

那么用 SonataAdmin 更新用户密码的正确方法是什么

【问题讨论】:

  • 现在遇到同样的问题,希望您能找到解决办法。
  • 请检查新答案

标签: symfony sonata-admin


【解决方案1】:

我找到了一种破解方法:

创建一个 AdminAdminController 扩展 CRUDController,

final class AdminAdminController extends CRUDController
{
    /**
     * @var UserPasswordEncoderInterface
     */
    private $passwordEncode;

    public function __construct(UserPasswordEncoderInterface $passwordEncode)
    {
        $this->passwordEncode = $passwordEncode;
    }


    public function editAction($id = null)
    {
        $existingObject = $this->admin->getObject($id);

        $uniqid = $this->getRequest()->query->get('uniqid');
        $formData = $this->getRequest()->request->get($uniqid);

        if ($formData['password']['first'] ===  $formData['password']['second']){
            $enPass = $this->passwordEncode->encodePassword($existingObject, $formData['password']['first']);
            $formData['password'] = [
                'first' => $enPass,
                'second' => $enPass
            ];
            $this->getRequest()->request->set($uniqid, $formData);
            return parent::editAction($id);
        }else{
            return parent::editAction($id);
        }
    }

但我还是想知道如何在实体中更改用户密码,简单又干。

【讨论】:

    【解决方案2】:

    首先,实体不应该有依赖,所以你需要移除实体中的依赖注入。

    在您的AdminAdmin(混淆名称)中,您需要像这样添加密码字段:

    ->add('plainPassword', RepeatedType::class, [
        'type' => PasswordType::class,
        'options' => [
            'translation_domain' => 'FOSUserBundle',
        ],
        'first_options' => ['label' => 'form.password'],
        'second_options' => ['label' => 'form.password_confirmation'],
        'invalid_message' => 'fos_user.password.mismatch',
        'required' => true,
    ])
    

    您需要将UserManager 依赖注入到您的管理类中,如下所示:

    private $userManager;
    
    public function __construct($code, $class, $baseControllerName, UserManagerInterface $userManager)
    {
        $this->userManager = $userManager;
    
        parent::__construct($code, $class, $baseControllerName);
    }
    

    这可能会出错,因为它无法自动连接依赖项,请将此行添加到您的管理员定义下的admin.yamlautowire: true

    最后将preUpdate() 方法添加到您的管理类中:

    public function preUpdate($object)
    {
        parent::preUpdate($object);
    
        if ($object->getPlainPassword()) {
            $this->userManager->updatePassword($object);
        }
    }
    

    现在应该可以正确更新密码了。

    【讨论】:

    • 感谢您的回复,但我没有将 FOSUserBundle 用于 SonataAdmin
    猜你喜欢
    • 1970-01-01
    • 2012-09-25
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多