From 8e20429ebced80ca70d51bdfd46a838a43d7e5f0 Mon Sep 17 00:00:00 2001 From: Doug Schrashun Date: Thu, 9 Jan 2025 10:27:24 -0500 Subject: [PATCH] fix up new pages with translations and meta --- frontend/src/app/[locale]/error.tsx | 14 ----------- frontend/src/app/[locale]/error/page.tsx | 25 +++++++++++++++---- frontend/src/app/[locale]/not-found.tsx | 2 +- .../src/app/[locale]/unauthorized/page.tsx | 21 +++++++++++++--- frontend/src/i18n/messages/en/index.ts | 11 +++++++- frontend/src/middleware.ts | 2 +- 6 files changed, 49 insertions(+), 26 deletions(-) delete mode 100644 frontend/src/app/[locale]/error.tsx diff --git a/frontend/src/app/[locale]/error.tsx b/frontend/src/app/[locale]/error.tsx deleted file mode 100644 index 56996be15..000000000 --- a/frontend/src/app/[locale]/error.tsx +++ /dev/null @@ -1,14 +0,0 @@ -"use client"; - -import { GridContainer } from "@trussworks/react-uswds"; - -const TopLevelError = ({ error }: { error: Error }) => { - return ( - -

Error

-
{error.message}
-
- ); -}; - -export default TopLevelError; diff --git a/frontend/src/app/[locale]/error/page.tsx b/frontend/src/app/[locale]/error/page.tsx index ba6212b31..925b16626 100644 --- a/frontend/src/app/[locale]/error/page.tsx +++ b/frontend/src/app/[locale]/error/page.tsx @@ -1,14 +1,29 @@ -"use client"; +import { Metadata } from "next"; +import { useTranslations } from "next-intl"; +import { getTranslations } from "next-intl/server"; import { GridContainer } from "@trussworks/react-uswds"; -const Unauthorized = () => { +import ServerErrorAlert from "src/components/ServerErrorAlert"; + +export async function generateMetadata() { + const t = await getTranslations(); + const meta: Metadata = { + title: t("ErrorPages.generic_error.page_title"), + description: t("Index.meta_description"), + }; + return meta; +} + +// not a NextJS error page - this is here to be redirected to manually in cases +// where Next's error handling situation doesn't quite do what we need. +const TopLevelError = () => { + const t = useTranslations("Errors"); return ( -

Error

-
Oops, something went wrong. Please try again.
+
); }; -export default Unauthorized; +export default TopLevelError; diff --git a/frontend/src/app/[locale]/not-found.tsx b/frontend/src/app/[locale]/not-found.tsx index ce0e2e360..d280024aa 100644 --- a/frontend/src/app/[locale]/not-found.tsx +++ b/frontend/src/app/[locale]/not-found.tsx @@ -10,7 +10,7 @@ import BetaAlert from "src/components/BetaAlert"; export async function generateMetadata() { const t = await getTranslations(); const meta: Metadata = { - title: t("ErrorPages.page_not_found.title"), + title: t("ErrorPages.page_not_found.page_title"), description: t("Index.meta_description"), }; return meta; diff --git a/frontend/src/app/[locale]/unauthorized/page.tsx b/frontend/src/app/[locale]/unauthorized/page.tsx index 11e0c7dc1..e0813b2c4 100644 --- a/frontend/src/app/[locale]/unauthorized/page.tsx +++ b/frontend/src/app/[locale]/unauthorized/page.tsx @@ -1,12 +1,25 @@ -"use client"; +import { Metadata } from "next"; -import { GridContainer } from "@trussworks/react-uswds"; +import { useTranslations } from "next-intl"; +import { getTranslations } from "next-intl/server"; +import { Alert, GridContainer } from "@trussworks/react-uswds"; + +export async function generateMetadata() { + const t = await getTranslations(); + const meta: Metadata = { + title: t("ErrorPages.unauthorized.page_title"), + description: t("Index.meta_description"), + }; + return meta; +} const Unauthorized = () => { + const t = useTranslations("Errors"); return ( -

Unauthorized

-
Unable to log in
+ + {t("authorization_fail")} +
); }; diff --git a/frontend/src/i18n/messages/en/index.ts b/frontend/src/i18n/messages/en/index.ts index 1a1cb567c..3cc2b734b 100644 --- a/frontend/src/i18n/messages/en/index.ts +++ b/frontend/src/i18n/messages/en/index.ts @@ -463,8 +463,14 @@ export const messages = { "The Simpler.Grants.gov email subscriptions are powered by the Sendy data service. Personal information is not stored within Simpler.Grants.gov.", }, ErrorPages: { - page_title: "Page Not Found | Simpler.Grants.gov", + generic_error: { + page_title: "Error | Simpler.Grants.gov", + }, + unauthorized: { + page_title: "Unauthorized | Simpler.Grants.gov", + }, page_not_found: { + page_title: "Page Not Found | Simpler.Grants.gov", title: "Oops! Page Not Found", message_content_1: "The page you have requested cannot be displayed because it does not exist, has been moved, or the server has been instructed not to let you view it. There is nothing to see here.", @@ -521,6 +527,9 @@ export const messages = { Errors: { heading: "We're sorry.", generic_message: "There seems to have been an error.", + try_again: "Please try again.", + unauthorized: "Unauthorized", + authorization_fail: "Login or user authorization failed. Please try again.", }, Search: { title: "Search Funding Opportunities | Simpler.Grants.gov", diff --git a/frontend/src/middleware.ts b/frontend/src/middleware.ts index 30b27ce1b..039e8cac6 100644 --- a/frontend/src/middleware.ts +++ b/frontend/src/middleware.ts @@ -44,7 +44,7 @@ export default function middleware(request: NextRequest): NextResponse { request, i18nMiddleware(request), ); - // in Next 15 there is an experimantal `unauthorized` function that will send a 401 + // in Next 15 there is an experimental `unauthorized` function that will send a 401 // code to the client and display an unauthorized page // see https://nextjs.org/docs/app/api-reference/functions/unauthorized // For now we can set status codes on auth redirect errors here