diff --git a/apps/web/pages/api/link.ts b/apps/web/pages/api/link.ts index 9a0ebdba51..a2f51f2e1e 100644 --- a/apps/web/pages/api/link.ts +++ b/apps/web/pages/api/link.ts @@ -4,6 +4,7 @@ import { z } from "zod"; import { symmetricDecrypt } from "@calcom/lib/crypto"; import { defaultResponder } from "@calcom/lib/server"; import prisma from "@calcom/prisma"; +import { UserPermissionRole } from "@calcom/prisma/enums"; import { TRPCError } from "@calcom/trpc/server"; import { createContext } from "@calcom/trpc/server/createContext"; import { viewerRouter } from "@calcom/trpc/server/routers/viewer/_router"; @@ -38,9 +39,22 @@ async function handler(req: NextApiRequest, res: NextApiResponse) { where: { id: userId }, }); + /** We shape the session as required by tRPC router */ + async function sessionGetter() { + return { + user: { + id: userId, + username: "" /* Not used in this context */, + role: UserPermissionRole.USER, + }, + hasValidLicense: true, + expires: "" /* Not used in this context */, + }; + } + try { /** @see https://trpc.io/docs/server-side-calls */ - const ctx = await createContext({ req, res }); + const ctx = await createContext({ req, res }, sessionGetter); const caller = viewerRouter.createCaller({ ...ctx, req, @@ -55,7 +69,7 @@ async function handler(req: NextApiRequest, res: NextApiResponse) { }); } catch (e) { let message = "Error confirming booking"; - if (e instanceof TRPCError) message = e.message; + if (e instanceof TRPCError) message = (e as TRPCError).message; res.redirect(`/booking/${bookingUid}?error=${encodeURIComponent(message)}`); return; } diff --git a/packages/trpc/server/createContext.ts b/packages/trpc/server/createContext.ts index eee4d65acc..f7a0c565fd 100644 --- a/packages/trpc/server/createContext.ts +++ b/packages/trpc/server/createContext.ts @@ -61,10 +61,10 @@ export async function createContextInner(opts: CreateInnerContextOptions) { * Creates context for an incoming request * @link https://trpc.io/docs/context */ -export const createContext = async ({ req, res }: CreateContextOptions) => { +export const createContext = async ({ req, res }: CreateContextOptions, sessionGetter?: GetSessionFn) => { const locale = getLocaleFromHeaders(req); - - const contextInner = await createContextInner({ locale }); + const session = !!sessionGetter ? await sessionGetter({ req, res }) : null; + const contextInner = await createContextInner({ locale, session }); return { ...contextInner, req, diff --git a/packages/trpc/server/middlewares/sessionMiddleware.ts b/packages/trpc/server/middlewares/sessionMiddleware.ts index 922ff29bde..77d2f86efc 100644 --- a/packages/trpc/server/middlewares/sessionMiddleware.ts +++ b/packages/trpc/server/middlewares/sessionMiddleware.ts @@ -101,11 +101,18 @@ export async function getUserFromSession(ctx: TRPCContextInner, session: Maybe>; -const getUserSession = async (ctx: TRPCContextInner) => { - const { getServerSession } = await import("@calcom/features/auth/lib/getServerSession"); +const getSession = async (ctx: TRPCContextInner) => { const { req, res } = ctx; + const { getServerSession } = await import("@calcom/features/auth/lib/getServerSession"); + return req ? await getServerSession({ req, res }) : null; +}; - const session = req ? await getServerSession({ req, res }) : null; +const getUserSession = async (ctx: TRPCContextInner) => { + /** + * It is possible that the session and user have already been added to the context by a previous middleware + * or when creating the context + */ + const session = ctx.session || (await getSession(ctx)); const user = session ? await getUserFromSession(ctx, session) : null; return { user, session };