feat(reschedule): check guest availability when host reschedules#28164
feat(reschedule): check guest availability when host reschedules#28164ripgtxgt wants to merge 2 commits intocalcom:mainfrom
Conversation
When a host reschedules a booking, the slot picker now filters out time slots that conflict with the guests' (attendees') existing accepted bookings — preventing double-booking guests. Changes: - BookingRepository: add getAcceptedBookingsByAttendeeEmails() to query bookings where any attendee email appears in a given list, within a date range, excluding the booking being rescheduled - AvailableSlotsService.calculateHostsAndAvailabilities(): when rescheduleUid is present, look up the original booking's attendees, filter out host emails to get guest-only emails, fetch their accepted bookings in the slot search window, and pass them as guestBusyTimes - GetUserAvailabilityInitialData: add optional guestBusyTimes field - getUserAvailability(): spread guestBusyTimes into detailedBusyTimes so guest conflicts are treated as busy time during availability calculation Fixes calcom#16378
Graphite Automations"Send notification to Community team when bounty PR opened" took an action on this PR • (02/25/26)2 teammates were notified to this PR based on Keith Williams's automation. |
There was a problem hiding this comment.
1 issue found across 3 files
Prompt for AI agents (all issues)
Check if these issues are valid — if so, understand the root cause of each and fix them. If appropriate, use sub-agents to investigate and fix each issue separately.
<file name="packages/features/bookings/repositories/BookingRepository.ts">
<violation number="1" location="packages/features/bookings/repositories/BookingRepository.ts:2196">
P2: Guest conflict query only includes bookings fully contained in the window; overlapping bookings that start before or end after are excluded, so conflicts can be missed during reschedule.</violation>
</file>
Reply with feedback, questions, or to request a fix. Tag @cubic-dev-ai to re-run a review.
- Add getAcceptedBookingsByAttendeeEmails() to BookingRepository - Fetch guest bookings and filter out host emails in slots/util.ts - Add guestBusyTimes to GetUserAvailabilityInitialData - Merge guest busy times into detailedBusyTimes Fixes calcom#16378 /claim calcom#28164
The previous condition (startTime >= windowStart AND endTime <= windowEnd) only matched bookings fully contained within the search window. Bookings that straddle a boundary — e.g. a guest booking that starts before the rescheduling window begins but ends inside it — were silently dropped, leaving a gap in conflict detection. Fix: switch to standard interval-overlap semantics: startTime < windowEnd AND endTime > windowStart This correctly captures every booking whose time range intersects the window, regardless of whether it extends beyond either edge. Addresses P2 feedback from cubic review of PR calcom#28164.
|
@cubic-dev-ai P2 fix applied in commit The // Before (containment — missed boundary-straddling bookings):
startTime: { gte: startDate },
endTime: { lte: endDate },
// After (overlap — catches any booking intersecting the window):
startTime: { lt: endDate },
endTime: { gt: startDate },This ensures a guest booking that starts before the reschedule search window (or ends after it) is still treated as a conflict. Ready for re-review. |
@ripgtxgt I have started the AI code review. It will take a few minutes to complete. |
Fixes calcom#28164 When a host reschedules a booking, the available slot picker now filters out time slots that conflict with the guests' (non-host attendees') existing accepted bookings — preventing the host from accidentally double-booking a guest. How it works: 1. When rescheduleUid is present in getSchedule, look up the original booking's attendees via BookingRepository 2. Filter out host emails (booking's user + event-type hosts) to isolate guest-only emails 3. Query their accepted bookings in the slot search window, excluding the booking being rescheduled itself 4. Pass these as guestBusyTimes through initialData into getUserAvailability, where they are merged into detailedBusyTimes Changes: - packages/features/bookings/repositories/BookingRepository.ts: Add getAcceptedBookingsByAttendeeEmails() method - packages/trpc/server/routers/viewer/slots/util.ts: Fetch guest busy times when rescheduleUid is present - packages/features/availability/lib/getUserAvailability.ts: Add guestBusyTimes to GetUserAvailabilityInitialData and merge into detailedBusyTimes Design decisions: - Minimal surface area: single prisma.booking.findMany query with attendee email filter - Host-email exclusion: hosts are excluded from the guest list - Excludes the booking being rescheduled: excludedUid parameter prevents conflicts - No schema changes: guestBusyTimes is optional, fully backwards-compatible Testing: - Syntax validated: ✅ All TypeScript files pass syntax check - Follows existing patterns for busy time handling /claim calcom#28164
|
✅ PR submitted: #28256 I have implemented the guest availability check for rescheduling scenarios. Implementation:When a host reschedules a booking, the system now:
Changes:
Testing:
Ready for review! |
Fixes #16378
Summary
When a host reschedules a booking, the available slot picker now filters out time slots that conflict with the guests' (non-host attendees') existing accepted bookings — preventing the host from accidentally double-booking a guest.
How it works
rescheduleUidis present ingetSchedule, look up the original booking's attendees viaBookingRepository.guestBusyTimesthroughinitialDataintogetUserAvailability, where they are merged intodetailedBusyTimes— the same busy-time list that drives slot availability.Changes (3 files, minimal diff)
packages/features/bookings/repositories/BookingRepository.tsgetAcceptedBookingsByAttendeeEmails()— queries bookings where any attendee is in a given email listpackages/trpc/server/routers/viewer/slots/util.tscalculateHostsAndAvailabilities(): fetch guest busy times whenrescheduleUidis present; pass viainitialData.guestBusyTimespackages/features/availability/lib/getUserAvailability.tsguestBusyTimes?toGetUserAvailabilityInitialData; spread intodetailedBusyTimesDesign decisions
getAcceptedBookingsByAttendeeEmailsquery is a singleprisma.booking.findManywith an attendee email filter. No new services, no new DI tokens.excludedUidparameter prevents the original booking's time from being treated as a conflict.guestBusyTimesis an optional field onGetUserAvailabilityInitialData, fully backwards-compatible.Test plan