从 Laravel 5.3 开始,添加了这个中间件...
\Illuminate\Session\Middleware\AuthenticateSession
虽然出于安全目的这绝对是一个好处,但它还负责在用户更改密码时注销用户(向用户显示登录页面)。
在 Laravel 5.5 中,我们如何防止用户在更改密码时被注销(被迫重新登录)?
无需更改中间件,只需在更改密码后“重新登录”用户即可:
<?php
//$user->passwordChangeMagicHere()
Auth::login($user);
//And the user is logged in again!
对我有用的是注销,清除会话,然后再次登录
Auth::guard('web')->logout();
Session::flush();
Auth::guard('web')->login($this);
只是一个旁注,有时您可能需要更新会话的密码哈希。完成更新密码过程的最佳方法。
auth()->login($user, true);
$request->session()->put([
'password_hash' => $newUser->getAuthPassword(),
]);
重要的是在再次登录用户后执行此操作,否则,进一步调用
auth()->user();
将返回 null。
对于 Laravel > 8.x
当会话的 password_hash 与当前的不同时
auth()->user()
laravel 将自动注销用户。这是在这个中间件上完成的:
vendor/laravel/framework/src/Illuminate/Session/Middleware/AuthenticateSession.php
如果您使用新的哈希密码更新会话中的 password_hash,用户将不会注销。
session()->put([
'password_hash_' . auth()->getDefaultDriver() => $user->getAuthPassword()
]);
例子:
session()->put([
'password_hash_web' => "$2y$10$...hashpasswordstoredondatabase"
]);
对于 Laravel > 8.x
更好的方法:
// $user - user model after password change
auth()->setUser($user);
从 manniL(使用
Auth::login
)和 Lukmon Awoyemi(使用记住我功能)的答案得出的 Laravel 8 项目中对我有用的内容:
public function updatePassword(UpdatePasswordRequest $request) {
$user = $request->user();
$user->fill([
'password' => Hash::make($request->password),
])->save();
// make sure to re-login the user
Auth::login($user, !!$user->getRememberToken());
$request->session()->flash('status', 'Password updated!');
return redirect()->route('some.route');
}
UpdatePasswordRequest
只是一个表单请求,它验证给定的原始密码和新密码,检查提供的原始密码是否有效并确认新密码。
这里增加的是先检查一个remember token。如果没有设置记住标记,此检查将返回一个标记或
null
。此信息将转换为布尔值并提供给 login
函数。
像这样登录用户将确保在会话中更新所有必要的密码和登录哈希以匹配新密码哈希。因此,
AuthenticateSession
中间件仍会将用户识别为已登录。此外,当且仅当在密码更改之前记住了用户时,才会记住用户。
您可以使用
update
方法而不是save
来解决它:
$user = auth()->user();
$user->update([
'password' => Hash::make($data['new_password']),
]);