开发者

Is there a better way to change user password in cakephp using Auth?

I am learning cakephp by myself. I tried to create a user controller with a changepassword function. It works, but I am not sure if this is the best way, and I could not googled up useful tutorials on this. Here is my code:

class UsersController extends AppController {

    var $name = 'Users';

    function login() {
    }

    function l开发者_如何学编程ogout() {
        $this->redirect($this->Auth->logout());
    }

    function changepassword() {
        $session=$this->Session->read();
        $id=$session['Auth']['User']['id'];
        $user=$this->User->find('first',array('conditions' => array('id' => $id)));
        $this->set('user',$user);
        if (!empty($this->data)) {
            if ($this->Auth->password($this->data['User']['password'])==$user['User']['password']) {
                if ($this->data['User']['passwordn']==$this->data['User']['password2']) {
                // Passwords match, continue processing
                $data=$this->data;
                $this->data=$user;
                $this->data['User']['password']=$this->Auth->password($data['User']['passwordn']);
                $this->User->id=$id;
                $this->User->save($this->data);
                $this->Session->setFlash('Password changed.');
                $this->redirect(array('controller'=>'Toners','action' => 'index'));
                } else {
                    $this->Session->setFlash('New passwords differ.');
                    }
            } else {
                $this->Session->setFlash('Typed passwords did not match.');
            }
        }
    }
}

password is the old password, passwordn is the new one, password2 is the new one retyped. Is there any other, more coomon way to do it in cake?


I see that you validate and manipulate data in the controller. Doing this in a model is generally a better practice. I implemented similar functionality just a few days ago. My change_password() method looks somewhat like this:

# app/controllers/users_controller.php
function change_password() {
    if (!empty($this->data)) {
        if ($this->User->save($this->data)) {
            $this->Session->setFlash('Password has been changed.');
            // call $this->redirect() here
        } else {
            $this->Session->setFlash('Password could not be changed.');
        }
    } else {
        $this->data = $this->User->findById($this->Auth->user('id'));
    }
}

And here's a stripped down version of the view used with that method:

# app/views/users/change_password.ctp
echo $this->Form->create('User');
echo $this->Form->input('id');
echo $this->Form->input('current_password');
echo $this->Form->input('password1');
echo $this->Form->input('password2');
echo $this->Form->end('Submit');

The code that does something interesting is in the model. I added the fields from the form to the validate property and wrote custom validation methods. This allows me to use password1 and password2 fields in any other place in the application, for example, on the registration form.

# app/models/user.php
var $validate = array(
    'current_password' => array(
        'rule' => 'checkCurrentPassword',
        'message' => '...'
    ),
    'password1' => array(
        'rule' => 'checkPasswordStrength',
        'message' => '...',
    ),
    'password2' => array(
        'rule' => 'passwordsMatch',
        'message' => '...',
    )
);

Finally, in the beforeSave() callback of the model I set password to the hash of password1 to prepare the data to be stored it in the database.


The solution provided by Mike is great, but he left out the "checkCurrentPassword" function. Here is an example of that function you can place in your Model:

# app/models/user.php
public function checkCurrentPassword($data) {
    $this->id = AuthComponent::user('id');
    $password = $this->field('password');
    return(AuthComponent::password($data['current_password']) == $password);
}

This solution gets the current user ID from the Auth component and changes the model to point to that particular user. Then it compares the hash of the current_password entered on the form with the hashed password stored for that user.

Also, here is the beforeSave function you can use to hash the new password:

# app/models/user.php
public function beforeSave($options = array()) {
    if (isset($this->data[$this->alias]['password1'])) {
        $this->data[$this->alias]['password'] = AuthComponent::password($this->data[$this->alias]['password1']);
    }       
    return true;
}


You can use the latest version of the cakeDC plugin. This plugin gives you all functionality of all functions related to login, logout, reset password, change password, etc. You can find the latest version here.


You can simply use the:-

Step1)

$password = $this->Auth->password($this->data['User']['password']); // It will generate the hashed password using the cakephp's Auth component.

Step2)

if($this->User->update(array('User.password'=>$password), array('User.id'=>$this->Auth->User('id')))) {
     echo $this->Session->setFlash('Password changed successfully.', 'default',   
     array('class'=>'successMsg'));
}
0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜