feat: bpn as single source of truth for role and hotel code assignments

This commit is contained in:
Björn Fromme
2026-08-18 11:33:42 +02:00
parent 1fd0fbc21e
commit f0e850978b
17 changed files with 818 additions and 198 deletions
+17 -7
View File
@@ -38,7 +38,7 @@ class BpnAuthenticatorTest extends TestCase
{
$this->stubApiClient($this->createCrmAttributes());
$this->userDataHandler->method('collectRoles')->willReturn([]);
$this->userDataHandler->method('collectClaimedRoles')->willReturn([]);
$this->userDataHandler->method('findLocalUser')->willReturn(null);
$this->userDataHandler->expects($this->never())->method('createLocalUser');
@@ -55,7 +55,7 @@ class BpnAuthenticatorTest extends TestCase
$this->stubApiClient($this->createCrmAttributes());
$this->userDataHandler->method('collectRoles')->willReturn([]);
$this->userDataHandler->method('collectClaimedRoles')->willReturn([]);
$this->userDataHandler->method('findLocalUser')->willReturn($user);
$this->userDataHandler->expects($this->never())->method('updateLocalUser');
@@ -69,6 +69,11 @@ class BpnAuthenticatorTest extends TestCase
$this->assertSame($user, $this->loadUser());
}
/**
* This guard is what stands between a degraded response and a mass revocation: with the
* roles led by the CRM, a login that reached updateLocalUser() on an empty payload would
* strip every role of every user logging in, one at a time.
*/
public function testResponseWithoutAttributeGroupsRefusesTheLoginWithoutBlocking(): void
{
$user = (new User())->setRoles(['ROLE_ADMIN']);
@@ -76,14 +81,19 @@ class BpnAuthenticatorTest extends TestCase
// an empty payload carries no roles either and must not read as a revocation
$this->stubApiClient(new CrmAttributesResponse());
$this->userDataHandler->method('collectRoles')->willReturn([]);
$this->userDataHandler->method('collectClaimedRoles')->willReturn([]);
$this->userDataHandler->method('findLocalUser')->willReturn($user);
$this->userDataHandler->expects($this->never())->method('disableForRevokedCrmRoles');
$this->userDataHandler->expects($this->never())->method('updateLocalUser');
$this->expectException(UserNotFoundException::class);
try {
$this->loadUser();
$this->fail('Expected the login to be refused');
} catch (UserNotFoundException) {
}
$this->loadUser();
$this->assertSame(['ROLE_ADMIN'], $user->getAssignedRoles());
}
/**
@@ -97,7 +107,7 @@ class BpnAuthenticatorTest extends TestCase
$this->stubApiClient($this->createCrmAttributes());
$this->userDataHandler->method('collectRoles')->willReturn(['ROLE_TEAMER']);
$this->userDataHandler->method('collectClaimedRoles')->willReturn(['ROLE_TEAMER']);
$this->userDataHandler->method('findLocalUser')->willReturn($user);
$this->userDataHandler->expects($this->never())->method('updateLocalUser');
@@ -115,7 +125,7 @@ class BpnAuthenticatorTest extends TestCase
$this->stubApiClient($this->createCrmAttributes());
$this->userDataHandler->method('collectRoles')->willReturn([]);
$this->userDataHandler->method('collectClaimedRoles')->willReturn([]);
$this->userDataHandler->method('findLocalUser')->willReturn($user);
$this->userDataHandler->expects($this->never())->method('disableForRevokedCrmRoles');