Skip to content

Commit 5f08f50

Browse files
committed
Add tests for cases access control and Gate setup
Ensure the 'view-all_cases' permission row exists and register a Gate in tests so the can:view-all_cases middleware is enforceable. Update the existing forbidden test to define the permission and Gate, and add two new tests: one that confirms a user can view their own cases (scoped by userId) without the global permission, and another that verifies a user cannot view another user's cases without the permission and that granting it restores access. Creates test data via factories and asserts correct response codes and payload counts.
1 parent 44829fb commit 5f08f50

1 file changed

Lines changed: 60 additions & 6 deletions

File tree

tests/Feature/Api/V1_1/CaseControllerTest.php

Lines changed: 60 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -479,23 +479,26 @@ public function test_get_my_cases_counters_ok(): void
479479

480480
public function test_get_all_cases_forbidden_without_view_all_cases_permission(): void
481481
{
482-
// Seed permissions and register gates so the `can:view-all_cases`
483-
// middleware on api.1.1.cases.all_cases is enforceable in tests.
484-
$this->initializePermissions();
482+
// Ensure the permission row exists and register it as a Laravel Gate
483+
// so $user->can('view-all_cases') is enforceable in tests.
484+
Permission::firstOrCreate(
485+
['name' => 'view-all_cases'],
486+
['title' => 'View All Cases'],
487+
);
488+
Gate::define('view-all_cases', fn ($user) => $user->hasPermission('view-all_cases'));
485489

486490
$nonAdmin = User::factory()->create([
487491
'is_administrator' => false,
488492
]);
489493

490-
// Create some cases so a permitted user would get a non-empty payload.
491494
self::createCasesStartedForUser($nonAdmin->id, 3);
492495

493-
// Without the permission, access is denied.
496+
// Unscoped request (the "All cases" tab) — denied without the permission.
494497
$response = $this->actingAs($nonAdmin, 'api')
495498
->json('GET', route('api.1.1.cases.all_cases'));
496499
$response->assertStatus(403);
497500

498-
// Granting the permission restores access.
501+
// Granting the permission restores access to the unscoped query.
499502
$nonAdmin->giveDirectPermission('view-all_cases');
500503

501504
$response = $this->actingAs($nonAdmin, 'api')
@@ -504,6 +507,57 @@ public function test_get_all_cases_forbidden_without_view_all_cases_permission()
504507
$response->assertJsonCount(3, 'data');
505508
}
506509

510+
public function test_get_all_cases_allows_user_to_view_their_own_cases_without_permission(): void
511+
{
512+
// The endpoint is shared by the "My cases" tab, which scopes the
513+
// query to the authenticated user. That self-scoped path must work
514+
// even when the user lacks `view-all_cases`.
515+
$nonAdmin = User::factory()->create([
516+
'is_administrator' => false,
517+
]);
518+
519+
$ownCases = self::createCasesStartedForUser($nonAdmin->id, 4);
520+
$otherUser = self::createUser('other_user');
521+
self::createCasesStartedForUser($otherUser->id, 6);
522+
523+
$response = $this->actingAs($nonAdmin, 'api')
524+
->json('GET', route('api.1.1.cases.all_cases', ['userId' => $nonAdmin->id]));
525+
526+
$response->assertStatus(200);
527+
$response->assertJsonCount($ownCases->count(), 'data');
528+
$response->assertJsonMissing(['user_id' => $otherUser->id]);
529+
}
530+
531+
public function test_get_all_cases_forbids_user_from_viewing_another_users_cases_without_permission(): void
532+
{
533+
Permission::firstOrCreate(
534+
['name' => 'view-all_cases'],
535+
['title' => 'View All Cases'],
536+
);
537+
Gate::define('view-all_cases', fn ($user) => $user->hasPermission('view-all_cases'));
538+
539+
$nonAdmin = User::factory()->create([
540+
'is_administrator' => false,
541+
]);
542+
$otherUser = self::createUser('other_user');
543+
self::createCasesStartedForUser($otherUser->id, 2);
544+
545+
// Passing another user's id must require `view-all_cases`; otherwise
546+
// any authenticated user could iterate userIds to enumerate the
547+
// entire platform.
548+
$response = $this->actingAs($nonAdmin, 'api')
549+
->json('GET', route('api.1.1.cases.all_cases', ['userId' => $otherUser->id]));
550+
$response->assertStatus(403);
551+
552+
// With the permission, the same request succeeds.
553+
$nonAdmin->giveDirectPermission('view-all_cases');
554+
555+
$response = $this->actingAs($nonAdmin, 'api')
556+
->json('GET', route('api.1.1.cases.all_cases', ['userId' => $otherUser->id]));
557+
$response->assertStatus(200);
558+
$response->assertJsonCount(2, 'data');
559+
}
560+
507561
public function test_get_all_cases_participants(): void
508562
{
509563
$userA = $this->createUser('user_a');

0 commit comments

Comments
 (0)