diff --git a/app/Http/Controllers/AccountController.php b/app/Http/Controllers/AccountController.php index 87423c5aa..980dd4dcd 100644 --- a/app/Http/Controllers/AccountController.php +++ b/app/Http/Controllers/AccountController.php @@ -339,6 +339,11 @@ class AccountController extends Controller $request->session()->push('2fa.session.active', true); return redirect('/'); } else { + + if($this->twoFactorBackupCheck($request, $code, $user)) { + return redirect('/'); + } + if($request->session()->has('2fa.attempts')) { $count = (int) $request->session()->has('2fa.attempts'); $request->session()->push('2fa.attempts', $count + 1); @@ -350,4 +355,31 @@ class AccountController extends Controller ]); } } + + protected function twoFactorBackupCheck($request, $code, User $user) + { + $backupCodes = $user->{'2fa_backup_codes'}; + if($backupCodes) { + $codes = json_decode($backupCodes, true); + foreach ($codes as $c) { + if(hash_equals($c, $code)) { + // remove code + $codes = array_flatten(array_diff($codes, [$code])); + $user->{'2fa_backup_codes'} = json_encode($codes); + $user->save(); + $request->session()->push('2fa.session.active', true); + return true; + } else { + return false; + } + } + } else { + return false; + } + } + + public function accountRestored(Request $request) + { + // + } } diff --git a/app/Http/Controllers/Settings/SecuritySettings.php b/app/Http/Controllers/Settings/SecuritySettings.php index 99547b73b..5d1c49ad3 100644 --- a/app/Http/Controllers/Settings/SecuritySettings.php +++ b/app/Http/Controllers/Settings/SecuritySettings.php @@ -110,6 +110,19 @@ trait SecuritySettings return view('settings.security.2fa.recovery-codes', compact('user', 'codes')); } + public function securityTwoFactorRecoveryCodesRegenerate(Request $request) + { + $user = Auth::user(); + + if(!$user->{'2fa_enabled'} || !$user->{'2fa_secret'}) { + abort(403); + } + $backups = $this->generateBackupCodes(); + $user->{'2fa_backup_codes'} = json_encode($backups); + $user->save(); + return redirect(route('settings.security.2fa.recovery')); + } + public function securityTwoFactorUpdate(Request $request) { $user = Auth::user(); diff --git a/config/pixelfed.php b/config/pixelfed.php index 419e38e02..25c9c0870 100644 --- a/config/pixelfed.php +++ b/config/pixelfed.php @@ -23,7 +23,7 @@ return [ | This value is the version of your PixelFed instance. | */ - 'version' => '0.7.5', + 'version' => '0.7.6', /* |-------------------------------------------------------------------------- diff --git a/resources/views/settings/security/2fa/recovery-codes.blade.php b/resources/views/settings/security/2fa/recovery-codes.blade.php index 47f37af29..9b6c61e4a 100644 --- a/resources/views/settings/security/2fa/recovery-codes.blade.php +++ b/resources/views/settings/security/2fa/recovery-codes.blade.php @@ -7,16 +7,26 @@
- Each code can only be used once. -
- - -{{$code}}
+ Each code can only be used once. +
+{{$code}}
Generate more recovery codes and store them in a safe place.
++
+ +