Add guest management functionality to existing bookings#3
Conversation
* feat: ability to add guests via app.cal.com/bookings * fix: some update * fix: minor issue * fix: final update * update * update * add requested changes * fix type error * small update * final update * fix type error * fix location * update calender event --------- Co-authored-by: Somay Chauhan <somaychauhan98@gmail.com>
There was a problem hiding this comment.
Pull request overview
This PR adds functionality to allow users to add additional guests to existing bookings. The feature includes a new dialog interface for email input with validation, backend support for updating bookings and calendar events, and automated email notifications.
Changes:
- Added a new
MultiEmailUI component for managing multiple email inputs with validation - Implemented a tRPC endpoint
addGueststhat validates permissions, filters duplicate/blacklisted emails, updates the database, and syncs with calendar providers - Created email templates for notifying organizers and attendees about newly added guests
Reviewed changes
Copilot reviewed 15 out of 15 changed files in this pull request and generated 5 comments.
Show a summary per file
| File | Description |
|---|---|
| packages/ui/index.tsx | Exports the new MultiEmail component |
| packages/ui/form/MultiEmailLazy.tsx | Lazy-loaded wrapper for the MultiEmail component |
| packages/ui/form/MultiEmail.tsx | UI component for adding/removing multiple email addresses |
| packages/trpc/server/routers/viewer/bookings/addGuests.schema.ts | Zod schema for validating addGuests input |
| packages/trpc/server/routers/viewer/bookings/addGuests.handler.ts | Backend handler for adding guests to bookings |
| packages/trpc/server/routers/viewer/bookings/_router.tsx | Registers the addGuests tRPC endpoint |
| packages/emails/templates/organizer-add-guests-email.ts | Email template for notifying organizers |
| packages/emails/templates/attendee-add-guests-email.ts | Email template for notifying attendees |
| packages/emails/src/templates/index.ts | Exports new email template components |
| packages/emails/src/templates/OrganizerAddGuestsEmail.tsx | React component for organizer email |
| packages/emails/src/templates/AttendeeAddGuestsEmail.tsx | React component for attendee email |
| packages/emails/email-manager.ts | Implements sendAddGuestsEmails function to dispatch emails |
| apps/web/public/static/locales/en/common.json | Adds localization strings for the new feature |
| apps/web/components/dialog/AddGuestsDialog.tsx | Dialog component for adding guests |
| apps/web/components/booking/BookingListItem.tsx | Integrates AddGuestsDialog into the booking list UI |
Comments suppressed due to low confidence (1)
packages/emails/email-manager.ts:1
- The BLACKLISTED_GUEST_EMAILS environment variable is used but not documented. Add a comment explaining its purpose and expected format (comma-separated email list).
// eslint-disable-next-line no-restricted-imports
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
| if (!booking) throw new TRPCError({ code: "NOT_FOUND", message: "booking_not_found" }); | ||
|
|
||
| const isTeamAdminOrOwner = | ||
| (await isTeamAdmin(user.id, booking.eventType?.teamId ?? 0)) && |
There was a problem hiding this comment.
The condition uses AND (&&) instead of OR (||), requiring the user to be both a team admin AND owner. This will always be false since a user cannot simultaneously satisfy both conditions. Change to || to allow either role.
| (await isTeamAdmin(user.id, booking.eventType?.teamId ?? 0)) && | |
| (await isTeamAdmin(user.id, booking.eventType?.teamId ?? 0)) || |
| <></> | ||
| )} |
There was a problem hiding this comment.
Replace empty fragment <></> with null for better readability and convention when rendering nothing.
| const ZAddGuestsInputSchema = z.array(z.string().email()).refine((emails) => { | ||
| const uniqueEmails = new Set(emails); | ||
| return uniqueEmails.size === emails.length; | ||
| }); |
There was a problem hiding this comment.
The uniqueness validation is duplicated between the client (AddGuestsDialog) and server (addGuests.handler.ts). Consider moving this schema to a shared location or relying solely on server-side validation.
| const uniqueGuests = guests.filter( | ||
| (guest) => | ||
| !booking.attendees.some((attendee) => guest === attendee.email) && | ||
| !blacklistedGuestEmails.includes(guest) | ||
| ); |
There was a problem hiding this comment.
Consider using guest.toLowerCase() when comparing against attendee emails and blacklisted emails to ensure case-insensitive matching, since email addresses are case-insensitive.
| try { | ||
| await sendAddGuestsEmails(evt, guests); | ||
| } catch (err) { | ||
| console.log("Error sending AddGuestsEmails"); |
There was a problem hiding this comment.
The error message doesn't include the actual error details. Change to console.error('Error sending AddGuestsEmails', err) to include the error object for debugging.
| console.log("Error sending AddGuestsEmails"); | |
| console.error("Error sending AddGuestsEmails", err); |
Test 10nn
Summary by CodeRabbit
Release Notes
✏️ Tip: You can customize this high-level summary in your review settings.
nn---n*Replicated from [ai-code-review-evaluation/cal.com-coderabbit#10](https://github.com/ai-code-review-evaluation/cal.com-coderabbit/pull/10)*