From 7e585b2d9a8c0dddaf88618e3464602481f96168 Mon Sep 17 00:00:00 2001 From: Anton Gunnarsson Date: Thu, 4 Sep 2025 07:45:14 +0000 Subject: [PATCH] Merged in chore/more-partner-sas-boilerplate (pull request #2756) chore: Misc for partner-sas * Add global-error to partner-sas * Add redirect to lang in partner-sas * Actually use language from param * Increase test timeouts and use parsed lang to fix tests * Remove need to import serverClient to setup trpc Approved-by: Hrishikesh Vaipurkar --- apps/partner-sas/app/[lang]/layout.tsx | 16 +-- .../app/[lang]/middleware-error/404/page.tsx | 2 +- apps/partner-sas/app/global-error.tsx | 124 ++++++++++++++++++ apps/partner-sas/app/layout.tsx | 11 ++ apps/partner-sas/app/page.tsx | 5 + apps/partner-sas/i18n/serverContext.ts | 6 +- apps/partner-sas/lib/trpc.ts | 4 +- apps/partner-sas/middleware.ts | 15 +-- apps/partner-sas/playwright.config.ts | 5 +- 9 files changed, 162 insertions(+), 26 deletions(-) create mode 100644 apps/partner-sas/app/global-error.tsx create mode 100644 apps/partner-sas/app/layout.tsx create mode 100644 apps/partner-sas/app/page.tsx diff --git a/apps/partner-sas/app/[lang]/layout.tsx b/apps/partner-sas/app/[lang]/layout.tsx index af717b698..3a7637130 100644 --- a/apps/partner-sas/app/[lang]/layout.tsx +++ b/apps/partner-sas/app/[lang]/layout.tsx @@ -10,8 +10,6 @@ import { NuqsAdapter } from "@scandic-hotels/booking-flow/utils/nuqs" import { Lang } from "@scandic-hotels/common/constants/language" import { TrpcProvider } from "@scandic-hotels/trpc/Provider" -import { serverClient } from "@/lib/trpc" - import { getMessages } from "@/i18n" import ClientIntlProvider from "@/i18n/Provider" import { setLang } from "@/i18n/serverContext" @@ -41,17 +39,13 @@ type RootLayoutProps = { } export default async function RootLayout(props: RootLayoutProps) { - // const params = await props.params - const lang = Lang.en //params.lang + const params = await props.params + const lang = params.lang const { children } = props - setLang(lang) - const messages = await getMessages(lang) - - // TODO we need this import right now to ensure configureServerClient is called, - // but check where we do this - const _caller = await serverClient() + const parsedLanguage = setLang(lang) + const messages = await getMessages(parsedLanguage) return ( @@ -60,7 +54,7 @@ export default async function RootLayout(props: RootLayoutProps) {
diff --git a/apps/partner-sas/app/[lang]/middleware-error/404/page.tsx b/apps/partner-sas/app/[lang]/middleware-error/404/page.tsx index d61fa34cb..5bbeb77e9 100644 --- a/apps/partner-sas/app/[lang]/middleware-error/404/page.tsx +++ b/apps/partner-sas/app/[lang]/middleware-error/404/page.tsx @@ -1,4 +1,4 @@ export default function NotFoundPage() { // eslint-disable-next-line formatjs/no-literal-string-in-jsx - return
Not found, forgot lang in url?
+ return
Not Found
} diff --git a/apps/partner-sas/app/global-error.tsx b/apps/partner-sas/app/global-error.tsx new file mode 100644 index 000000000..d457bc4c5 --- /dev/null +++ b/apps/partner-sas/app/global-error.tsx @@ -0,0 +1,124 @@ +"use client" + +import * as Sentry from "@sentry/nextjs" +import { useEffect } from "react" + +import { logger } from "@scandic-hotels/common/logger" + +// TODO verify how this looks with someone +/* eslint-disable formatjs/no-literal-string-in-jsx */ +export default function GlobalError({ + error, +}: { + error: Error & { digest?: string } +}) { + logger.error("Global Error", { global_error: error }) + + useEffect(() => { + Sentry.captureException(error) + }, [error]) + + return ( + + + + + +
+

SORRY, SOMETHING WENT WRONG!

+ +

+ + { + "While we're working hard to fix it, you can always give us a call:" + } + +

+ + + +

+ + You can also switch languages to try if it works better this way: + +

+ + +

+ Thanks for your patience! +

+
+ + + ) +} diff --git a/apps/partner-sas/app/layout.tsx b/apps/partner-sas/app/layout.tsx new file mode 100644 index 000000000..f19baa541 --- /dev/null +++ b/apps/partner-sas/app/layout.tsx @@ -0,0 +1,11 @@ +import { configureTrpc } from "@/lib/trpc" + +configureTrpc() + +export default function RootLayout({ + children, +}: { + children: React.ReactNode +}) { + return <>{children} +} diff --git a/apps/partner-sas/app/page.tsx b/apps/partner-sas/app/page.tsx new file mode 100644 index 000000000..49a5e977e --- /dev/null +++ b/apps/partner-sas/app/page.tsx @@ -0,0 +1,5 @@ +import { redirect } from "next/navigation" + +export default function Page() { + redirect("/en") +} diff --git a/apps/partner-sas/i18n/serverContext.ts b/apps/partner-sas/i18n/serverContext.ts index 9e191b7a9..572badb38 100644 --- a/apps/partner-sas/i18n/serverContext.ts +++ b/apps/partner-sas/i18n/serverContext.ts @@ -18,7 +18,11 @@ const getRef = cache(() => ({ current: undefined as Lang | undefined })) */ export function setLang(newLang: Lang) { const parseResult = languageSchema.safeParse(newLang) - getRef().current = parseResult.success ? parseResult.data : Lang.en + const parsedLanguage = parseResult.success ? parseResult.data : Lang.en + + getRef().current = parsedLanguage + + return parsedLanguage } /** diff --git a/apps/partner-sas/lib/trpc.ts b/apps/partner-sas/lib/trpc.ts index 4ba549d84..eada8f0fe 100644 --- a/apps/partner-sas/lib/trpc.ts +++ b/apps/partner-sas/lib/trpc.ts @@ -25,7 +25,9 @@ export async function createAppContext() { return ctx } -configureServerClient(createAppContext) +export function configureTrpc() { + configureServerClient(createAppContext) +} export async function serverClient() { const ctx = await createAppContext() diff --git a/apps/partner-sas/middleware.ts b/apps/partner-sas/middleware.ts index 785855436..de77f1c78 100644 --- a/apps/partner-sas/middleware.ts +++ b/apps/partner-sas/middleware.ts @@ -23,16 +23,11 @@ export const middleware: NextMiddleware = async (request, event) => { // Default to English if no lang is found. headers.set("x-lang", Lang.en) - return NextResponse.rewrite( - new URL(`/${Lang.en}/middleware-error/404`, request.nextUrl), - { - request: { - headers, - }, - status: 404, - statusText: "Not found", - } - ) + return NextResponse.next({ + request: { + headers, + }, + }) } // Note that the order of middlewares is important since that is the order they are matched by. diff --git a/apps/partner-sas/playwright.config.ts b/apps/partner-sas/playwright.config.ts index 210215d9c..1d67c1806 100644 --- a/apps/partner-sas/playwright.config.ts +++ b/apps/partner-sas/playwright.config.ts @@ -23,19 +23,20 @@ export default defineConfig({ workers: process.env.CI ? 1 : undefined, /* Reporter to use. See https://playwright.dev/docs/test-reporters */ reporter: "html", + timeout: 120_000, /* Shared settings for all the projects below. See https://playwright.dev/docs/api/class-testoptions. */ use: { /* Base URL to use in actions like `await page.goto('/')`. */ baseURL: "http://localhost:3001", /* How long to wait for actions to complete. */ - actionTimeout: 15 * 1000, + actionTimeout: 60_000, /* Collect trace when retrying the failed test. See https://playwright.dev/docs/trace-viewer */ trace: process.env.CI ? "on-first-retry" : "retain-on-failure", }, expect: { - timeout: 10_000, + timeout: 60_000, }, /* Configure projects for major browsers */