145 lines
5.6 KiB
PHP
145 lines
5.6 KiB
PHP
|
|
<?php
|
||
|
|
|
||
|
|
namespace MintyPHP\Tests\Service\Settings;
|
||
|
|
|
||
|
|
use MintyPHP\Repository\Access\RoleRepository;
|
||
|
|
use MintyPHP\Repository\Org\DepartmentRepository;
|
||
|
|
use MintyPHP\Repository\Settings\SettingRepository;
|
||
|
|
use MintyPHP\Repository\Tenant\TenantRepository;
|
||
|
|
use MintyPHP\Service\Settings\SettingService;
|
||
|
|
use MintyPHP\Service\Settings\ThemeConfigService;
|
||
|
|
use PHPUnit\Framework\TestCase;
|
||
|
|
|
||
|
|
class SettingServiceTest extends TestCase
|
||
|
|
{
|
||
|
|
public function testSetDefaultTenantIdRejectsUnknownTenant(): void
|
||
|
|
{
|
||
|
|
$settingRepository = $this->createMock(SettingRepository::class);
|
||
|
|
$settingRepository->expects($this->never())->method('set');
|
||
|
|
|
||
|
|
$tenantRepository = $this->createMock(TenantRepository::class);
|
||
|
|
$tenantRepository->expects($this->once())->method('find')->with(99)->willReturn(null);
|
||
|
|
|
||
|
|
$service = $this->newService($settingRepository, $tenantRepository);
|
||
|
|
$this->assertFalse($service->setDefaultTenantId(99));
|
||
|
|
}
|
||
|
|
|
||
|
|
public function testSetApiTokenDefaultTtlDaysRejectsAboveCurrentMax(): void
|
||
|
|
{
|
||
|
|
$settingRepository = $this->createMock(SettingRepository::class);
|
||
|
|
$settingRepository->method('getValue')->willReturnCallback(
|
||
|
|
static function (string $key): ?string {
|
||
|
|
if ($key === SettingService::API_TOKEN_MAX_TTL_DAYS_KEY) {
|
||
|
|
return '30';
|
||
|
|
}
|
||
|
|
return null;
|
||
|
|
}
|
||
|
|
);
|
||
|
|
$settingRepository->expects($this->never())->method('set');
|
||
|
|
|
||
|
|
$service = $this->newService($settingRepository);
|
||
|
|
$this->assertFalse($service->setApiTokenDefaultTtlDays(31));
|
||
|
|
}
|
||
|
|
|
||
|
|
public function testSetApiTokenMaxTtlDaysUpdatesDefaultWhenNeeded(): void
|
||
|
|
{
|
||
|
|
$settingRepository = $this->createMock(SettingRepository::class);
|
||
|
|
$settingRepository->method('getValue')->willReturnCallback(
|
||
|
|
static function (string $key): ?string {
|
||
|
|
if ($key === SettingService::API_TOKEN_DEFAULT_TTL_DAYS_KEY) {
|
||
|
|
return '365';
|
||
|
|
}
|
||
|
|
return null;
|
||
|
|
}
|
||
|
|
);
|
||
|
|
|
||
|
|
$calls = [];
|
||
|
|
$settingRepository->expects($this->exactly(2))
|
||
|
|
->method('set')
|
||
|
|
->willReturnCallback(
|
||
|
|
static function (string $key, ?string $value, ?string $description) use (&$calls): bool {
|
||
|
|
$calls[] = [$key, $value, $description];
|
||
|
|
return true;
|
||
|
|
}
|
||
|
|
);
|
||
|
|
|
||
|
|
$service = $this->newService($settingRepository);
|
||
|
|
$this->assertTrue($service->setApiTokenMaxTtlDays(120));
|
||
|
|
$this->assertSame(
|
||
|
|
[
|
||
|
|
[SettingService::API_TOKEN_DEFAULT_TTL_DAYS_KEY, '120', 'setting.api_token_default_ttl_days'],
|
||
|
|
[SettingService::API_TOKEN_MAX_TTL_DAYS_KEY, '120', 'setting.api_token_max_ttl_days'],
|
||
|
|
],
|
||
|
|
$calls
|
||
|
|
);
|
||
|
|
}
|
||
|
|
|
||
|
|
public function testSetUserInactivityDeleteDaysRequiresDeactivatePolicy(): void
|
||
|
|
{
|
||
|
|
$settingRepository = $this->createMock(SettingRepository::class);
|
||
|
|
$settingRepository->method('getValue')->willReturnCallback(
|
||
|
|
static function (string $key): ?string {
|
||
|
|
if ($key === SettingService::USER_INACTIVITY_DEACTIVATE_DAYS_KEY) {
|
||
|
|
return '0';
|
||
|
|
}
|
||
|
|
return null;
|
||
|
|
}
|
||
|
|
);
|
||
|
|
$settingRepository->expects($this->never())->method('set');
|
||
|
|
|
||
|
|
$service = $this->newService($settingRepository);
|
||
|
|
$this->assertFalse($service->setUserInactivityDeleteDays(30));
|
||
|
|
}
|
||
|
|
|
||
|
|
public function testSetApiCorsAllowedOriginsRejectsInvalidOrigins(): void
|
||
|
|
{
|
||
|
|
$settingRepository = $this->createMock(SettingRepository::class);
|
||
|
|
$settingRepository->expects($this->never())->method('set');
|
||
|
|
|
||
|
|
$service = $this->newService($settingRepository);
|
||
|
|
$this->assertFalse($service->setApiCorsAllowedOrigins("https://ok.example\njavascript:alert(1)"));
|
||
|
|
}
|
||
|
|
|
||
|
|
public function testSetMicrosoftAuthorityRequiresHttps(): void
|
||
|
|
{
|
||
|
|
$settingRepository = $this->createMock(SettingRepository::class);
|
||
|
|
$settingRepository->expects($this->never())->method('set');
|
||
|
|
|
||
|
|
$service = $this->newService($settingRepository);
|
||
|
|
$this->assertFalse($service->setMicrosoftAuthority('http://login.microsoftonline.com/common/v2.0'));
|
||
|
|
}
|
||
|
|
|
||
|
|
public function testSetAppPrimaryColorNormalizesHexWithoutHash(): void
|
||
|
|
{
|
||
|
|
$settingRepository = $this->createMock(SettingRepository::class);
|
||
|
|
$settingRepository->expects($this->once())
|
||
|
|
->method('set')
|
||
|
|
->with(SettingService::APP_PRIMARY_COLOR_KEY, '#abc', 'setting.app_primary_color')
|
||
|
|
->willReturn(true);
|
||
|
|
|
||
|
|
$service = $this->newService($settingRepository);
|
||
|
|
$this->assertTrue($service->setAppPrimaryColor('abc'));
|
||
|
|
}
|
||
|
|
|
||
|
|
private function newService(
|
||
|
|
SettingRepository $settingRepository,
|
||
|
|
?TenantRepository $tenantRepository = null,
|
||
|
|
?RoleRepository $roleRepository = null,
|
||
|
|
?DepartmentRepository $departmentRepository = null
|
||
|
|
): SettingService {
|
||
|
|
$tenantRepository = $tenantRepository ?? $this->createMock(TenantRepository::class);
|
||
|
|
$roleRepository = $roleRepository ?? $this->createMock(RoleRepository::class);
|
||
|
|
$departmentRepository = $departmentRepository ?? $this->createMock(DepartmentRepository::class);
|
||
|
|
$themeConfigService = $this->createMock(ThemeConfigService::class);
|
||
|
|
$themeConfigService->method('all')->willReturn(['light' => 'Light', 'dark' => 'Dark']);
|
||
|
|
|
||
|
|
return new SettingService(
|
||
|
|
$settingRepository,
|
||
|
|
$tenantRepository,
|
||
|
|
$roleRepository,
|
||
|
|
$departmentRepository,
|
||
|
|
$themeConfigService
|
||
|
|
);
|
||
|
|
}
|
||
|
|
}
|