From e28b477d703137dd997a457b655f004ac4b0aa31 Mon Sep 17 00:00:00 2001 From: Sacha Corazzi Date: Mon, 3 Jun 2024 12:40:12 +0100 Subject: [PATCH] Destroy a recovery code when used. --- src/Pages/TwoFactorPage.php | 5 +++++ src/Traits/TwoFactorAuthenticatable.php | 9 +++++++++ 2 files changed, 14 insertions(+) diff --git a/src/Pages/TwoFactorPage.php b/src/Pages/TwoFactorPage.php index f715a54..3ed55a0 100644 --- a/src/Pages/TwoFactorPage.php +++ b/src/Pages/TwoFactorPage.php @@ -130,6 +130,11 @@ public function authenticate() return null; } + // If using a recovery code, unset it so it can only be used once + if ($this->usingRecoveryCode) { + filament('filament-breezy')->auth()->user()->destroyRecoveryCode($this->code); + } + // If it makes it to the bottom, we're going to set the session var and send them to the dashboard. filament('filament-breezy')->auth()->user()->setTwoFactorSession(); diff --git a/src/Traits/TwoFactorAuthenticatable.php b/src/Traits/TwoFactorAuthenticatable.php index 4163d1c..d66f281 100644 --- a/src/Traits/TwoFactorAuthenticatable.php +++ b/src/Traits/TwoFactorAuthenticatable.php @@ -99,6 +99,15 @@ public function generateRecoveryCodes() })->all())); } + public function destroyRecoveryCode(string $recoveryCode): void + { + $unusedCodes = array_filter($this->two_factor_recovery_codes ?? [], fn ($code) => $code !== $recoveryCode); + + $this->breezy_session->forceFill([ + 'two_factor_recovery_codes' => $unusedCodes ? encrypt(json_encode($unusedCodes)) : null, + ])->save(); + } + public function getTwoFactorQrCodeUrl() { return filament('filament-breezy')->getQrCodeUrl(