feat(SW-190): added hero to static content pages
This commit is contained in:
@@ -1,6 +1,6 @@
|
|||||||
import { notFound } from "next/navigation"
|
import { notFound } from "next/navigation"
|
||||||
|
|
||||||
import ContentPage from "@/components/ContentType/ContentPage"
|
import ContentPage from "@/components/ContentType/ContentPage/ContentPage"
|
||||||
import HotelPage from "@/components/ContentType/HotelPage/HotelPage"
|
import HotelPage from "@/components/ContentType/HotelPage/HotelPage"
|
||||||
import LoyaltyPage from "@/components/ContentType/LoyaltyPage/LoyaltyPage"
|
import LoyaltyPage from "@/components/ContentType/LoyaltyPage/LoyaltyPage"
|
||||||
import { setLang } from "@/i18n/serverContext"
|
import { setLang } from "@/i18n/serverContext"
|
||||||
@@ -19,7 +19,7 @@ export default async function ContentTypePage({
|
|||||||
|
|
||||||
switch (params.contentType) {
|
switch (params.contentType) {
|
||||||
case "content-page":
|
case "content-page":
|
||||||
return <ContentPage />
|
return <ContentPage lang={params.lang} />
|
||||||
case "loyalty-page":
|
case "loyalty-page":
|
||||||
return <LoyaltyPage />
|
return <LoyaltyPage />
|
||||||
case "hotel-page":
|
case "hotel-page":
|
||||||
|
|||||||
@@ -1,3 +0,0 @@
|
|||||||
export default async function ContentPage() {
|
|
||||||
return null
|
|
||||||
}
|
|
||||||
47
components/ContentType/ContentPage/ContentPage.tsx
Normal file
47
components/ContentType/ContentPage/ContentPage.tsx
Normal file
@@ -0,0 +1,47 @@
|
|||||||
|
import { serverClient } from "@/lib/trpc/server"
|
||||||
|
|
||||||
|
import Hero from "@/components/TempDesignSystem/Hero"
|
||||||
|
import Preamble from "@/components/TempDesignSystem/Text/Preamble"
|
||||||
|
import Title from "@/components/TempDesignSystem/Text/Title"
|
||||||
|
import TrackingSDK from "@/components/TrackingSDK"
|
||||||
|
|
||||||
|
import Intro from "./Intro"
|
||||||
|
|
||||||
|
import styles from "./contentPage.module.css"
|
||||||
|
|
||||||
|
import type { LangParams } from "@/types/params"
|
||||||
|
|
||||||
|
export default async function ContentPage({ lang }: LangParams) {
|
||||||
|
const contentPageRes = await serverClient().contentstack.contentPage.get()
|
||||||
|
|
||||||
|
if (!contentPageRes) {
|
||||||
|
return null
|
||||||
|
}
|
||||||
|
|
||||||
|
const { tracking, contentPage } = contentPageRes
|
||||||
|
const heroImage = contentPage.hero_image
|
||||||
|
|
||||||
|
return (
|
||||||
|
<>
|
||||||
|
<section>
|
||||||
|
<header className={styles.header}>
|
||||||
|
<Intro>
|
||||||
|
<Title as="h2">{contentPage.header.heading}</Title>
|
||||||
|
<Preamble>{contentPage.header.preamble}</Preamble>
|
||||||
|
</Intro>
|
||||||
|
</header>
|
||||||
|
|
||||||
|
{heroImage ? (
|
||||||
|
<div className={styles.hero}>
|
||||||
|
<Hero
|
||||||
|
alt={heroImage.meta.alt || heroImage.meta.caption || ""}
|
||||||
|
src={heroImage.url}
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
) : null}
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<TrackingSDK pageData={tracking} />
|
||||||
|
</>
|
||||||
|
)
|
||||||
|
}
|
||||||
22
components/ContentType/ContentPage/Intro/index.tsx
Normal file
22
components/ContentType/ContentPage/Intro/index.tsx
Normal file
@@ -0,0 +1,22 @@
|
|||||||
|
import { PropsWithChildren } from "react"
|
||||||
|
|
||||||
|
import MaxWidth from "@/components/MaxWidth"
|
||||||
|
|
||||||
|
import styles from "./intro.module.css"
|
||||||
|
|
||||||
|
export default async function Intro({ children }: PropsWithChildren) {
|
||||||
|
return (
|
||||||
|
<div className={styles.intro}>
|
||||||
|
<MaxWidth variant="content" tag="div">
|
||||||
|
<MaxWidth
|
||||||
|
className={styles.content}
|
||||||
|
variant="text"
|
||||||
|
align="left"
|
||||||
|
tag="div"
|
||||||
|
>
|
||||||
|
{children}
|
||||||
|
</MaxWidth>
|
||||||
|
</MaxWidth>
|
||||||
|
</div>
|
||||||
|
)
|
||||||
|
}
|
||||||
@@ -0,0 +1,8 @@
|
|||||||
|
.intro {
|
||||||
|
padding: var(--Spacing-x4) var(--Spacing-x2);
|
||||||
|
}
|
||||||
|
|
||||||
|
.content {
|
||||||
|
display: grid;
|
||||||
|
gap: var(--Spacing-x3);
|
||||||
|
}
|
||||||
17
components/ContentType/ContentPage/contentPage.module.css
Normal file
17
components/ContentType/ContentPage/contentPage.module.css
Normal file
@@ -0,0 +1,17 @@
|
|||||||
|
.content {
|
||||||
|
display: grid;
|
||||||
|
padding-bottom: var(--Spacing-x9);
|
||||||
|
position: relative;
|
||||||
|
justify-content: center;
|
||||||
|
align-items: flex-start;
|
||||||
|
}
|
||||||
|
|
||||||
|
.header {
|
||||||
|
background-color: var(--Base-Surface-Subtle-Normal);
|
||||||
|
}
|
||||||
|
|
||||||
|
.hero {
|
||||||
|
display: grid;
|
||||||
|
justify-content: center;
|
||||||
|
padding: var(--Spacing-x4) var(--Spacing-x2);
|
||||||
|
}
|
||||||
@@ -9,7 +9,6 @@ import TrackingSDK from "@/components/TrackingSDK"
|
|||||||
|
|
||||||
import styles from "./loyaltyPage.module.css"
|
import styles from "./loyaltyPage.module.css"
|
||||||
|
|
||||||
import { ImageVaultAsset } from "@/types/components/imageVaultImage"
|
|
||||||
import type { LangParams } from "@/types/params"
|
import type { LangParams } from "@/types/params"
|
||||||
|
|
||||||
export default async function LoyaltyPage({ lang }: LangParams) {
|
export default async function LoyaltyPage({ lang }: LangParams) {
|
||||||
@@ -20,7 +19,7 @@ export default async function LoyaltyPage({ lang }: LangParams) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
const { tracking, loyaltyPage } = loyaltyPageRes
|
const { tracking, loyaltyPage } = loyaltyPageRes
|
||||||
const heroImage: ImageVaultAsset = loyaltyPage.header?.hero_image
|
const heroImage = loyaltyPage.hero_image
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
<section className={styles.content}>
|
<section className={styles.content}>
|
||||||
|
|||||||
@@ -1,17 +1,21 @@
|
|||||||
"use client"
|
"use client"
|
||||||
import { cva } from "class-variance-authority"
|
|
||||||
|
|
||||||
import styles from "./maxWidth.module.css"
|
import { maxWidthVariants } from "./variants"
|
||||||
|
|
||||||
import type { MaxWidthProps } from "@/types/components/max-width"
|
import type { MaxWidthProps } from "@/types/components/max-width"
|
||||||
|
|
||||||
const maxWidthVariants = cva(styles.container)
|
|
||||||
|
|
||||||
export default function MaxWidth({
|
export default function MaxWidth({
|
||||||
className,
|
className,
|
||||||
tag = "section",
|
tag = "section",
|
||||||
|
variant,
|
||||||
|
align,
|
||||||
...props
|
...props
|
||||||
}: MaxWidthProps) {
|
}: MaxWidthProps) {
|
||||||
const Cmp = tag
|
const Cmp = tag
|
||||||
return <Cmp className={maxWidthVariants({ className })} {...props} />
|
return (
|
||||||
|
<Cmp
|
||||||
|
className={maxWidthVariants({ className, variant, align })}
|
||||||
|
{...props}
|
||||||
|
/>
|
||||||
|
)
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,4 +1,20 @@
|
|||||||
.container {
|
.container {
|
||||||
max-width: var(--max-width, 1140px);
|
|
||||||
position: relative;
|
position: relative;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.container.default {
|
||||||
|
max-width: var(--max-width, 1140px);
|
||||||
|
}
|
||||||
|
|
||||||
|
.container.text {
|
||||||
|
max-width: 49.5rem;
|
||||||
|
}
|
||||||
|
|
||||||
|
.container.content {
|
||||||
|
max-width: 74.75rem;
|
||||||
|
}
|
||||||
|
|
||||||
|
.container.center {
|
||||||
|
margin: 0 auto;
|
||||||
|
width: 100vh;
|
||||||
|
}
|
||||||
|
|||||||
21
components/MaxWidth/variants.ts
Normal file
21
components/MaxWidth/variants.ts
Normal file
@@ -0,0 +1,21 @@
|
|||||||
|
import { cva } from "class-variance-authority"
|
||||||
|
|
||||||
|
import styles from "./maxWidth.module.css"
|
||||||
|
|
||||||
|
export const maxWidthVariants = cva(styles.container, {
|
||||||
|
variants: {
|
||||||
|
variant: {
|
||||||
|
text: styles.text,
|
||||||
|
content: styles.content,
|
||||||
|
default: styles.default,
|
||||||
|
},
|
||||||
|
align: {
|
||||||
|
center: styles.center,
|
||||||
|
left: styles.left,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
defaultVariants: {
|
||||||
|
variant: "default",
|
||||||
|
align: "center",
|
||||||
|
},
|
||||||
|
})
|
||||||
25
lib/graphql/Fragments/ContentPage/Breadcrumbs.graphql
Normal file
25
lib/graphql/Fragments/ContentPage/Breadcrumbs.graphql
Normal file
@@ -0,0 +1,25 @@
|
|||||||
|
fragment ContentPageBreadcrumbs on ContentPage {
|
||||||
|
web {
|
||||||
|
breadcrumbs {
|
||||||
|
title
|
||||||
|
parentsConnection {
|
||||||
|
edges {
|
||||||
|
node {
|
||||||
|
... on ContentPage {
|
||||||
|
web {
|
||||||
|
breadcrumbs {
|
||||||
|
title
|
||||||
|
}
|
||||||
|
}
|
||||||
|
system {
|
||||||
|
locale
|
||||||
|
uid
|
||||||
|
}
|
||||||
|
url
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
19
lib/graphql/Query/ContentPage.graphql
Normal file
19
lib/graphql/Query/ContentPage.graphql
Normal file
@@ -0,0 +1,19 @@
|
|||||||
|
#import "../Fragments/ContentPage/Breadcrumbs.graphql"
|
||||||
|
|
||||||
|
query GetContentPage($locale: String!, $uid: String!) {
|
||||||
|
content_page(uid: $uid, locale: $locale) {
|
||||||
|
title
|
||||||
|
header {
|
||||||
|
heading
|
||||||
|
preamble
|
||||||
|
}
|
||||||
|
hero_image
|
||||||
|
...ContentPageBreadcrumbs
|
||||||
|
system {
|
||||||
|
uid
|
||||||
|
created_at
|
||||||
|
updated_at
|
||||||
|
locale
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -107,9 +107,8 @@ query GetLoyaltyPage($locale: String!, $uid: String!) {
|
|||||||
}
|
}
|
||||||
title
|
title
|
||||||
heading
|
heading
|
||||||
header {
|
preamble
|
||||||
hero_image
|
hero_image
|
||||||
}
|
|
||||||
sidebar {
|
sidebar {
|
||||||
__typename
|
__typename
|
||||||
... on LoyaltyPageSidebarDynamicContent {
|
... on LoyaltyPageSidebarDynamicContent {
|
||||||
|
|||||||
5
server/routers/contentstack/contentPage/index.ts
Normal file
5
server/routers/contentstack/contentPage/index.ts
Normal file
@@ -0,0 +1,5 @@
|
|||||||
|
import { mergeRouters } from "@/server/trpc"
|
||||||
|
|
||||||
|
import { contentPageQueryRouter } from "./query"
|
||||||
|
|
||||||
|
export const contentPageRouter = mergeRouters(contentPageQueryRouter)
|
||||||
30
server/routers/contentstack/contentPage/output.ts
Normal file
30
server/routers/contentstack/contentPage/output.ts
Normal file
@@ -0,0 +1,30 @@
|
|||||||
|
import { z } from "zod"
|
||||||
|
|
||||||
|
import { Lang } from "@/constants/languages"
|
||||||
|
|
||||||
|
import { ImageVaultAsset } from "@/types/components/imageVaultImage"
|
||||||
|
|
||||||
|
export const validateContentPageSchema = z.object({
|
||||||
|
content_page: z.object({
|
||||||
|
title: z.string(),
|
||||||
|
header: z.object({
|
||||||
|
heading: z.string(),
|
||||||
|
preamble: z.string(),
|
||||||
|
}),
|
||||||
|
hero_image: z.any().nullable(),
|
||||||
|
system: z.object({
|
||||||
|
uid: z.string(),
|
||||||
|
locale: z.nativeEnum(Lang),
|
||||||
|
created_at: z.string(),
|
||||||
|
updated_at: z.string(),
|
||||||
|
}),
|
||||||
|
}),
|
||||||
|
})
|
||||||
|
|
||||||
|
export type ContentPageDataRaw = z.infer<typeof validateContentPageSchema>
|
||||||
|
|
||||||
|
type ContentPageRaw = ContentPageDataRaw["content_page"]
|
||||||
|
|
||||||
|
export type ContentPage = Omit<ContentPageRaw, "hero_image"> & {
|
||||||
|
hero_image?: ImageVaultAsset
|
||||||
|
}
|
||||||
64
server/routers/contentstack/contentPage/query.ts
Normal file
64
server/routers/contentstack/contentPage/query.ts
Normal file
@@ -0,0 +1,64 @@
|
|||||||
|
import { Lang } from "@/constants/languages"
|
||||||
|
import { GetContentPage } from "@/lib/graphql/Query/ContentPage.graphql"
|
||||||
|
import { request } from "@/lib/graphql/request"
|
||||||
|
import { notFound } from "@/server/errors/trpc"
|
||||||
|
import { contentstackExtendedProcedureUID, router } from "@/server/trpc"
|
||||||
|
|
||||||
|
import {
|
||||||
|
ContentPage,
|
||||||
|
ContentPageDataRaw,
|
||||||
|
validateContentPageSchema,
|
||||||
|
} from "./output"
|
||||||
|
import { makeImageVaultImage } from "./utils"
|
||||||
|
|
||||||
|
import {
|
||||||
|
TrackingChannelEnum,
|
||||||
|
TrackingSDKPageData,
|
||||||
|
} from "@/types/components/tracking"
|
||||||
|
|
||||||
|
export const contentPageQueryRouter = router({
|
||||||
|
get: contentstackExtendedProcedureUID.query(async ({ ctx }) => {
|
||||||
|
const { lang, uid } = ctx
|
||||||
|
|
||||||
|
const response = await request<ContentPageDataRaw>(GetContentPage, {
|
||||||
|
locale: lang,
|
||||||
|
uid,
|
||||||
|
})
|
||||||
|
|
||||||
|
if (!response.data) {
|
||||||
|
throw notFound(response)
|
||||||
|
}
|
||||||
|
|
||||||
|
const validatedContentPage = validateContentPageSchema.safeParse(
|
||||||
|
response.data
|
||||||
|
)
|
||||||
|
|
||||||
|
if (!validatedContentPage.success) {
|
||||||
|
console.error(
|
||||||
|
`Failed to validate Contentpage Data - (lang: ${lang}, uid: ${uid})`
|
||||||
|
)
|
||||||
|
console.error(validatedContentPage.error)
|
||||||
|
return null
|
||||||
|
}
|
||||||
|
|
||||||
|
const contentPageData = validatedContentPage.data.content_page
|
||||||
|
const contentPage: ContentPage = {
|
||||||
|
...contentPageData,
|
||||||
|
hero_image: makeImageVaultImage(contentPageData.hero_image),
|
||||||
|
}
|
||||||
|
|
||||||
|
const tracking: TrackingSDKPageData = {
|
||||||
|
pageId: contentPageData.system.uid,
|
||||||
|
lang: contentPageData.system.locale as Lang,
|
||||||
|
publishedDate: contentPageData.system.updated_at,
|
||||||
|
createdDate: contentPageData.system.created_at,
|
||||||
|
channel: TrackingChannelEnum["static-content-page"],
|
||||||
|
pageType: "staticcontentpage",
|
||||||
|
}
|
||||||
|
|
||||||
|
return {
|
||||||
|
contentPage,
|
||||||
|
tracking,
|
||||||
|
}
|
||||||
|
}),
|
||||||
|
})
|
||||||
9
server/routers/contentstack/contentPage/utils.ts
Normal file
9
server/routers/contentstack/contentPage/utils.ts
Normal file
@@ -0,0 +1,9 @@
|
|||||||
|
import { insertResponseToImageVaultAsset } from "@/utils/imageVault"
|
||||||
|
|
||||||
|
import { InsertResponse } from "@/types/components/imageVaultImage"
|
||||||
|
|
||||||
|
export function makeImageVaultImage(image: any) {
|
||||||
|
return image && !!Object.keys(image).length
|
||||||
|
? insertResponseToImageVaultAsset(image as InsertResponse)
|
||||||
|
: undefined
|
||||||
|
}
|
||||||
@@ -3,6 +3,7 @@ import { router } from "@/server/trpc"
|
|||||||
import { accountPageRouter } from "./accountPage"
|
import { accountPageRouter } from "./accountPage"
|
||||||
import { baseRouter } from "./base"
|
import { baseRouter } from "./base"
|
||||||
import { breadcrumbsRouter } from "./breadcrumbs"
|
import { breadcrumbsRouter } from "./breadcrumbs"
|
||||||
|
import { contentPageRouter } from "./contentPage"
|
||||||
import { hotelPageRouter } from "./hotelPage"
|
import { hotelPageRouter } from "./hotelPage"
|
||||||
import { languageSwitcherRouter } from "./languageSwitcher"
|
import { languageSwitcherRouter } from "./languageSwitcher"
|
||||||
import { loyaltyPageRouter } from "./loyaltyPage"
|
import { loyaltyPageRouter } from "./loyaltyPage"
|
||||||
@@ -15,5 +16,6 @@ export const contentstackRouter = router({
|
|||||||
hotelPage: hotelPageRouter,
|
hotelPage: hotelPageRouter,
|
||||||
languageSwitcher: languageSwitcherRouter,
|
languageSwitcher: languageSwitcherRouter,
|
||||||
loyaltyPage: loyaltyPageRouter,
|
loyaltyPage: loyaltyPageRouter,
|
||||||
|
contentPage: contentPageRouter,
|
||||||
myPages: myPagesRouter,
|
myPages: myPagesRouter,
|
||||||
})
|
})
|
||||||
|
|||||||
@@ -191,11 +191,8 @@ const loyaltyPageSidebarItem = z.discriminatedUnion("__typename", [
|
|||||||
|
|
||||||
export const validateLoyaltyPageSchema = z.object({
|
export const validateLoyaltyPageSchema = z.object({
|
||||||
heading: z.string().nullable(),
|
heading: z.string().nullable(),
|
||||||
header: z
|
preamble: z.string().nullable(),
|
||||||
.object({
|
hero_image: z.any().nullable(),
|
||||||
hero_image: z.any(),
|
|
||||||
})
|
|
||||||
.nullable(),
|
|
||||||
blocks: z.array(loyaltyPageBlockItem).nullable(),
|
blocks: z.array(loyaltyPageBlockItem).nullable(),
|
||||||
sidebar: z.array(loyaltyPageSidebarItem).nullable(),
|
sidebar: z.array(loyaltyPageSidebarItem).nullable(),
|
||||||
system: z.object({
|
system: z.object({
|
||||||
@@ -263,7 +260,11 @@ export type Sidebar =
|
|||||||
| SideBarDynamicContent
|
| SideBarDynamicContent
|
||||||
type LoyaltyPageDataRaw = z.infer<typeof validateLoyaltyPageSchema>
|
type LoyaltyPageDataRaw = z.infer<typeof validateLoyaltyPageSchema>
|
||||||
|
|
||||||
export type LoyaltyPage = Omit<LoyaltyPageDataRaw, "blocks" | "sidebar"> & {
|
export type LoyaltyPage = Omit<
|
||||||
|
LoyaltyPageDataRaw,
|
||||||
|
"blocks" | "sidebar" | "hero_image"
|
||||||
|
> & {
|
||||||
|
hero_image?: ImageVaultAsset
|
||||||
blocks: Block[]
|
blocks: Block[]
|
||||||
sidebar: Sidebar[]
|
sidebar: Sidebar[]
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -12,7 +12,6 @@ import {
|
|||||||
generateTag,
|
generateTag,
|
||||||
generateTags,
|
generateTags,
|
||||||
} from "@/utils/generateTag"
|
} from "@/utils/generateTag"
|
||||||
import { insertResponseToImageVaultAsset } from "@/utils/imageVault"
|
|
||||||
import { removeMultipleSlashes } from "@/utils/url"
|
import { removeMultipleSlashes } from "@/utils/url"
|
||||||
|
|
||||||
import { removeEmptyObjects } from "../../utils"
|
import { removeEmptyObjects } from "../../utils"
|
||||||
@@ -22,9 +21,8 @@ import {
|
|||||||
validateLoyaltyPageRefsSchema,
|
validateLoyaltyPageRefsSchema,
|
||||||
validateLoyaltyPageSchema,
|
validateLoyaltyPageSchema,
|
||||||
} from "./output"
|
} from "./output"
|
||||||
import { getConnections } from "./utils"
|
import { getConnections, makeButtonObject, makeImageVaultImage } from "./utils"
|
||||||
|
|
||||||
import { InsertResponse } from "@/types/components/imageVaultImage"
|
|
||||||
import {
|
import {
|
||||||
LoyaltyBlocksTypenameEnum,
|
LoyaltyBlocksTypenameEnum,
|
||||||
LoyaltyCardsGridEnum,
|
LoyaltyCardsGridEnum,
|
||||||
@@ -35,35 +33,6 @@ import {
|
|||||||
TrackingSDKPageData,
|
TrackingSDKPageData,
|
||||||
} from "@/types/components/tracking"
|
} from "@/types/components/tracking"
|
||||||
|
|
||||||
function makeImageVaultImage(image: any) {
|
|
||||||
return image && !!Object.keys(image).length
|
|
||||||
? insertResponseToImageVaultAsset(image as InsertResponse)
|
|
||||||
: undefined
|
|
||||||
}
|
|
||||||
|
|
||||||
function makeButtonObject(button: any) {
|
|
||||||
if (!button) return null
|
|
||||||
|
|
||||||
const isContenstackLink =
|
|
||||||
button?.is_contentstack_link || button.linkConnection?.edges?.length
|
|
||||||
|
|
||||||
return {
|
|
||||||
openInNewTab: button?.open_in_new_tab,
|
|
||||||
title:
|
|
||||||
button.cta_text ||
|
|
||||||
(isContenstackLink
|
|
||||||
? button.linkConnection.edges[0].node.title
|
|
||||||
: button.external_link.title),
|
|
||||||
href: isContenstackLink
|
|
||||||
? button.linkConnection.edges[0].node.web?.original_url ||
|
|
||||||
removeMultipleSlashes(
|
|
||||||
`/${button.linkConnection.edges[0].node.system.locale}/${button.linkConnection.edges[0].node.url}`
|
|
||||||
)
|
|
||||||
: button.external_link.href,
|
|
||||||
isExternal: !isContenstackLink,
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
export const loyaltyPageQueryRouter = router({
|
export const loyaltyPageQueryRouter = router({
|
||||||
get: contentstackExtendedProcedureUID.query(async ({ ctx }) => {
|
get: contentstackExtendedProcedureUID.query(async ({ ctx }) => {
|
||||||
const { lang, uid } = ctx
|
const { lang, uid } = ctx
|
||||||
@@ -208,17 +177,10 @@ export const loyaltyPageQueryRouter = router({
|
|||||||
})
|
})
|
||||||
: null
|
: null
|
||||||
|
|
||||||
const header = response.data.loyalty_page.header
|
|
||||||
? {
|
|
||||||
hero_image: makeImageVaultImage(
|
|
||||||
response.data.loyalty_page.header.hero_image
|
|
||||||
),
|
|
||||||
}
|
|
||||||
: null
|
|
||||||
|
|
||||||
const loyaltyPage = {
|
const loyaltyPage = {
|
||||||
heading: response.data.loyalty_page.heading,
|
heading: response.data.loyalty_page.heading,
|
||||||
header,
|
preamble: response.data.loyalty_page.preamble,
|
||||||
|
hero_image: makeImageVaultImage(response.data.loyalty_page.hero_image),
|
||||||
system: response.data.loyalty_page.system,
|
system: response.data.loyalty_page.system,
|
||||||
blocks,
|
blocks,
|
||||||
sidebar,
|
sidebar,
|
||||||
|
|||||||
@@ -1,5 +1,9 @@
|
|||||||
|
import { insertResponseToImageVaultAsset } from "@/utils/imageVault"
|
||||||
|
import { removeMultipleSlashes } from "@/utils/url"
|
||||||
|
|
||||||
import { LoyaltyPageRefsDataRaw } from "./output"
|
import { LoyaltyPageRefsDataRaw } from "./output"
|
||||||
|
|
||||||
|
import { InsertResponse } from "@/types/components/imageVaultImage"
|
||||||
import {
|
import {
|
||||||
LoyaltyBlocksTypenameEnum,
|
LoyaltyBlocksTypenameEnum,
|
||||||
LoyaltyCardsGridEnum,
|
LoyaltyCardsGridEnum,
|
||||||
@@ -77,3 +81,32 @@ export function getConnections(refs: LoyaltyPageRefsDataRaw) {
|
|||||||
|
|
||||||
return connections
|
return connections
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export function makeImageVaultImage(image: any) {
|
||||||
|
return image && !!Object.keys(image).length
|
||||||
|
? insertResponseToImageVaultAsset(image as InsertResponse)
|
||||||
|
: undefined
|
||||||
|
}
|
||||||
|
|
||||||
|
export function makeButtonObject(button: any) {
|
||||||
|
if (!button) return null
|
||||||
|
|
||||||
|
const isContenstackLink =
|
||||||
|
button?.is_contentstack_link || button.linkConnection?.edges?.length
|
||||||
|
|
||||||
|
return {
|
||||||
|
openInNewTab: button?.open_in_new_tab,
|
||||||
|
title:
|
||||||
|
button.cta_text ||
|
||||||
|
(isContenstackLink
|
||||||
|
? button.linkConnection.edges[0].node.title
|
||||||
|
: button.external_link.title),
|
||||||
|
href: isContenstackLink
|
||||||
|
? button.linkConnection.edges[0].node.web?.original_url ||
|
||||||
|
removeMultipleSlashes(
|
||||||
|
`/${button.linkConnection.edges[0].node.system.locale}/${button.linkConnection.edges[0].node.url}`
|
||||||
|
)
|
||||||
|
: button.external_link.href,
|
||||||
|
isExternal: !isContenstackLink,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|||||||
@@ -1,3 +1,9 @@
|
|||||||
export interface MaxWidthProps extends React.HTMLAttributes<HTMLElement> {
|
import { VariantProps } from "class-variance-authority"
|
||||||
|
|
||||||
|
import { maxWidthVariants } from "@/components/MaxWidth/variants"
|
||||||
|
|
||||||
|
export interface MaxWidthProps
|
||||||
|
extends React.HTMLAttributes<HTMLElement>,
|
||||||
|
VariantProps<typeof maxWidthVariants> {
|
||||||
tag?: "article" | "div" | "main" | "section"
|
tag?: "article" | "div" | "main" | "section"
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -4,6 +4,7 @@ import type { Lang } from "@/constants/languages"
|
|||||||
|
|
||||||
export enum TrackingChannelEnum {
|
export enum TrackingChannelEnum {
|
||||||
"scandic-friends" = "scandic-friends",
|
"scandic-friends" = "scandic-friends",
|
||||||
|
"static-content-page" = "static-content-page",
|
||||||
}
|
}
|
||||||
|
|
||||||
export type TrackingChannel = keyof typeof TrackingChannelEnum
|
export type TrackingChannel = keyof typeof TrackingChannelEnum
|
||||||
|
|||||||
Reference in New Issue
Block a user