我执行了make:crud为实体用户生成一些文件的命令。
一切都像一种魅力,但我在编辑用户时遇到了一个问题。当我编辑用户时,我可以:
或者
从生成的用户“编辑”控制器:
/**
* @Route("/{id}/edit", name="user_edit", methods={"GET","POST"})
*/
public function edit(Request $request, User $user): Response
{
$form = $this->createForm(UserType::class, $user);
$form->handleRequest($request);
if ($form->isSubmitted() && $form->isValid()) {
// HERE : How can I check if the password was changed ?
$this->getDoctrine()->getManager()->flush();
return $this->redirectToRoute('user_index', [
'id' => $user->getId(),
]);
}
return $this->render('user/edit.html.twig', [
'user' => $user,
'form' => $form->createView(),
'title' => 'edit userr'
]);
}
Run Code Online (Sandbox Code Playgroud)
如何检查密码是否已更改?用户变量包含新密码值...
如果密码是新的,我必须使用编码器服务。如果没有,我只需要用新数据更新用户
为此,在您的用户中有一个未写入数据库的类变量会有所帮助。在您的表单中,您可以使用此变量临时存储更新后的密码,然后对其进行编码和删除。这就是eraseCredentials()UserInterface 中-method 的用途。
例如在您的用户中,您可以拥有
class User implements UserInterface
{
private $plainPassword;
// ...
public function setPlainPassword(string $plainPassword)
{
$this->plainPassword = $plainPassword;
}
public function getPlainPassword()
{
return $this->plainPassword;
}
public function eraseCredentials()
{
$this->plainPassword = null;
}
}
Run Code Online (Sandbox Code Playgroud)
注意private $plainPassword没有任何 ORM 注释,这意味着它不会存储在数据库中。但是,您可以使用验证约束,例如,如果您想确保密码具有最小长度或一定的复杂性。您仍然需要存储加密密码的原始密码字段。
然后将此字段添加到用户更新表单而不是实际的密码字段。在您的控制器中,您只能检查是否填写了新的普通密码字段,然后读取该值,对其进行编码并替换实际的密码字段。
if ($form->isSubmitted() && $form->isValid()) {
$user = $form->getData();
if ($user->getPlainPassword() !== null) {
$user->setPassword($this->userPasswordEncoder->encode(
$user->getPlainPassword(),
$user
);
}
// ...
Run Code Online (Sandbox Code Playgroud)
执行此操作的另一种方法是使用未映射的表单字段,而不向用户添加此“帮助程序”属性:
# UserForm
public function buildForm(FormBuilderInterface $builder, array $options)
{
$builder
// ...
->add('plainPassword', PasswordType::class, ['mapped' => false])
;
}
Run Code Online (Sandbox Code Playgroud)
控制器看起来很相似,只是您从未映射的字段而不是从用户获取数据:
$form->get('plainPassword')->getData();
Run Code Online (Sandbox Code Playgroud)