tests(unit): add RequireTwoFactorAuthenticationTest
This commit is contained in:
parent
790f109e66
commit
64110d84af
9 changed files with 373 additions and 7 deletions
|
@ -0,0 +1,317 @@
|
|||
<?php
|
||||
|
||||
namespace Http\Middleware;
|
||||
|
||||
use Mockery as m;
|
||||
use Pterodactyl\Models\User;
|
||||
use Pterodactyl\Models\WebauthnKey;
|
||||
use Prologue\Alerts\AlertsMessageBag;
|
||||
use Pterodactyl\Tests\Unit\Http\Middleware\MiddlewareTestCase;
|
||||
use Pterodactyl\Http\Middleware\RequireTwoFactorAuthentication;
|
||||
use Pterodactyl\Exceptions\Http\TwoFactorAuthRequiredException;
|
||||
|
||||
class RequireTwoFactorAuthenticationTest extends MiddlewareTestCase
|
||||
{
|
||||
private $alerts;
|
||||
|
||||
/**
|
||||
* Setup tests.
|
||||
*/
|
||||
public function setUp(): void
|
||||
{
|
||||
parent::setUp();
|
||||
|
||||
$this->alerts = m::mock(AlertsMessageBag::class);
|
||||
}
|
||||
|
||||
public function testNoRequirement__userWithout_2fa()
|
||||
{
|
||||
// Disable the 2FA requirement
|
||||
config()->set('pterodactyl.auth.2fa_required', RequireTwoFactorAuthentication::LEVEL_NONE);
|
||||
|
||||
$user = $this->generateRequestUserModel(['use_totp' => false]);
|
||||
|
||||
$this->assertFalse($user->use_totp);
|
||||
$this->assertEmpty($user->totp_secret);
|
||||
$this->assertEmpty($user->totp_authenticated_at);
|
||||
|
||||
$this->request->shouldReceive('getRequestUri')->withNoArgs()->andReturn('/');
|
||||
$this->request->shouldReceive('route->getName')->withNoArgs()->andReturn(null);
|
||||
$this->request->shouldReceive('isJson')->withNoArgs()->andReturn(true);
|
||||
|
||||
$this->getMiddleware()->handle($this->request, $this->getClosureAssertions());
|
||||
}
|
||||
|
||||
public function testNoRequirement__userWithTotp_2fa()
|
||||
{
|
||||
// Disable the 2FA requirement
|
||||
config()->set('pterodactyl.auth.2fa_required', RequireTwoFactorAuthentication::LEVEL_NONE);
|
||||
|
||||
$user = $this->generateRequestUserModel(['use_totp' => true]);
|
||||
|
||||
$this->assertTrue($user->use_totp);
|
||||
$this->assertEmpty($user->totp_secret);
|
||||
$this->assertEmpty($user->totp_authenticated_at);
|
||||
|
||||
$this->request->shouldReceive('getRequestUri')->withNoArgs()->andReturn('/');
|
||||
$this->request->shouldReceive('route->getName')->withNoArgs()->andReturn(null);
|
||||
$this->request->shouldReceive('isJson')->withNoArgs()->andReturn(true);
|
||||
|
||||
$this->getMiddleware()->handle($this->request, $this->getClosureAssertions());
|
||||
}
|
||||
|
||||
public function testNoRequirement__userWithWebauthn_2fa()
|
||||
{
|
||||
// Disable the 2FA requirement
|
||||
config()->set('pterodactyl.auth.2fa_required', RequireTwoFactorAuthentication::LEVEL_NONE);
|
||||
|
||||
/** @var \Pterodactyl\Models\User $user */
|
||||
$user = User::factory()
|
||||
->has(WebauthnKey::factory()->count(1))
|
||||
->create(['use_totp' => false]);
|
||||
$this->setRequestUserModel($user);
|
||||
|
||||
$this->assertFalse($user->use_totp);
|
||||
$this->assertEmpty($user->totp_secret);
|
||||
$this->assertEmpty($user->totp_authenticated_at);
|
||||
$this->assertNotEmpty($user->webauthnKeys);
|
||||
|
||||
$this->request->shouldReceive('getRequestUri')->withNoArgs()->andReturn('/');
|
||||
$this->request->shouldReceive('route->getName')->withNoArgs()->andReturn(null);
|
||||
$this->request->shouldReceive('isJson')->withNoArgs()->andReturn(true);
|
||||
|
||||
$this->getMiddleware()->handle($this->request, $this->getClosureAssertions());
|
||||
}
|
||||
|
||||
public function testNoRequirement__guestUser()
|
||||
{
|
||||
// Disable the 2FA requirement
|
||||
config()->set('pterodactyl.auth.2fa_required', RequireTwoFactorAuthentication::LEVEL_NONE);
|
||||
|
||||
$this->setRequestUserModel();
|
||||
|
||||
$this->request->shouldReceive('getRequestUri')->withNoArgs()->andReturn('/auth/login');
|
||||
$this->request->shouldReceive('route->getName')->withNoArgs()->andReturn('auth.login');
|
||||
$this->request->shouldReceive('isJson')->withNoArgs()->andReturn(true);
|
||||
|
||||
$this->getMiddleware()->handle($this->request, $this->getClosureAssertions());
|
||||
}
|
||||
|
||||
public function testAllRequirement__userWithout_2fa()
|
||||
{
|
||||
$this->expectException(TwoFactorAuthRequiredException::class);
|
||||
|
||||
// Disable the 2FA requirement
|
||||
config()->set('pterodactyl.auth.2fa_required', RequireTwoFactorAuthentication::LEVEL_ALL);
|
||||
|
||||
$user = $this->generateRequestUserModel(['use_totp' => false]);
|
||||
|
||||
$this->assertFalse($user->use_totp);
|
||||
$this->assertEmpty($user->totp_secret);
|
||||
$this->assertEmpty($user->totp_authenticated_at);
|
||||
|
||||
$this->request->shouldReceive('getRequestUri')->withNoArgs()->andReturn('/');
|
||||
$this->request->shouldReceive('route->getName')->withNoArgs()->andReturn(null);
|
||||
$this->request->shouldReceive('isJson')->withNoArgs()->andReturn(true);
|
||||
|
||||
$this->getMiddleware()->handle($this->request, $this->getClosureAssertions());
|
||||
}
|
||||
|
||||
public function testAllRequirement__userWithTotp_2fa()
|
||||
{
|
||||
// Disable the 2FA requirement
|
||||
config()->set('pterodactyl.auth.2fa_required', RequireTwoFactorAuthentication::LEVEL_ALL);
|
||||
|
||||
$user = $this->generateRequestUserModel(['use_totp' => true]);
|
||||
|
||||
$this->assertTrue($user->use_totp);
|
||||
$this->assertEmpty($user->totp_secret);
|
||||
$this->assertEmpty($user->totp_authenticated_at);
|
||||
|
||||
$this->request->shouldReceive('getRequestUri')->withNoArgs()->andReturn('/');
|
||||
$this->request->shouldReceive('route->getName')->withNoArgs()->andReturn(null);
|
||||
$this->request->shouldReceive('isJson')->withNoArgs()->andReturn(true);
|
||||
|
||||
$this->getMiddleware()->handle($this->request, $this->getClosureAssertions());
|
||||
}
|
||||
|
||||
public function testAllRequirement__ruserWithWebauthn_2fa()
|
||||
{
|
||||
// Disable the 2FA requirement
|
||||
config()->set('pterodactyl.auth.2fa_required', RequireTwoFactorAuthentication::LEVEL_ALL);
|
||||
|
||||
/** @var \Pterodactyl\Models\User $user */
|
||||
$user = User::factory()
|
||||
->has(WebauthnKey::factory()->count(1))
|
||||
->create(['use_totp' => false]);
|
||||
$this->setRequestUserModel($user);
|
||||
|
||||
$this->assertFalse($user->use_totp);
|
||||
$this->assertEmpty($user->totp_secret);
|
||||
$this->assertEmpty($user->totp_authenticated_at);
|
||||
$this->assertNotEmpty($user->webauthnKeys);
|
||||
|
||||
$this->request->shouldReceive('getRequestUri')->withNoArgs()->andReturn('/');
|
||||
$this->request->shouldReceive('route->getName')->withNoArgs()->andReturn(null);
|
||||
$this->request->shouldReceive('isJson')->withNoArgs()->andReturn(true);
|
||||
|
||||
$this->getMiddleware()->handle($this->request, $this->getClosureAssertions());
|
||||
}
|
||||
|
||||
public function testAllRequirement__guestUser()
|
||||
{
|
||||
// Disable the 2FA requirement
|
||||
config()->set('pterodactyl.auth.2fa_required', RequireTwoFactorAuthentication::LEVEL_ALL);
|
||||
|
||||
$this->setRequestUserModel();
|
||||
|
||||
$this->request->shouldReceive('getRequestUri')->withNoArgs()->andReturn('/auth/login');
|
||||
$this->request->shouldReceive('route->getName')->withNoArgs()->andReturn('auth.login');
|
||||
$this->request->shouldReceive('isJson')->withNoArgs()->andReturn(true);
|
||||
|
||||
$this->getMiddleware()->handle($this->request, $this->getClosureAssertions());
|
||||
}
|
||||
|
||||
public function testAdminRequirement__userWithout_2fa()
|
||||
{
|
||||
// Disable the 2FA requirement
|
||||
config()->set('pterodactyl.auth.2fa_required', RequireTwoFactorAuthentication::LEVEL_ADMIN);
|
||||
|
||||
$user = $this->generateRequestUserModel(['use_totp' => false]);
|
||||
|
||||
$this->assertFalse($user->use_totp);
|
||||
$this->assertEmpty($user->totp_secret);
|
||||
$this->assertEmpty($user->totp_authenticated_at);
|
||||
$this->assertFalse($user->root_admin);
|
||||
|
||||
$this->request->shouldReceive('getRequestUri')->withNoArgs()->andReturn('/');
|
||||
$this->request->shouldReceive('route->getName')->withNoArgs()->andReturn(null);
|
||||
$this->request->shouldReceive('isJson')->withNoArgs()->andReturn(true);
|
||||
|
||||
$this->getMiddleware()->handle($this->request, $this->getClosureAssertions());
|
||||
}
|
||||
|
||||
public function testAdminRequirement__adminUserWithout_2fa()
|
||||
{
|
||||
$this->expectException(TwoFactorAuthRequiredException::class);
|
||||
|
||||
// Disable the 2FA requirement
|
||||
config()->set('pterodactyl.auth.2fa_required', RequireTwoFactorAuthentication::LEVEL_ADMIN);
|
||||
|
||||
$user = $this->generateRequestUserModel(['use_totp' => false, 'root_admin' => true]);
|
||||
|
||||
$this->assertFalse($user->use_totp);
|
||||
$this->assertEmpty($user->totp_secret);
|
||||
$this->assertEmpty($user->totp_authenticated_at);
|
||||
$this->assertTrue($user->root_admin);
|
||||
|
||||
$this->request->shouldReceive('getRequestUri')->withNoArgs()->andReturn('/');
|
||||
$this->request->shouldReceive('route->getName')->withNoArgs()->andReturn(null);
|
||||
$this->request->shouldReceive('isJson')->withNoArgs()->andReturn(true);
|
||||
|
||||
$this->getMiddleware()->handle($this->request, $this->getClosureAssertions());
|
||||
}
|
||||
|
||||
public function testAdminRequirement__userWithTotp_2fa()
|
||||
{
|
||||
// Disable the 2FA requirement
|
||||
config()->set('pterodactyl.auth.2fa_required', RequireTwoFactorAuthentication::LEVEL_ADMIN);
|
||||
|
||||
$user = $this->generateRequestUserModel(['use_totp' => true]);
|
||||
|
||||
$this->assertTrue($user->use_totp);
|
||||
$this->assertEmpty($user->totp_secret);
|
||||
$this->assertEmpty($user->totp_authenticated_at);
|
||||
$this->assertFalse($user->root_admin);
|
||||
|
||||
$this->request->shouldReceive('getRequestUri')->withNoArgs()->andReturn('/');
|
||||
$this->request->shouldReceive('route->getName')->withNoArgs()->andReturn(null);
|
||||
$this->request->shouldReceive('isJson')->withNoArgs()->andReturn(true);
|
||||
|
||||
$this->getMiddleware()->handle($this->request, $this->getClosureAssertions());
|
||||
}
|
||||
|
||||
public function testAdminRequirement__adminUserWithTotp_2fa()
|
||||
{
|
||||
// Disable the 2FA requirement
|
||||
config()->set('pterodactyl.auth.2fa_required', RequireTwoFactorAuthentication::LEVEL_ADMIN);
|
||||
|
||||
$user = $this->generateRequestUserModel(['use_totp' => true, 'root_admin' => true]);
|
||||
|
||||
$this->assertTrue($user->use_totp);
|
||||
$this->assertEmpty($user->totp_secret);
|
||||
$this->assertEmpty($user->totp_authenticated_at);
|
||||
$this->assertTrue($user->root_admin);
|
||||
|
||||
$this->request->shouldReceive('getRequestUri')->withNoArgs()->andReturn('/');
|
||||
$this->request->shouldReceive('route->getName')->withNoArgs()->andReturn(null);
|
||||
$this->request->shouldReceive('isJson')->withNoArgs()->andReturn(true);
|
||||
|
||||
$this->getMiddleware()->handle($this->request, $this->getClosureAssertions());
|
||||
}
|
||||
|
||||
public function testAdminRequirement__userWithWebauthn_2fa()
|
||||
{
|
||||
// Disable the 2FA requirement
|
||||
config()->set('pterodactyl.auth.2fa_required', RequireTwoFactorAuthentication::LEVEL_ADMIN);
|
||||
|
||||
/** @var \Pterodactyl\Models\User $user */
|
||||
$user = User::factory()->has(WebauthnKey::factory()->count(1))->create(['use_totp' => false]);
|
||||
$this->setRequestUserModel($user);
|
||||
|
||||
$this->assertFalse($user->use_totp);
|
||||
$this->assertEmpty($user->totp_secret);
|
||||
$this->assertEmpty($user->totp_authenticated_at);
|
||||
$this->assertFalse($user->root_admin);
|
||||
$this->assertNotEmpty($user->webauthnKeys);
|
||||
|
||||
$this->request->shouldReceive('getRequestUri')->withNoArgs()->andReturn('/');
|
||||
$this->request->shouldReceive('route->getName')->withNoArgs()->andReturn(null);
|
||||
$this->request->shouldReceive('isJson')->withNoArgs()->andReturn(true);
|
||||
|
||||
$this->getMiddleware()->handle($this->request, $this->getClosureAssertions());
|
||||
}
|
||||
|
||||
public function testAdminRequirement__adminUserWithWebauthn_2fa()
|
||||
{
|
||||
// Disable the 2FA requirement
|
||||
config()->set('pterodactyl.auth.2fa_required', RequireTwoFactorAuthentication::LEVEL_ADMIN);
|
||||
|
||||
/** @var \Pterodactyl\Models\User $user */
|
||||
$user = User::factory()
|
||||
->has(WebauthnKey::factory()->count(1))
|
||||
->create(['use_totp' => false, 'root_admin' => true]);
|
||||
$this->setRequestUserModel($user);
|
||||
|
||||
$this->assertFalse($user->use_totp);
|
||||
$this->assertEmpty($user->totp_secret);
|
||||
$this->assertEmpty($user->totp_authenticated_at);
|
||||
$this->assertTrue($user->root_admin);
|
||||
$this->assertNotEmpty($user->webauthnKeys);
|
||||
|
||||
$this->request->shouldReceive('getRequestUri')->withNoArgs()->andReturn('/');
|
||||
$this->request->shouldReceive('route->getName')->withNoArgs()->andReturn(null);
|
||||
$this->request->shouldReceive('isJson')->withNoArgs()->andReturn(true);
|
||||
|
||||
$this->getMiddleware()->handle($this->request, $this->getClosureAssertions());
|
||||
}
|
||||
|
||||
public function testAdminRequirement__guestUser()
|
||||
{
|
||||
// Disable the 2FA requirement
|
||||
config()->set('pterodactyl.auth.2fa_required', RequireTwoFactorAuthentication::LEVEL_ADMIN);
|
||||
|
||||
$this->setRequestUserModel();
|
||||
|
||||
$this->request->shouldReceive('getRequestUri')->withNoArgs()->andReturn('/auth/login');
|
||||
$this->request->shouldReceive('route->getName')->withNoArgs()->andReturn('auth.login');
|
||||
$this->request->shouldReceive('isJson')->withNoArgs()->andReturn(true);
|
||||
|
||||
$this->getMiddleware()->handle($this->request, $this->getClosureAssertions());
|
||||
}
|
||||
|
||||
private function getMiddleware(): RequireTwoFactorAuthentication
|
||||
{
|
||||
return new RequireTwoFactorAuthentication($this->alerts);
|
||||
}
|
||||
}
|
Loading…
Add table
Add a link
Reference in a new issue