import { TRPCError } from "@trpc/server" import { cookies, headers } from "next/headers" import { redirect } from "next/navigation" import { Lang } from "@scandic-hotels/common/constants/language" import { login } from "@scandic-hotels/common/constants/routes/handleAuth" import { createLogger } from "@scandic-hotels/common/logger/createLogger" import { createContext } from "@scandic-hotels/trpc/context" import { getBasicUser } from "@scandic-hotels/trpc/routers/user/utils/getBasicUser" import { getVerifiedUser } from "@scandic-hotels/trpc/routers/user/utils/getVerifiedUser" import { appServerClient, configureServerClient, } from "@scandic-hotels/trpc/serverClient" import { isValidSession } from "@scandic-hotels/trpc/utils/session" import { webviews } from "@/constants/routes/webviews" import { auth } from "@/auth" import type { Session } from "next-auth" export async function createAppContext() { const headersList = await headers() const cookie = await cookies() const webviewTokenCookie = cookie.get("webviewToken") const loginType = headersList.get("loginType") async function getUserSession(): Promise { const session = await auth() const webToken = webviewTokenCookie?.value if (!session?.token && !webToken) { return null } return ( session || ({ token: { access_token: webToken, loginType }, } as Session) ) } const ctx = createContext({ app: "scandic-web", lang: headersList.get("x-lang") as Lang, pathname: headersList.get("x-pathname")!, uid: headersList.get("x-uid"), url: headersList.get("x-url")!, webToken: webviewTokenCookie?.value, contentType: headersList.get("x-contenttype")!, auth: async () => await getUserSession(), getScandicUserToken: async () => { const session = await getUserSession() if (!isValidSession(session)) { return null } return session?.token?.access_token ?? null }, getUserPointsBalance: async () => { const session = await getUserSession() if (!session) return null const user = await getVerifiedUser({ token: { expires_at: session.token.expires_at ?? 0, access_token: session.token.access_token, }, }) if (!user) { return null } return user.membership?.currentPoints ?? 0 }, getScandicUser: async (input) => { const session = await getUserSession() if (!session) return null const user = await getVerifiedUser({ token: { expires_at: session.token.expires_at ?? 0, access_token: session.token.access_token, }, includeExtendedPartnerData: input?.withExtendedPartnerData, }) return user ?? null }, getScandicBasicUser: async () => { const session = await getUserSession() if (!session) return null const user = await getBasicUser({ token: { expires_at: session.token.expires_at ?? 0, access_token: session.token.access_token, }, }) return user ?? null }, }) return ctx } configureServerClient(createAppContext) const serverClientLogger = createLogger("serverClient") export async function serverClient() { const ctx = await createAppContext() return appServerClient(ctx, { onError: ({ ctx, error }) => { if (error instanceof TRPCError) { if (error.code === "UNAUTHORIZED") { let lang = Lang.en let pathname = "/" let fullUrl = "/" if (ctx) { lang = ctx.lang pathname = ctx.pathname fullUrl = ctx.url } const fullPathname = new URL(fullUrl).pathname if (webviews.includes(fullPathname)) { const redirectUrl = `/${lang}/webview/refresh?returnurl=${encodeURIComponent(fullPathname)}` serverClientLogger.debug( "Unautorized in webview, redirecting to: ", redirectUrl ) redirect(redirectUrl) } const redirectUrl = `${login[lang]}?redirectTo=${encodeURIComponent(`/${lang}/${pathname}`)}` serverClientLogger.debug( `[serverClient] onError redirecting to: ${redirectUrl}` ) redirect(redirectUrl) } } }, }) }