In this post, I will explain how we can implement it with server-side validations and the steps involved in it.
To implement CakePhp 3 Change Password functionality in CakePHP 3 with validations, we will follow 5 steps of implementation.
I am considering the “Users” table for normal user registration and user data manipulation.
You may have a different table for your user registration purpose. But this example can be used in any table. Have a look.
Steps involve:
- Create function “changePassword” in UsersController.
- Create a new view file change_password.ctp in “Users” template folder.
- Add a form in change_password.ctp file with three fields – old_password, new_password, and confirm_password.
- Build validation rules in “UsersTable”.
- Update function “changePassword” for the form submission.
Let’s start with steps implementation.
Step 1: Create function “changePassword” in UsersController.
Add function “changePassword” in your UsersController with the initial code as below:
public function changePassword() { $user = $this->Users->get($this->Auth->user('id')); $this->set('user',$user); }
Here we have to fetch current user and send it to the form which will appear in change_password.ctp.
Step 2: Create a new view file change_password.ctp in “Users” template folder.
Go to Template->Users and create change_password.ctp in “Users” template folder.
Step 3: Add form in change_password.ctp file with three fields – old_password, new_password, and confirm_password.
Note: Don’t forget to add “$user” in “$this->Form->create()”, this is necessary to identify explicitly by validator that the form submitted in for Users table. If $user not added then it may possible that validation messages for form fields would not get displayed.
Step 4: Build validation rules in “UsersTable” for CakePHP 3 Change Password form.
Add below code in “UsersTable” for custom validation for change password form fields.
public function validationPassword(Validator $validator) { $validator ->add('old_password','custom',[ 'rule' => function($value, $context){ $user = $this->get($context['data']['id']); if($user) { if((new CakeAuthDefaultPasswordHasher)->check($value, $user->password)) { return true; } } return false; }, 'message' => 'Your old password does not match the entered password!', ]) ->notEmpty('old_password'); $validator ->add('new_password',[ 'length' => [ 'rule' => ['minLength',4], 'message' => 'Please enter atleast 4 characters in password your password.' ] ]) ->add('new_password',[ 'match' => [ 'rule' => ['compareWith','confirm_password'], 'message' => 'Sorry! Password dose not match. Please try again!' ] ]) ->notEmpty('new_password'); $validator ->add('confirm_password',[ 'length' => [ 'rule' => ['minLength',4], 'message' => 'Please enter atleast 4 characters in password your password.' ] ]) ->add('confirm_password',[ 'match' => [ 'rule' => ['compareWith','new_password'], 'message' => 'Sorry! Password dose not match. Please try again!' ] ]) ->notEmpty('confirm_password'); return $validator; }
Above code will do two important validations, apart from default validations and those are:
- Checking old_passwod entered is correctly matching the password present in the database for a current user. It also uses DefaultPasswordHasher for converting plain password to the hashed password.
- Checking new_password and confirm_password are equal or not.
Step 5: Update function “changePassword” for the form submission.
In this final step we will update “changePassword” function with below code:
public function changePassword() { $user = $this->Users->get($this->Auth->user('id')); if(!empty($this->request->data)) { $user = $this->Users->patchEntity($user, [ 'old_password' => $this->request->data['old_password'], 'password' => $this->request->data['new_password'], 'new_password' => $this->request->data['new_password'], 'confirm_password' => $this->request->data['confirm_password'] ], ['validate' => 'password'] ); if($this->Users->save($user)) { $this->Flash->success('Your password has been changed successfully'); //Email code $this->redirect(['action'=>'view']); } else { $this->Flash->error('Error changing password. Please try again!'); } } $this->set('user',$user); }
Here we have used patchEntity method to store form submitted data. Also note that we have used “[‘validate’ => ‘password’] here. This will call the custom validator method “validationPassword” we have implemented in “UsersTable”.
Here naming convention is important, for method name “validationPassword” we have used ‘password’ in [‘validate’ => ‘password’], same will apply if you use another method name like, “validationEmail”, then use [‘validate’ => ’email’], etc.
That’s it. Now try to run functionality of change password and test your code.