by default the password reset token emailed to email is different from one being saved to database. I have used the Hasher::make() and hash_hmac('sha256', $token, env('APP_KEY')) to hash that and then compare that token to database but invain. what should i do to transform emailed token to database token or compare them?
I also tried
public function convertToken($token)
{
if (Str::startsWith($key = env('APP_KEY'), 'base64:')) {
$key = base64_decode(substr($key, 7));
}
return hash_hmac('sha256', $token, $key);
}
The Hasher used by the Laravel default implementation can be retrieved with
$hasher = Password::broker()->getRepository()->getHasher();
You can then hash your token to add them to your database like this :
$hasher->make($token);
And you can check a token against the value stored in your database with this code :
$hasher->check($token, $databaseToken);
But why do you want to implement yourself what Laravel team has already done ? You'd better use Laravel default authentication, unless you do this for fun.
Related
I'm trying to use the Laravel passport and I don't know if I found a bug or I'm missing something.
Login controller:
$user = $request->user();
$tokenResult = $user->createToken('Personal Access Token');
$token = $tokenResult->token;
$token->expires_at = Carbon::now()->addWeeks(1);
$token->save();
So I'm creating the token when an user login. On the database I see that the generated token has expires_at field: one week after so it's correct.
But if I change this value for an older date I can still use this token...
Laravel is simply ignoring this field? Why?
I did my research but I'm a bit confused... so many people says tokens don't expire or expire in 1 year. But then I found some posts with this snippet:
public function boot(){
$this->registerPolicies();
Passport::routes();
Passport::tokensExpireIn(Carbon::now()->addHours(24));
Passport::refreshTokensExpireIn(Carbon::now()->addDays(30));
}
I understand tokensExpireIn sets the expires_at field and refreshTokensExpireIn is for refresh this field everytime the user uses his token...
But if Laravel does not check this field anyway, it's no use.
You can also set the expiration date for personal tokens
Passport::personalAccessTokensExpireIn(now()->addMonths(1));
You will also need to regenerate your tokens as old will still have their expiration dates.
When a user forgets their password and try to reset it, they get a reset password email link with a token:
site.com/my/password/reset/ddc3669ab1bbd78abe620ef910716ae91678bb4beb5cd8896e21efaaa0c9d5c6
On the backend though, the token in the database password_resets table looks like it's hashed:
$2y$10$O6pgU21FhsOcgpgeqR8RReFYoCGhHNBH5bHKxtE6q1tJMTUufrbr.
So when the route is visited, the only piece of identifying information passed is the token:
ddc3669ab1bbd78abe620ef910716ae91678bb4beb5cd8896e21efaaa0c9d5c6
// Controller Method
passwordResetVerifyByToken($token){
$record = DB::table('password_resets')->where('token', $token)
->first();
}
Ofcourse we won't get a record, as the plain token from the email will NOT match the hashed one in the database with the above query. So with the plain emailed token link, when the user clicks it, how can we compare it to the one in the database to verify it exists and is a matching token?
You should use the Hash::check method, which will return true or false depending of if the hash of the reset token matches the stored database value.
if (Hash::check($token, $row->token)) {
// The passwords match...
}
Laravel docs:
https://laravel.com/docs/5.6/hashing#basic-usage
Dont worry Laravel Have there own advanced function Hash you should try this
if (Hash::check($token, $row->token)) {
// write your code or other function
}
jwt token works perfectly with user model.
jwt tokens works perfectly with environment variable's.
Using both scenario 1 and 2 in one system.
I want to generate jwt token using environment variable's email and password which are not stored in user table and also I don't want to change the existing flow of jwt token.
I want to generate JWT token for master user who is not part of system and his email and password are not stored in database.
Is there any way to generate jwt token using both user model and environment variable's??
I have got the solution.
We can create token using JWT::encode.
Here the sample code is :
$customClaims = ['foo' => 'bar', 'baz' => 'bob'];
$factory = JWTFactory::customClaims($customClaims);
$payload = $factory->make();
$token = JWTAuth::encode($payload);
I've got an issue when I try to validate the post password via Hash::check in Laravel 5.5
I made a posts table (in this case sales table) with password column. When I try to create the post, it's working perfectly and the password is hashed and also belongs to logged in User. Then on the current post page is a button with an input (password) to delete that specific post, but the condition is always false.
My Controller public function destroy(Request $request, $id)
$input_pass = request('input_password');
$sale = Sale::find($id);
$hashed = $sale->password;
// Check if sale password is correct
if (Hash::check($input_pass, $sale->password)) {
$sale->delete();
} else {
// something else to do
}
For the post store, I used bcrypt method to hash the password. I've been also trying to dd('sale->password') which refers to column in sales table (correct) and dd('$input_pass') which refers to typed in password in DELETE form (also correct) - so I'm a little bit confused, why the pass don't match.
From your comment I find that you have a logical error where you initially hash your password and persist it in DB.
You are passing the string password to bcrypt where it should actually be something like request('password')
Change
'password' => bcrypt('password'),
to
'password' => bcrypt(request('password')),
I am using tymon/jwt-auth liibrary for JWT authentication in my project which is built using laravel.
In my mysql users table I am having a role_id column. I want to include that in my generated JWT token's claim on login so that I can implement role based ACL using my JWT token on subsquent requests.
Below is what I have tried to get it working
$credentials = $request->only('email', 'password');
$userModel = User::where('email',$request->input('email'))->get()->first();
$role = $userModel->roles_id;
$customClaim = ['role' => $role];
try
{
// attempt to verify the credentials and create a token for the user
if (! $token = JWTAuth::attempt($credentials, $customClaim))
{
//return 401 error
}
}
catch (JWTException $e)
{
//return 500 error
}
return response()->json(compact('token'));
}
Above code is working fine as expected but problem with above code is on login I have to hit my database twice once for getting role and one for authenticating user. That would be great if someone can suggest a better way to do it in a single database hit.