fix(security): enforce ownership on GET date-override (IDOR)
getOverride leaked any doctor's override to any authenticated user; add the owner-or-admin check (matching the update/delete endpoints) + regression test.
This commit is contained in:
@@ -237,13 +237,17 @@ class AppointmentSettingsController extends BaseController
|
||||
}
|
||||
|
||||
#[Route('/api/v1/appointment-settings/date-override/{uuid}', methods: ['GET'])]
|
||||
public function getOverride(string $uuid): JsonResponse
|
||||
public function getOverride(string $uuid, #[CurrentUser] User $user): JsonResponse
|
||||
{
|
||||
$override = $this->overrideRepo->findByUuid($uuid);
|
||||
if ($override === null) {
|
||||
return $this->error(ErrorCodes::ERR_VALIDATION_002, 'Override یافت نشد', 404);
|
||||
}
|
||||
|
||||
if ($override->getDoctor()->getUser()->getId() !== $user->getId() && !$user->hasRole('ROLE_ADMIN')) {
|
||||
return $this->error(ErrorCodes::ERR_AUTH_006, 'دسترسی ممنوع', 403);
|
||||
}
|
||||
|
||||
return $this->success(['data' => $override->toArray()]);
|
||||
}
|
||||
|
||||
|
||||
@@ -0,0 +1,40 @@
|
||||
<?php
|
||||
|
||||
namespace App\Tests\Appointment;
|
||||
|
||||
use App\Appointment\Entity\DateOverride;
|
||||
use App\Doctor\Entity\Doctor;
|
||||
use App\Tests\ApiTestCase;
|
||||
|
||||
/**
|
||||
* Regression: GET date-override/{uuid} must enforce ownership (IDOR fix).
|
||||
*/
|
||||
class DateOverrideOwnershipTest extends ApiTestCase
|
||||
{
|
||||
private function makeOverride(): array
|
||||
{
|
||||
$owner = $this->createUser(['ROLE_DOCTOR']);
|
||||
$doctor = new Doctor($owner, 'دکتر تست');
|
||||
$this->em->persist($doctor);
|
||||
$override = new DateOverride($doctor, time(), true);
|
||||
$this->em->persist($override);
|
||||
$this->em->flush();
|
||||
|
||||
return [$owner, $override];
|
||||
}
|
||||
|
||||
public function testOwnerCanRead(): void
|
||||
{
|
||||
[$owner, $override] = $this->makeOverride();
|
||||
$this->authJson('GET', '/api/v1/appointment-settings/date-override/' . $override->getUuid(), $owner);
|
||||
$this->assertSame(200, $this->responseCode());
|
||||
}
|
||||
|
||||
public function testOtherUserIsForbidden(): void
|
||||
{
|
||||
[, $override] = $this->makeOverride();
|
||||
$attacker = $this->createUser(['ROLE_DOCTOR']);
|
||||
$this->authJson('GET', '/api/v1/appointment-settings/date-override/' . $override->getUuid(), $attacker);
|
||||
$this->assertSame(403, $this->responseCode());
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user