feat: implement booking page error boundary (#20492)

* implement booking page error boundary

* use it
This commit is contained in:
Benny Joo
2025-04-01 22:13:18 +00:00
committed by GitHub
parent 01ca2ca3de
commit b5b4134b75
5 changed files with 101 additions and 68 deletions
@@ -0,0 +1,17 @@
import { captureReactException } from "@sentry/nextjs";
import React from "react";
import { ErrorBoundary } from "react-error-boundary";
import { ErrorPage } from "./error-page";
export default function BookingPageErrorBoundary({ children }: { children: React.ReactNode }) {
return (
<ErrorBoundary
fallbackRender={({ error }) => <ErrorPage error={error} message={`${error}`} displayDebug={true} />}
onError={(error, info) => {
captureReactException(error, info);
}}>
{children}
</ErrorBoundary>
);
}
+17 -13
View File
@@ -5,6 +5,8 @@ import { getBookerWrapperClasses } from "@calcom/features/bookings/Booker/utils/
import { type PageProps } from "@lib/d/[link]/[slug]/getServerSideProps";
import BookingPageErrorBoundary from "@components/error/BookingPageErrorBoundary";
export default function Type({
slug,
isEmbed,
@@ -18,18 +20,20 @@ export default function Type({
durationConfig,
}: PageProps) {
return (
<main className={getBookerWrapperClasses({ isEmbed: !!isEmbed })}>
<Booker
username={user}
eventSlug={slug}
bookingData={booking}
hideBranding={isBrandingHidden}
isTeamEvent={isTeamEvent}
entity={entity}
duration={duration}
hashedLink={hashedLink}
durationConfig={durationConfig}
/>
</main>
<BookingPageErrorBoundary>
<main className={getBookerWrapperClasses({ isEmbed: !!isEmbed })}>
<Booker
username={user}
eventSlug={slug}
bookingData={booking}
hideBranding={isBrandingHidden}
isTeamEvent={isTeamEvent}
entity={entity}
duration={duration}
hashedLink={hashedLink}
durationConfig={durationConfig}
/>
</main>
</BookingPageErrorBoundary>
);
}
@@ -8,22 +8,26 @@ import { getBookerWrapperClasses } from "@calcom/features/bookings/Booker/utils/
import type { getServerSideProps } from "@lib/org/[orgSlug]/instant-meeting/team/[slug]/[type]/getServerSideProps";
import type { inferSSRProps } from "@lib/types/inferSSRProps";
import BookingPageErrorBoundary from "@components/error/BookingPageErrorBoundary";
export type Props = inferSSRProps<typeof getServerSideProps> & EmbedProps;
function Type({ slug, user, booking, isEmbed, isBrandingHidden, entity, eventTypeId, duration }: Props) {
return (
<main className={getBookerWrapperClasses({ isEmbed: !!isEmbed })}>
<Booker
username={user}
eventSlug={slug}
bookingData={booking}
hideBranding={isBrandingHidden}
isTeamEvent
isInstantMeeting
entity={{ ...entity, eventTypeId: eventTypeId }}
duration={duration}
/>
</main>
<BookingPageErrorBoundary>
<main className={getBookerWrapperClasses({ isEmbed: !!isEmbed })}>
<Booker
username={user}
eventSlug={slug}
bookingData={booking}
hideBranding={isBrandingHidden}
isTeamEvent
isInstantMeeting
entity={{ ...entity, eventTypeId: eventTypeId }}
duration={duration}
/>
</main>
</BookingPageErrorBoundary>
);
}
+28 -24
View File
@@ -9,6 +9,8 @@ import { getBookerWrapperClasses } from "@calcom/features/bookings/Booker/utils/
import type { getServerSideProps } from "@lib/team/[slug]/[type]/getServerSideProps";
import type { inferSSRProps } from "@lib/types/inferSSRProps";
import BookingPageErrorBoundary from "@components/error/BookingPageErrorBoundary";
export type PageProps = inferSSRProps<typeof getServerSideProps> & EmbedProps;
export const getMultipleDurationValue = (
@@ -37,30 +39,32 @@ function Type({
const searchParams = useSearchParams();
return (
<main className={getBookerWrapperClasses({ isEmbed: !!isEmbed })}>
<Booker
username={user}
eventSlug={slug}
bookingData={booking}
isInstantMeeting={isInstantMeeting}
hideBranding={isBrandingHidden}
isTeamEvent
entity={{ ...eventData.entity, eventTypeId: eventData?.eventTypeId }}
durationConfig={eventData.metadata?.multipleDuration}
/* TODO: Currently unused, evaluate it is needed-
* Possible alternative approach is to have onDurationChange.
*/
duration={getMultipleDurationValue(
eventData.metadata?.multipleDuration,
searchParams?.get("duration"),
eventData.length
)}
orgBannerUrl={orgBannerUrl}
teamMemberEmail={teamMemberEmail}
crmOwnerRecordType={crmOwnerRecordType}
crmAppSlug={crmAppSlug}
/>
</main>
<BookingPageErrorBoundary>
<main className={getBookerWrapperClasses({ isEmbed: !!isEmbed })}>
<Booker
username={user}
eventSlug={slug}
bookingData={booking}
isInstantMeeting={isInstantMeeting}
hideBranding={isBrandingHidden}
isTeamEvent
entity={{ ...eventData.entity, eventTypeId: eventData?.eventTypeId }}
durationConfig={eventData.metadata?.multipleDuration}
/* TODO: Currently unused, evaluate it is needed-
* Possible alternative approach is to have onDurationChange.
*/
duration={getMultipleDurationValue(
eventData.metadata?.multipleDuration,
searchParams?.get("duration"),
eventData.length
)}
orgBannerUrl={orgBannerUrl}
teamMemberEmail={teamMemberEmail}
crmOwnerRecordType={crmOwnerRecordType}
crmAppSlug={crmAppSlug}
/>
</main>
</BookingPageErrorBoundary>
);
}
@@ -8,6 +8,8 @@ import { getBookerWrapperClasses } from "@calcom/features/bookings/Booker/utils/
import type { inferSSRProps } from "@lib/types/inferSSRProps";
import BookingPageErrorBoundary from "@components/error/BookingPageErrorBoundary";
import type { getServerSideProps } from "@server/lib/[user]/[type]/getServerSideProps";
export type PageProps = inferSSRProps<typeof getServerSideProps> & EmbedProps;
@@ -26,25 +28,27 @@ function Type({ slug, user, isEmbed, booking, isBrandingHidden, eventData, orgBa
const searchParams = useSearchParams();
return (
<main className={getBookerWrapperClasses({ isEmbed: !!isEmbed })}>
<Booker
username={user}
eventSlug={slug}
bookingData={booking}
hideBranding={isBrandingHidden}
entity={{ ...eventData.entity, eventTypeId: eventData?.id }}
durationConfig={eventData.metadata?.multipleDuration}
orgBannerUrl={orgBannerUrl}
/* TODO: Currently unused, evaluate it is needed-
* Possible alternative approach is to have onDurationChange.
*/
duration={getMultipleDurationValue(
eventData.metadata?.multipleDuration,
searchParams?.get("duration"),
eventData.length
)}
/>
</main>
<BookingPageErrorBoundary>
<main className={getBookerWrapperClasses({ isEmbed: !!isEmbed })}>
<Booker
username={user}
eventSlug={slug}
bookingData={booking}
hideBranding={isBrandingHidden}
entity={{ ...eventData.entity, eventTypeId: eventData?.id }}
durationConfig={eventData.metadata?.multipleDuration}
orgBannerUrl={orgBannerUrl}
/* TODO: Currently unused, evaluate it is needed-
* Possible alternative approach is to have onDurationChange.
*/
duration={getMultipleDurationValue(
eventData.metadata?.multipleDuration,
searchParams?.get("duration"),
eventData.length
)}
/>
</main>
</BookingPageErrorBoundary>
);
}