feat: add RichTextEditor component for rich text editing in articles
feat: create SanitizeBlogBodiesCommand to clean existing blog bodies according to current HTML sanitization policies test: add AppointmentTreatmentSessionLinkTest to ensure appointment booking functionality works correctly with treatment session links
This commit is contained in:
@@ -29,6 +29,8 @@ use Symfony\Component\Security\Http\Attribute\IsGranted;
|
||||
#[OA\Tag(name: 'Appointments')]
|
||||
class AppointmentController extends BaseController
|
||||
{
|
||||
use \App\Shared\Controller\PermissionGateTrait;
|
||||
|
||||
public function __construct(
|
||||
private readonly AppointmentRepository $appointmentRepo,
|
||||
private readonly DoctorRepository $doctorRepo,
|
||||
@@ -1042,6 +1044,11 @@ class AppointmentController extends BaseController
|
||||
#[Route('/api/v1/appointment/{uuid}/status', methods: ['PATCH'])]
|
||||
public function updateStatus(string $uuid, Request $request, #[CurrentUser] User $user): JsonResponse
|
||||
{
|
||||
// پیشچکِ منشی، پیش از واکشیِ رکورد. چکِ اصلی به خودِ شیء نیاز دارد و بالا
|
||||
// نمیرود؛ سهمِ منشی از آن اما همیشه همین توگل است، پس این خط هیچ مسیرِ
|
||||
// مجازی نمیبندد و فقط ۴۰۴ را به ۴۰۳ تبدیل میکند. یافتهٔ ۱۰ آدیت ۲۰۲۶-۰۸-۰۷.
|
||||
$this->denySecretaryWithout($user, 'appointments', 'update_status');
|
||||
|
||||
$appointment = $this->appointmentRepo->findByUuid($uuid);
|
||||
if ($appointment === null) {
|
||||
return $this->error(ErrorCodes::ERR_VALIDATION_002, 'نوبت یافت نشد', 404);
|
||||
@@ -1131,6 +1138,11 @@ class AppointmentController extends BaseController
|
||||
#[IsGranted('IS_AUTHENTICATED_FULLY')]
|
||||
public function confirm(string $uuid, Request $request, #[CurrentUser] User $user): JsonResponse
|
||||
{
|
||||
// پیشچکِ منشی، پیش از واکشیِ رکورد. چکِ اصلی به خودِ شیء نیاز دارد و بالا
|
||||
// نمیرود؛ سهمِ منشی از آن اما همیشه همین توگل است، پس این خط هیچ مسیرِ
|
||||
// مجازی نمیبندد و فقط ۴۰۴ را به ۴۰۳ تبدیل میکند. یافتهٔ ۱۰ آدیت ۲۰۲۶-۰۸-۰۷.
|
||||
$this->denySecretaryWithout($user, 'appointments', 'update_status');
|
||||
|
||||
$appointment = $this->appointmentRepo->findByUuid($uuid);
|
||||
if ($appointment === null) {
|
||||
return $this->error(ErrorCodes::ERR_VALIDATION_002, 'نوبت یافت نشد', 404);
|
||||
@@ -1214,6 +1226,11 @@ class AppointmentController extends BaseController
|
||||
#[IsGranted('IS_AUTHENTICATED_FULLY')]
|
||||
public function update(string $uuid, Request $request, #[CurrentUser] User $user): JsonResponse
|
||||
{
|
||||
// پیشچکِ منشی، پیش از واکشیِ رکورد. چکِ اصلی به خودِ شیء نیاز دارد و بالا
|
||||
// نمیرود؛ سهمِ منشی از آن اما همیشه همین توگل است، پس این خط هیچ مسیرِ
|
||||
// مجازی نمیبندد و فقط ۴۰۴ را به ۴۰۳ تبدیل میکند. یافتهٔ ۱۰ آدیت ۲۰۲۶-۰۸-۰۷.
|
||||
$this->denySecretaryWithout($user, 'appointments', 'update_status');
|
||||
|
||||
$appointment = $this->appointmentRepo->findByUuid($uuid);
|
||||
if ($appointment === null) {
|
||||
return $this->error(ErrorCodes::ERR_VALIDATION_002, 'نوبت یافت نشد', 404);
|
||||
@@ -1396,6 +1413,11 @@ class AppointmentController extends BaseController
|
||||
#[IsGranted('IS_AUTHENTICATED_FULLY')]
|
||||
public function serviceReschedule(string $uuid, Request $request, #[CurrentUser] User $user): JsonResponse
|
||||
{
|
||||
// پیشچکِ منشی، پیش از واکشیِ رکورد. چکِ اصلی به خودِ شیء نیاز دارد و بالا
|
||||
// نمیرود؛ سهمِ منشی از آن اما همیشه همین توگل است، پس این خط هیچ مسیرِ
|
||||
// مجازی نمیبندد و فقط ۴۰۴ را به ۴۰۳ تبدیل میکند. یافتهٔ ۱۰ آدیت ۲۰۲۶-۰۸-۰۷.
|
||||
$this->denySecretaryWithout($user, 'appointments', 'update_status');
|
||||
|
||||
$appointment = $this->appointmentRepo->findByUuid($uuid);
|
||||
if ($appointment === null) {
|
||||
return $this->error(ErrorCodes::ERR_VALIDATION_002, 'نوبت یافت نشد', 404);
|
||||
|
||||
@@ -187,6 +187,12 @@ class AppointmentSettingsController extends BaseController
|
||||
#[Route('/api/v1/appointment-settings/weekly-schedule', methods: ['POST'])]
|
||||
public function createSchedule(Request $request, #[CurrentUser] User $user): JsonResponse
|
||||
{
|
||||
// پیشچکِ منشی، پیش از هر واکشی. چکِ اصلی (denyDoctorAccess) به پزشکِ
|
||||
// همان رکورد نیاز دارد و بالا نمیرود؛ ولی سهمِ منشی از آن همیشه همین
|
||||
// توگل است، پس این خط هیچ مسیرِ مجازی نمیبندد و فقط ۴۰۴ را به ۴۰۳
|
||||
// تبدیل میکند. یافتهٔ ۱۰ آدیت ۲۰۲۶-۰۸-۰۷.
|
||||
$this->secretaryAccess->denyUnlessGranted($user, 'appointment_settings', 'update');
|
||||
|
||||
$data = json_decode($request->getContent(), true) ?? [];
|
||||
$doctorUuid = trim($data['doctor_uuid'] ?? '');
|
||||
|
||||
@@ -243,6 +249,12 @@ class AppointmentSettingsController extends BaseController
|
||||
#[Route('/api/v1/appointment-settings/weekly-schedule/{uuid}', methods: ['PATCH'])]
|
||||
public function updateSchedule(string $uuid, Request $request, #[CurrentUser] User $user): JsonResponse
|
||||
{
|
||||
// پیشچکِ منشی، پیش از هر واکشی. چکِ اصلی (denyDoctorAccess) به پزشکِ
|
||||
// همان رکورد نیاز دارد و بالا نمیرود؛ ولی سهمِ منشی از آن همیشه همین
|
||||
// توگل است، پس این خط هیچ مسیرِ مجازی نمیبندد و فقط ۴۰۴ را به ۴۰۳
|
||||
// تبدیل میکند. یافتهٔ ۱۰ آدیت ۲۰۲۶-۰۸-۰۷.
|
||||
$this->secretaryAccess->denyUnlessGranted($user, 'appointment_settings', 'update');
|
||||
|
||||
$data = json_decode($request->getContent(), true) ?? [];
|
||||
|
||||
// uuid may be doctor uuid or schedule uuid
|
||||
@@ -325,6 +337,12 @@ class AppointmentSettingsController extends BaseController
|
||||
#[Route('/api/v1/booking-setting/{uuid}', methods: ['DELETE'])]
|
||||
public function deleteSchedule(string $uuid, #[CurrentUser] User $user): JsonResponse
|
||||
{
|
||||
// پیشچکِ منشی، پیش از هر واکشی. چکِ اصلی (denyDoctorAccess) به پزشکِ
|
||||
// همان رکورد نیاز دارد و بالا نمیرود؛ ولی سهمِ منشی از آن همیشه همین
|
||||
// توگل است، پس این خط هیچ مسیرِ مجازی نمیبندد و فقط ۴۰۴ را به ۴۰۳
|
||||
// تبدیل میکند. یافتهٔ ۱۰ آدیت ۲۰۲۶-۰۸-۰۷.
|
||||
$this->secretaryAccess->denyUnlessGranted($user, 'appointment_settings', 'update');
|
||||
|
||||
$schedule = $this->scheduleRepo->findByUuid($uuid);
|
||||
if ($schedule === null) {
|
||||
return $this->error(ErrorCodes::ERR_VALIDATION_002, 'برنامه یافت نشد', 404);
|
||||
@@ -366,6 +384,12 @@ class AppointmentSettingsController extends BaseController
|
||||
#[Route('/api/v1/appointment-settings/date-override', methods: ['POST'])]
|
||||
public function createOverride(Request $request, #[CurrentUser] User $user): JsonResponse
|
||||
{
|
||||
// پیشچکِ منشی، پیش از هر واکشی. چکِ اصلی (denyDoctorAccess) به پزشکِ
|
||||
// همان رکورد نیاز دارد و بالا نمیرود؛ ولی سهمِ منشی از آن همیشه همین
|
||||
// توگل است، پس این خط هیچ مسیرِ مجازی نمیبندد و فقط ۴۰۴ را به ۴۰۳
|
||||
// تبدیل میکند. یافتهٔ ۱۰ آدیت ۲۰۲۶-۰۸-۰۷.
|
||||
$this->secretaryAccess->denyUnlessGranted($user, 'appointment_settings', 'update');
|
||||
|
||||
$data = json_decode($request->getContent(), true) ?? [];
|
||||
$doctorUuid = trim($data['doctor_uuid'] ?? '');
|
||||
$dateStr = trim($data['date'] ?? '');
|
||||
@@ -399,6 +423,12 @@ class AppointmentSettingsController extends BaseController
|
||||
#[Route('/api/v1/appointment-settings/date-override/{uuid}', methods: ['PATCH'])]
|
||||
public function updateOverride(string $uuid, Request $request, #[CurrentUser] User $user): JsonResponse
|
||||
{
|
||||
// پیشچکِ منشی، پیش از هر واکشی. چکِ اصلی (denyDoctorAccess) به پزشکِ
|
||||
// همان رکورد نیاز دارد و بالا نمیرود؛ ولی سهمِ منشی از آن همیشه همین
|
||||
// توگل است، پس این خط هیچ مسیرِ مجازی نمیبندد و فقط ۴۰۴ را به ۴۰۳
|
||||
// تبدیل میکند. یافتهٔ ۱۰ آدیت ۲۰۲۶-۰۸-۰۷.
|
||||
$this->secretaryAccess->denyUnlessGranted($user, 'appointment_settings', 'update');
|
||||
|
||||
$override = $this->overrideRepo->findByUuid($uuid);
|
||||
if ($override === null) {
|
||||
return $this->error(ErrorCodes::ERR_VALIDATION_002, 'Override یافت نشد', 404);
|
||||
@@ -425,6 +455,12 @@ class AppointmentSettingsController extends BaseController
|
||||
#[Route('/api/v1/appointment-settings/date-override/{uuid}', methods: ['DELETE'])]
|
||||
public function deleteOverride(string $uuid, #[CurrentUser] User $user): JsonResponse
|
||||
{
|
||||
// پیشچکِ منشی، پیش از هر واکشی. چکِ اصلی (denyDoctorAccess) به پزشکِ
|
||||
// همان رکورد نیاز دارد و بالا نمیرود؛ ولی سهمِ منشی از آن همیشه همین
|
||||
// توگل است، پس این خط هیچ مسیرِ مجازی نمیبندد و فقط ۴۰۴ را به ۴۰۳
|
||||
// تبدیل میکند. یافتهٔ ۱۰ آدیت ۲۰۲۶-۰۸-۰۷.
|
||||
$this->secretaryAccess->denyUnlessGranted($user, 'appointment_settings', 'update');
|
||||
|
||||
$override = $this->overrideRepo->findByUuid($uuid);
|
||||
if ($override === null) {
|
||||
return $this->error(ErrorCodes::ERR_VALIDATION_002, 'Override یافت نشد', 404);
|
||||
@@ -484,6 +520,12 @@ class AppointmentSettingsController extends BaseController
|
||||
#[Route('/api/v1/appointment-settings/holidays/{uuid}', methods: ['DELETE'])]
|
||||
public function deleteHoliday(string $uuid, #[CurrentUser] User $user): JsonResponse
|
||||
{
|
||||
// پیشچکِ منشی، پیش از هر واکشی. چکِ اصلی (denyDoctorAccess) به پزشکِ
|
||||
// همان رکورد نیاز دارد و بالا نمیرود؛ ولی سهمِ منشی از آن همیشه همین
|
||||
// توگل است، پس این خط هیچ مسیرِ مجازی نمیبندد و فقط ۴۰۴ را به ۴۰۳
|
||||
// تبدیل میکند. یافتهٔ ۱۰ آدیت ۲۰۲۶-۰۸-۰۷.
|
||||
$this->secretaryAccess->denyUnlessGranted($user, 'appointment_settings', 'update');
|
||||
|
||||
$holiday = $this->holidayRepo->findByUuid($uuid);
|
||||
if ($holiday === null) {
|
||||
return $this->error(ErrorCodes::ERR_VALIDATION_002, 'تعطیلات یافت نشد', 404);
|
||||
@@ -501,6 +543,12 @@ class AppointmentSettingsController extends BaseController
|
||||
#[Route('/api/v1/appointment-settings/holidays', methods: ['POST'])]
|
||||
public function createHoliday(Request $request, #[CurrentUser] User $user): JsonResponse
|
||||
{
|
||||
// پیشچکِ منشی، پیش از هر واکشی. چکِ اصلی (denyDoctorAccess) به پزشکِ
|
||||
// همان رکورد نیاز دارد و بالا نمیرود؛ ولی سهمِ منشی از آن همیشه همین
|
||||
// توگل است، پس این خط هیچ مسیرِ مجازی نمیبندد و فقط ۴۰۴ را به ۴۰۳
|
||||
// تبدیل میکند. یافتهٔ ۱۰ آدیت ۲۰۲۶-۰۸-۰۷.
|
||||
$this->secretaryAccess->denyUnlessGranted($user, 'appointment_settings', 'update');
|
||||
|
||||
$data = json_decode($request->getContent(), true) ?? [];
|
||||
$doctorUuid = trim($data['doctor_uuid'] ?? '');
|
||||
$startStr = trim($data['start_date'] ?? '');
|
||||
@@ -541,6 +589,12 @@ class AppointmentSettingsController extends BaseController
|
||||
#[Route('/api/v1/appointment-settings/holidays/{uuid}', methods: ['PATCH'])]
|
||||
public function updateHoliday(string $uuid, Request $request, #[CurrentUser] User $user): JsonResponse
|
||||
{
|
||||
// پیشچکِ منشی، پیش از هر واکشی. چکِ اصلی (denyDoctorAccess) به پزشکِ
|
||||
// همان رکورد نیاز دارد و بالا نمیرود؛ ولی سهمِ منشی از آن همیشه همین
|
||||
// توگل است، پس این خط هیچ مسیرِ مجازی نمیبندد و فقط ۴۰۴ را به ۴۰۳
|
||||
// تبدیل میکند. یافتهٔ ۱۰ آدیت ۲۰۲۶-۰۸-۰۷.
|
||||
$this->secretaryAccess->denyUnlessGranted($user, 'appointment_settings', 'update');
|
||||
|
||||
$holiday = $this->holidayRepo->findByUuid($uuid);
|
||||
if ($holiday === null) {
|
||||
return $this->error(ErrorCodes::ERR_VALIDATION_002, 'تعطیلات یافت نشد', 404);
|
||||
|
||||
@@ -62,6 +62,10 @@ class MyAppointmentsController extends BaseController
|
||||
private readonly \App\Resource\Service\ResourceBookingSlotService $resourceSlots,
|
||||
private readonly \App\Appointment\Availability\Service\ResourceOccupier $occupier,
|
||||
private readonly \App\Treatment\Service\SessionBookingLink $sessionLink,
|
||||
// اتصال نوبت به جلسهٔ درمان جفتِ [entityType, entityId] میخواهد. تا پیش از
|
||||
// ۲۰۲۶-۰۸-۰۸ همینجا صدا زده میشد ولی هرگز تزریق نشده بود، پس هر درخواستِ
|
||||
// دارای `treatment_session_uuid` روی «Undefined property» ۵۰۰ میگرفت.
|
||||
private readonly \App\Doctor\Service\AddressResolver $branches,
|
||||
) {}
|
||||
|
||||
/**
|
||||
|
||||
Reference in New Issue
Block a user