- Updated date handling in BlogSeoFields and ScheduleSection to use Tehran timezone utilities for consistency.
- Introduced `toTehranClockTime`, `tehranWallClockToUnix`, and `todayIso` functions for accurate date representation.
- Modified various components to utilize these new utilities, ensuring that date strings are correctly formatted and timestamps are accurately converted.
- Enhanced API documentation to clarify the handling of date fields, emphasizing the importance of server-local midnight.
- Added tests to verify that date overrides and holidays maintain the correct day without shifting due to timezone discrepancies.
- Introduced clinic_id to weekly_schedules, date_overrides, and holidays to differentiate between personal and clinic schedules.
- Updated unique constraints and indexes to accommodate the new clinic context.
feat(command): create AssignScheduleClinicCommand to move schedules
- Added a command to move a doctor's personal weekly schedule into a clinic context.
- Implemented checks to ensure sessions align with the target clinic.
feat(context): implement EntityContext and EntityContextResolver
- Created EntityContext to represent the effective working environment of a request (doctor or clinic).
- Developed EntityContextResolver to determine the execution context based on user roles and active contexts.
test: add ServiceModeContextTest for appointment scheduling
- Implemented tests to ensure service booking respects clinic and personal contexts.
- Verified that financial data is omitted in clinic contexts in InvitedDoctorDashboardScopeTest.
The API and React components were already parameterized by doctor uuid, but 14
copy-pasted identity checks limited every endpoint to "the doctor themselves or
an admin", so a clinic owner could not touch a member doctor's booking setup.
- Replaces those 14 checks with one denyDoctorAccess() that also admits the
owner of a clinic the doctor belongs to, and a member doctor holding the
clinic's appointment_settings permission (view for GET, update for writes).
A doctor's own settings short-circuit before any permission lookup.
- Moves ScheduleSection and its tabs out of DoctorDetailPage into
components/schedule/ScheduleSection.tsx so the doctor panel and the new
clinic page render the same module instead of one page importing another.
Pure relocation — no logic changed.
- Adds ClinicAppointmentSettingsPage: one tab per clinic doctor, each rendering
that same section. The tab wrapper is keyed by doctor uuid so in-progress
schedule edits cannot leak onto the wrong doctor.
- insurance-pricing accepts an optional doctor_uuid (query on GET, body on PUT)
under the same access rule, so the visit-price card works inside the clinic
tabs. Fixes saveInsurancePricing calling getInsurancePricing with the wrong
argument by extracting the shared pricingPayload().
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
- M2 GET /insurance/{id}: was unguarded; now owner-or-admin (403 otherwise) —
stops reading another doctor's negotiated price by id enumeration.
- M3 GET /clinic-pro/doctor-address/{id}: add the same owner/admin check the
sibling PATCH/DELETE already had.
- M4 POST/PATCH /service-item: staff_uuid must belong to the caller's tenant
(entity_type/entity_id) → 422; stops binding another tenant's staff.
- M5 appointment-settings list endpoints (date-override/holidays/
available-locations): add the per-doctor ownership check the sibling
single-record endpoints already enforce.
Regressions (6 negative cases fail without the fixes):
DoctorInsuranceOwnershipTest, DoctorAddressOwnershipTest,
ServiceItemStaffOwnershipTest, AppointmentSettingsListOwnershipTest.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Appointments now persist address_id resolved from the weekly-schedule
session (location_id) across all booking paths (online, secretary, admin).
On confirm, the patient is added to the clinic owning that address, or to
the doctor's single clinic as fallback. Weekly-schedule create/update now
requires location_id on every active session. PatientSession exposes
doctor_uuid/doctor_name so clinic records show which doctor each visit is for.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
- appointment-settings.md: weekly-schedule meta (online_booking_enabled,
booking_window value/unit), defaults, and the slot-gating behavior.
- appointment.md: new public month-availability endpoint (Gregorian
year/month, disabled/enabled dates) and the empty-slots conditions for
appointment-slots.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
- Added `clinic_id` and `type` fields to `DoctorAddress` entity to differentiate between personal and clinic addresses.
- Updated constructor to support creation of addresses for both doctors and clinics.
- Modified repository methods to handle new address types and added methods for counting and finding addresses by clinic.
- Implemented migration to update the database schema accordingly.
- Removed deprecated endpoint for creating addresses from clinics and updated related controller methods.
- Added new endpoints for managing clinic addresses, including CRUD operations.
- Updated frontend components to handle new address types and display accordingly.