Code Coverage
 
Lines
Functions and Methods
Classes and Traits
Total
100.00% covered (success)
100.00%
94 / 94
n/a
0 / 0
CRAP
n/a
0 / 0
1<?php
2
3// ╔════════════════════════════════════════════════════════════╗
4// ║ MIT Licence (#Expat) - https://opensource.org/licenses/MIT ║
5// ║ Copyright 2026 Frederic Poeydomenge <dyno@phexium.com>     ║
6// ╚════════════════════════════════════════════════════════════╝
7
8declare(strict_types=1);
9
10use AppDemo\Shared\Domain\UserContext;
11use AppDemo\User\Domain\UserGroup;
12use Phexium\Domain\Id\IdInterface;
13use Tests\AppDemo\Fake\Application\Service\RbacPermissionService as FakeRbacPermissionService;
14use Tests\AppDemo\Fixture\UserMother;
15
16beforeEach(function (): void {
17    $this->rbacService = new FakeRbacPermissionService();
18});
19
20test('Returns true when authenticated user has the requested permission', function (): void {
21    $user = UserMother::admin();
22
23    $this->rbacService->addPermission(UserGroup::Admin, 'book.create');
24
25    $userContext = new UserContext($user, $this->rbacService);
26
27    expect($userContext->can('book.create'))->toBeTrue();
28});
29
30test('Returns false when authenticated user does not have the requested permission', function (): void {
31    $user = UserMother::user();
32
33    $userContext = new UserContext($user, $this->rbacService);
34
35    expect($userContext->can('book.delete'))->toBeFalse();
36});
37
38test('can() returns false when user is not authenticated', function (): void {
39    $userContext = new UserContext(null, $this->rbacService);
40
41    expect($userContext->can('book.create'))->toBeFalse();
42});
43
44test('Returns true when authenticated user has at least one of the requested permissions', function (): void {
45    $user = UserMother::admin();
46    $permissions = ['book.create', 'book.update', 'book.delete'];
47
48    $this->rbacService->addPermission(UserGroup::Admin, 'book.create');
49
50    $userContext = new UserContext($user, $this->rbacService);
51
52    expect($userContext->canAny($permissions))->toBeTrue();
53});
54
55test('Returns false when authenticated user has none of the requested permissions', function (): void {
56    $user = UserMother::user();
57    $permissions = ['book.delete', 'user.delete'];
58
59    $userContext = new UserContext($user, $this->rbacService);
60
61    expect($userContext->canAny($permissions))->toBeFalse();
62});
63
64test('Returns false when checking multiple permissions and user is not authenticated', function (): void {
65    $userContext = new UserContext(null, $this->rbacService);
66
67    expect($userContext->canAny(['book.create', 'book.update']))->toBeFalse();
68});
69
70test('Returns true when authenticated user has all requested permissions', function (): void {
71    $user = UserMother::admin();
72    $permissions = ['book.create', 'book.update'];
73
74    $this->rbacService->setPermissions(UserGroup::Admin, $permissions);
75
76    $userContext = new UserContext($user, $this->rbacService);
77
78    expect($userContext->canAll($permissions))->toBeTrue();
79});
80
81test('Returns false when authenticated user is missing at least one permission', function (): void {
82    $user = UserMother::user();
83    $permissions = ['book.create', 'book.delete'];
84
85    $this->rbacService->addPermission(UserGroup::User, 'book.create');
86
87    $userContext = new UserContext($user, $this->rbacService);
88
89    expect($userContext->canAll($permissions))->toBeFalse();
90});
91
92test('Returns false when checking all permissions and user is not authenticated', function (): void {
93    $userContext = new UserContext(null, $this->rbacService);
94
95    expect($userContext->canAll(['book.create', 'book.update']))->toBeFalse();
96});
97
98test('Returns all permissions when user is authenticated', function (): void {
99    $user = UserMother::admin();
100    $expectedPermissions = ['book.create', 'book.update', 'book.delete'];
101
102    $this->rbacService->setPermissions(UserGroup::Admin, $expectedPermissions);
103
104    $userContext = new UserContext($user, $this->rbacService);
105
106    expect($userContext->getPermissions())->toBe($expectedPermissions);
107});
108
109test('Returns empty array when user is not authenticated', function (): void {
110    $userContext = new UserContext(null, $this->rbacService);
111
112    expect($userContext->getPermissions())->toBe([]);
113});
114
115test('Returns user when authenticated', function (): void {
116    $user = UserMother::admin();
117    $userContext = new UserContext($user, $this->rbacService);
118
119    expect($userContext->getUser())->toBe($user);
120});
121
122test('getUser() returns null when user is not authenticated', function (): void {
123    $userContext = new UserContext(null, $this->rbacService);
124
125    expect($userContext->getUser())->toBeNull();
126});
127
128test('Returns user ID when authenticated', function (): void {
129    $user = UserMother::admin(123);
130    $userContext = new UserContext($user, $this->rbacService);
131
132    $userId = $userContext->getUserId();
133    expect($userId)->toBeInstanceOf(IdInterface::class)
134        ->and($userId->getValue())->toBe(123)
135    ;
136});
137
138test('getUserId() returns null when user is not authenticated', function (): void {
139    $userContext = new UserContext(null, $this->rbacService);
140
141    expect($userContext->getUserId())->toBeNull();
142});
143
144test('Returns true when user is authenticated', function (): void {
145    $user = UserMother::user();
146    $userContext = new UserContext($user, $this->rbacService);
147
148    expect($userContext->isAuthenticated())->toBeTrue();
149});
150
151test('isAuthenticated() returns false when user is not authenticated', function (): void {
152    $userContext = new UserContext(null, $this->rbacService);
153
154    expect($userContext->isAuthenticated())->toBeFalse();
155});