forked from Alex/Pterodactyl-Panel
Fix logic when generating recovery codes and update migration
This commit is contained in:
parent
a998b463e3
commit
c522935403
@ -6,6 +6,7 @@ use Carbon\Carbon;
|
|||||||
use Illuminate\Support\Str;
|
use Illuminate\Support\Str;
|
||||||
use Pterodactyl\Models\User;
|
use Pterodactyl\Models\User;
|
||||||
use PragmaRX\Google2FA\Google2FA;
|
use PragmaRX\Google2FA\Google2FA;
|
||||||
|
use Illuminate\Database\ConnectionInterface;
|
||||||
use Illuminate\Contracts\Encryption\Encrypter;
|
use Illuminate\Contracts\Encryption\Encrypter;
|
||||||
use Pterodactyl\Contracts\Repository\UserRepositoryInterface;
|
use Pterodactyl\Contracts\Repository\UserRepositoryInterface;
|
||||||
use Pterodactyl\Repositories\Eloquent\RecoveryTokenRepository;
|
use Pterodactyl\Repositories\Eloquent\RecoveryTokenRepository;
|
||||||
@ -33,15 +34,22 @@ class ToggleTwoFactorService
|
|||||||
*/
|
*/
|
||||||
private $recoveryTokenRepository;
|
private $recoveryTokenRepository;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @var \Illuminate\Database\ConnectionInterface
|
||||||
|
*/
|
||||||
|
private $connection;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* ToggleTwoFactorService constructor.
|
* ToggleTwoFactorService constructor.
|
||||||
*
|
*
|
||||||
|
* @param \Illuminate\Database\ConnectionInterface $connection
|
||||||
* @param \Illuminate\Contracts\Encryption\Encrypter $encrypter
|
* @param \Illuminate\Contracts\Encryption\Encrypter $encrypter
|
||||||
* @param \PragmaRX\Google2FA\Google2FA $google2FA
|
* @param \PragmaRX\Google2FA\Google2FA $google2FA
|
||||||
* @param \Pterodactyl\Repositories\Eloquent\RecoveryTokenRepository $recoveryTokenRepository
|
* @param \Pterodactyl\Repositories\Eloquent\RecoveryTokenRepository $recoveryTokenRepository
|
||||||
* @param \Pterodactyl\Contracts\Repository\UserRepositoryInterface $repository
|
* @param \Pterodactyl\Contracts\Repository\UserRepositoryInterface $repository
|
||||||
*/
|
*/
|
||||||
public function __construct(
|
public function __construct(
|
||||||
|
ConnectionInterface $connection,
|
||||||
Encrypter $encrypter,
|
Encrypter $encrypter,
|
||||||
Google2FA $google2FA,
|
Google2FA $google2FA,
|
||||||
RecoveryTokenRepository $recoveryTokenRepository,
|
RecoveryTokenRepository $recoveryTokenRepository,
|
||||||
@ -51,6 +59,7 @@ class ToggleTwoFactorService
|
|||||||
$this->google2FA = $google2FA;
|
$this->google2FA = $google2FA;
|
||||||
$this->repository = $repository;
|
$this->repository = $repository;
|
||||||
$this->recoveryTokenRepository = $recoveryTokenRepository;
|
$this->recoveryTokenRepository = $recoveryTokenRepository;
|
||||||
|
$this->connection = $connection;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -61,11 +70,10 @@ class ToggleTwoFactorService
|
|||||||
* @param bool|null $toggleState
|
* @param bool|null $toggleState
|
||||||
* @return string[]
|
* @return string[]
|
||||||
*
|
*
|
||||||
|
* @throws \Throwable
|
||||||
* @throws \PragmaRX\Google2FA\Exceptions\IncompatibleWithGoogleAuthenticatorException
|
* @throws \PragmaRX\Google2FA\Exceptions\IncompatibleWithGoogleAuthenticatorException
|
||||||
* @throws \PragmaRX\Google2FA\Exceptions\InvalidCharactersException
|
* @throws \PragmaRX\Google2FA\Exceptions\InvalidCharactersException
|
||||||
* @throws \PragmaRX\Google2FA\Exceptions\SecretKeyTooShortException
|
* @throws \PragmaRX\Google2FA\Exceptions\SecretKeyTooShortException
|
||||||
* @throws \Pterodactyl\Exceptions\Model\DataValidationException
|
|
||||||
* @throws \Pterodactyl\Exceptions\Repository\RecordNotFoundException
|
|
||||||
* @throws \Pterodactyl\Exceptions\Service\User\TwoFactorAuthenticationTokenInvalid
|
* @throws \Pterodactyl\Exceptions\Service\User\TwoFactorAuthenticationTokenInvalid
|
||||||
*/
|
*/
|
||||||
public function handle(User $user, string $token, bool $toggleState = null): array
|
public function handle(User $user, string $token, bool $toggleState = null): array
|
||||||
@ -78,6 +86,7 @@ class ToggleTwoFactorService
|
|||||||
throw new TwoFactorAuthenticationTokenInvalid('The token provided is not valid.');
|
throw new TwoFactorAuthenticationTokenInvalid('The token provided is not valid.');
|
||||||
}
|
}
|
||||||
|
|
||||||
|
return $this->connection->transaction(function () use ($user, $toggleState) {
|
||||||
// Now that we're enabling 2FA on the account, generate 10 recovery tokens for the account
|
// Now that we're enabling 2FA on the account, generate 10 recovery tokens for the account
|
||||||
// and store them hashed in the database. We'll return them to the caller so that the user
|
// and store them hashed in the database. We'll return them to the caller so that the user
|
||||||
// can see and save them.
|
// can see and save them.
|
||||||
@ -99,12 +108,12 @@ class ToggleTwoFactorService
|
|||||||
$tokens[] = $token;
|
$tokens[] = $token;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Before inserting any new records make sure all of the old ones are deleted to avoid
|
||||||
|
// any issues or storing an unnecessary number of tokens in the database.
|
||||||
|
$this->recoveryTokenRepository->deleteWhere(['user_id' => $user->id]);
|
||||||
|
|
||||||
// Bulk insert the hashed tokens.
|
// Bulk insert the hashed tokens.
|
||||||
$this->recoveryTokenRepository->insert($inserts);
|
$this->recoveryTokenRepository->insert($inserts);
|
||||||
} elseif ($toggleState === false || $user->use_totp) {
|
|
||||||
// If we are disabling 2FA on this account we will delete all of the recovery codes
|
|
||||||
// that exist in the database for this account.
|
|
||||||
$this->recoveryTokenRepository->deleteWhere(['user_id' => $user->id]);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
$this->repository->withoutFreshModel()->update($user->id, [
|
$this->repository->withoutFreshModel()->update($user->id, [
|
||||||
@ -113,5 +122,6 @@ class ToggleTwoFactorService
|
|||||||
]);
|
]);
|
||||||
|
|
||||||
return $tokens;
|
return $tokens;
|
||||||
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -15,7 +15,11 @@ class CreateUserRecoveryTokensTable extends Migration
|
|||||||
{
|
{
|
||||||
Schema::create('recovery_tokens', function (Blueprint $table) {
|
Schema::create('recovery_tokens', function (Blueprint $table) {
|
||||||
$table->id();
|
$table->id();
|
||||||
$table->timestamps();
|
$table->unsignedInteger('user_id');
|
||||||
|
$table->string('token');
|
||||||
|
$table->timestamp('created_at')->nullable();
|
||||||
|
|
||||||
|
$table->foreign('user_id')->references('id')->on('users')->cascadeOnDelete();
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user