feat(appointment): update patient identification to use national code from profile and enhance appointment creation logic
This commit is contained in:
@@ -2,16 +2,19 @@
|
||||
|
||||
namespace App\Tests\Appointment;
|
||||
|
||||
use App\Appointment\Entity\Appointment;
|
||||
use App\Auth\Entity\User;
|
||||
use App\Doctor\Entity\Doctor;
|
||||
use App\Shared\Constant\ErrorCodes;
|
||||
use App\Tests\ApiTestCase;
|
||||
use App\UserProfile\Entity\UserProfile;
|
||||
|
||||
/**
|
||||
* POST /api/v1/my/appointment must identify the patient by national code:
|
||||
* it is required + validated, and the patient User (hence the case-file) is
|
||||
* resolved by national code first so one person keeps a single record even
|
||||
* when booked under a different mobile.
|
||||
* POST /api/v1/my/appointment must identify the patient by national code.
|
||||
* National code is stored on the patient's UserProfile (profiles.national_code,
|
||||
* unique), so the patient User — and thus the case-file — is resolved by that
|
||||
* profile first. One person keeps a single record even when booked under
|
||||
* several mobiles.
|
||||
*/
|
||||
class AppointmentNationalCodeTest extends ApiTestCase
|
||||
{
|
||||
@@ -50,17 +53,23 @@ class AppointmentNationalCodeTest extends ApiTestCase
|
||||
];
|
||||
}
|
||||
|
||||
public function testCreatesUserWithNationalCode(): void
|
||||
private function profileByNationalCode(string $nc): ?UserProfile
|
||||
{
|
||||
return $this->em->getRepository(UserProfile::class)->findOneBy(['nationalCode' => $nc]);
|
||||
}
|
||||
|
||||
public function testStoresNationalCodeOnProfile(): void
|
||||
{
|
||||
[$owner, $doctor] = $this->doctor();
|
||||
$nc = $this->nationalCode();
|
||||
$nc = $this->nationalCode();
|
||||
$mobile = $this->mobile();
|
||||
|
||||
$this->authJson('POST', '/api/v1/my/appointment', $owner, $this->body($doctor->getUuid(), $this->mobile(), $nc));
|
||||
$this->authJson('POST', '/api/v1/my/appointment', $owner, $this->body($doctor->getUuid(), $mobile, $nc));
|
||||
|
||||
self::assertSame(201, $this->responseCode());
|
||||
$patient = $this->em->getRepository(User::class)->findOneBy(['nationalCode' => $nc]);
|
||||
self::assertNotNull($patient);
|
||||
self::assertSame($nc, $patient->getNationalCode());
|
||||
$profile = $this->profileByNationalCode($nc);
|
||||
self::assertNotNull($profile);
|
||||
self::assertSame($mobile, $profile->getUser()->getMobileNumber());
|
||||
}
|
||||
|
||||
public function testSameNationalCodeDifferentMobileReusesSinglePatient(): void
|
||||
@@ -68,7 +77,7 @@ class AppointmentNationalCodeTest extends ApiTestCase
|
||||
[$owner, $doctor] = $this->doctor();
|
||||
$nc = $this->nationalCode();
|
||||
|
||||
// First booking under mobile A creates the patient.
|
||||
// First booking under mobile A creates the patient + profile.
|
||||
$this->authJson('POST', '/api/v1/my/appointment', $owner, $this->body($doctor->getUuid(), $this->mobile(), $nc));
|
||||
self::assertSame(201, $this->responseCode());
|
||||
|
||||
@@ -77,8 +86,38 @@ class AppointmentNationalCodeTest extends ApiTestCase
|
||||
$this->authJson('POST', '/api/v1/my/appointment', $owner, $this->body($doctor->getUuid(), $this->mobile(), $nc));
|
||||
self::assertSame(201, $this->responseCode());
|
||||
|
||||
$patients = $this->em->getRepository(User::class)->findBy(['nationalCode' => $nc]);
|
||||
self::assertCount(1, $patients);
|
||||
$profiles = $this->em->getRepository(UserProfile::class)->findBy(['nationalCode' => $nc]);
|
||||
self::assertCount(1, $profiles);
|
||||
}
|
||||
|
||||
/**
|
||||
* The reported bug: a patient already exists whose national code sits on
|
||||
* their profile. Booking under a brand-new mobile with that same national
|
||||
* code must attach to the existing patient, not stamp the code onto a new
|
||||
* user.
|
||||
*/
|
||||
public function testExistingProfileNationalCodeIsReusedNotDuplicated(): void
|
||||
{
|
||||
[$owner, $doctor] = $this->doctor();
|
||||
$nc = $this->nationalCode();
|
||||
|
||||
// Existing patient with the national code on their profile.
|
||||
$existing = $this->createUser(['ROLE_USER'], $this->mobile());
|
||||
$profile = new UserProfile($existing);
|
||||
$profile->setNationalCode($nc);
|
||||
$this->em->persist($profile);
|
||||
$this->em->flush();
|
||||
|
||||
// Book under a different mobile but the same national code.
|
||||
$res = $this->authJson('POST', '/api/v1/my/appointment', $owner, $this->body($doctor->getUuid(), $this->mobile(), $nc));
|
||||
self::assertSame(201, $this->responseCode());
|
||||
|
||||
// No duplicate profile, and the appointment is attached to the existing user.
|
||||
$profiles = $this->em->getRepository(UserProfile::class)->findBy(['nationalCode' => $nc]);
|
||||
self::assertCount(1, $profiles);
|
||||
|
||||
$appointment = $this->em->getRepository(Appointment::class)->findOneBy(['uuid' => $res['data']['uuid']]);
|
||||
self::assertSame($existing->getId(), $appointment->getUser()->getId());
|
||||
}
|
||||
|
||||
public function testMissingNationalCodeIs422(): void
|
||||
|
||||
Reference in New Issue
Block a user