Salar
Salar

Reputation: 5499

laravel 5,update User password

I'm using laravel 5 to develop an app that allow every user to update his profile.
in order to update password, the user needs to first enter his old password and if the old password matched then his newly entered password will be hashed and stored in DB. how can I validate this, using laravel form request validation?

Upvotes: 6

Views: 5783

Answers (3)

Salar
Salar

Reputation: 5499

I created a custom validator and added it to AppServiceProvider like this:

<?php

namespace App\Providers;

use Validator;
use Illuminate\Support\ServiceProvider;
use Illuminate\Support\Facades\Hash ;
class AppServiceProvider extends ServiceProvider
{
    /**
     * Bootstrap any application services.
     *
     * @return void
     */
    public function boot()
    {
        Validator::extend('password_hash_check', function($attribute, $value, $parameters, $validator) {
            return Hash::check($value , $parameters[0]) ;
        });
    }

then I used it in my form request validator like this:

<?php
namespace App\Http\Requests;
use App\Http\Requests\Request;
class UpdateUserProfileRequest extends Request
{
    /**
     * Get the validation rules that apply to the request.
     *
     * @return array
     */
    public function rules()
    {
        $hashed_password = $this->user()->password ;
        return [
            'oldPassword'=> "password_hash_check:$hashed_password|string|min:6",
            'newPassword' => 'required_with:oldPassword|confirmed|min:6',
        ];
    }

Upvotes: 4

Anatoliy Arkhipov
Anatoliy Arkhipov

Reputation: 691

I'm not sure but I think that there is no native way to do this in Laravel. If so, you can implement a custom "hash" validator:

class CustomValidator extends \Illuminate\Validation\Validator {

    public function validateHash($attribute, $value, $parameters)
    {
        $expected = $parameters[0];

        return Hash::check($value, $expected);
    }
}

Register it in a provider:

class AppServiceProvider extends ServiceProvider {

    /**
     * Bootstrap any application services.
     *
     * @return void
     */
    public function boot()
    {
        require_once __DIR__ . '/../Http/helpers.php';

        Validator::resolver(function($translator, $data, $rules, $messages)
        {
            return new CustomValidator($translator, $data, $rules, $messages);
        });
    }

    // ...
}

And use it in a form request:

class MyFormRequest extends FormRequest {

    public function rules()
    {
        $password = Auth::user()->password;

        return [
            'old_password' => "required|hash:" . $password
        ]
    }

    // ...

}

Link to documentation: http://laravel.com/docs/5.0/validation#custom-validation-rules

Upvotes: 3

Rajesh kumawat
Rajesh kumawat

Reputation: 180

When you want to check a Hashed value generated by

Hash::make()

you need to use

Hash::check('unhashed', $hashed)

Every time you run Hash::make('string'), a different hash is made and will not match the previous one. For example:

// Generate a hash
$password = Hash::make('password');

// $password == $2y$08$T9r9qUxrr6ejs9Ne.nLzMet8l0A8BM5QvLjhaaJasgsbMBdX4JjRu

// Generate a new hash
$new_password = Hash::make('password');

// $new_password ==  $2y$08$3KBlYKIMpIvk.TWwim9oPuwGA.Pzv1iF7BsDyYkz7kQlhkA/ueULe

// Compare hashes the WRONG way
$password === $new_password; // false

// Compare hash the RIGHT way
Hash::check('password', $password); // true
Hash::check('password', $new_password); // true 

So Use Hash::make() method of Hash class.

Upvotes: 3

Related Questions