{"record":{"id":"00526cde4cb87556","repo":"calcom/cal.diy","slug":"cannot-add-newguestcount-guests-this-booking-a","errorCode":null,"errorMessage":"Cannot add ${newGuestCount} guests. This booking already has ${currentGuestCount} attendees. Maximum total guests allowed is ${MAX_TOTAL_GUESTS_PER_BOOKING}. You can add up to ${remainingSlots} more guests.","messagePattern":"Cannot add (.+?) guests\\. This booking already has (.+?) attendees\\. Maximum total guests allowed is (.+?)\\. You can add up to (.+?) more guests\\.","errorType":"http","errorClass":"BadRequestException","httpStatus":400,"severity":"warning","filePath":"apps/api/v2/src/platform/bookings/2024-08-13/services/booking-guests.service.ts","lineNumber":34,"sourceCode":"  constructor(\n    private readonly bookingsRepository: BookingsRepository_2024_08_13,\n    private readonly bookingsService: BookingsService_2024_08_13,\n    private readonly platformBookingsService: PlatformBookingsService\n  ) {}\n\n  async addGuests(bookingUid: string, input: AddGuestsInput_2024_08_13, user: ApiAuthGuardUser) {\n    const booking = await this.bookingsRepository.getByUidWithAttendeesAndUserAndEvent(bookingUid);\n    if (!booking) {\n      throw new NotFoundException(`Booking with uid ${bookingUid} not found`);\n    }\n\n    const currentGuestCount = booking.attendees.length;\n    const newGuestCount = input.guests.length;\n    const totalGuestCount = currentGuestCount + newGuestCount;\n\n    if (totalGuestCount > MAX_TOTAL_GUESTS_PER_BOOKING) {\n      const remainingSlots = Math.max(0, MAX_TOTAL_GUESTS_PER_BOOKING - currentGuestCount);\n      throw new BadRequestException(\n        `Cannot add ${newGuestCount} guests. This booking already has ${currentGuestCount} attendees. ` +\n          `Maximum total guests allowed is ${MAX_TOTAL_GUESTS_PER_BOOKING}. You can add up to ${remainingSlots} more guests.`\n      );\n    }\n\n    const platformClientParams = booking.eventTypeId\n      ? await this.platformBookingsService.getOAuthClientParams(booking.eventTypeId)\n      : undefined;\n\n    const emailsEnabled = platformClientParams ? platformClientParams.arePlatformEmailsEnabled : true;\n\n    const res = await addGuestsHandler({\n      ctx: { user },\n      input: { bookingId: booking.id, guests: input.guests },\n      emailsEnabled,\n      actionSource: \"API_V2\",\n    });\n    if (res.message === \"Guests added\") {","sourceCodeStart":16,"sourceCodeEnd":52,"githubUrl":"https://github.com/calcom/cal.diy/blob/176037d0afbe572f870a3c702985e7cd83fe6c0c/apps/api/v2/src/platform/bookings/2024-08-13/services/booking-guests.service.ts#L16-L52","documentation":"A 400 BadRequestException thrown by BookingGuestsService_2024_08_13.addGuests when the sum of existing attendees plus new guests exceeds MAX_TOTAL_GUESTS_PER_BOOKING (hardcoded at 30). The error message includes the current count, requested count, the limit, and remaining slots to help the client adjust.","triggerScenarios":"POST /v2/bookings/{bookingUid}/guests with a guests array whose length, when added to the booking's existing attendees count (booking.attendees.length), exceeds 30. For example, a booking with 28 attendees where the client tries to add 3 more guests (28 + 3 = 31 > 30).","commonSituations":"Large group bookings where the organizer invites many guests. Automated systems bulk-adding guests without checking the limit first. A booking that already has many attendees from prior guest additions. Event types designed for large groups but hitting the platform-wide 30-guest cap.","solutions":["Read the error message — it tells you exactly how many guests you can still add (remainingSlots).","Reduce the number of guests in the request to fit within the remaining slots.","If you need more than 30 total attendees, consider using a different event type (e.g., a seated/routed event type) or contact Cal.com support about platform limits.","Call GET /v2/bookings/{bookingUid}/attendees first to check the current count before adding guests."],"exampleFix":"// before — trying to add 5 guests to a booking with 28 attendees\nPOST /v2/bookings/abc-123/guests\n{ \"guests\": [\"a@x.com\", \"b@x.com\", \"c@x.com\", \"d@x.com\", \"e@x.com\"] }\n// -> 400: Cannot add 5 guests. Already has 28. Max 30. Add up to 2 more.\n\n// after — add only 2 guests to stay within the limit\nPOST /v2/bookings/abc-123/guests\n{ \"guests\": [\"a@x.com\", \"b@x.com\"] }","handlingStrategy":"validation","validationCode":"// Check attendee count before adding guests to avoid exceeding the 30 limit\nconst MAX_TOTAL_GUESTS_PER_BOOKING = 30;\n\nasync function canAddGuests(token, bookingUid, guestCount) {\n  const res = await fetch(`/v2/bookings/${bookingUid}/attendees`, {\n    headers: { Authorization: `Bearer ${token}` }\n  });\n  if (!res.ok) return false;\n  const { data } = await res.json();\n  const currentCount = data.length;\n  const remaining = MAX_TOTAL_GUESTS_PER_BOOKING - currentCount;\n  return { canAdd: guestCount <= remaining, remaining };\n}\n\nconst { canAdd, remaining } = await canAddGuests(token, bookingUid, guests.length);\nif (!canAdd) {\n  throw new Error(`Cannot add ${guests.length} guests — only ${remaining} slots remaining`);\n}","typeGuard":null,"tryCatchPattern":"try {\n  await api.addGuests(bookingUid, guests);\n} catch (err) {\n  if (err.statusCode === 400 && err.message.includes('Maximum total guests')) {\n    // Parse remaining slots from the error message and add in batches\n    const remaining = parseRemainingSlots(err.message);\n    const batch = guests.slice(0, remaining);\n    if (batch.length > 0) await api.addGuests(bookingUid, batch);\n  } else { throw err; }\n}","preventionTips":["Fetch the current attendee count before adding guests to stay within the 30-guest limit.","Batch large guest lists to respect the remaining slots.","Consider whether a seated event type better suits large-group scenarios.","Cache the attendee count after each guest addition to avoid redundant calls."],"tags":["validation","booking","guests","limit","business-rule","nestjs"],"backgroundTag":null,"analyzedSha":"176037d0afbe572f870a3c702985e7cd83fe6c0c","analyzedAt":"2026-08-12T19:12:41.464Z","schemaVersion":2},"datasetVersion":"2026-08-12T23:17:12.415Z"}