feat/BOOK-755 alert content pages
* feat(BOOK-755): Added alert block on Collection pages * feat(BOOK-755): Added alert block on Content pages * feat(BOOK-755): Added alert functionality for RTE Approved-by: Bianca Widstam
This commit is contained in:
@@ -1,15 +1,13 @@
|
||||
import { z, ZodError, ZodIssueCode } from "zod"
|
||||
|
||||
import {
|
||||
AlertTypeEnum,
|
||||
AlertVisibleOnEnum,
|
||||
} from "@scandic-hotels/common/constants/alert"
|
||||
import { AlertVisibleOnEnum } from "@scandic-hotels/common/constants/alert"
|
||||
import { Lang } from "@scandic-hotels/common/constants/language"
|
||||
import { logger } from "@scandic-hotels/common/logger"
|
||||
import { removeMultipleSlashes } from "@scandic-hotels/common/utils/url"
|
||||
import { nullableStringValidator } from "@scandic-hotels/common/utils/zod/stringValidator"
|
||||
|
||||
import { discriminatedUnion } from "../../../utils/discriminatedUnion"
|
||||
import { transformedAlertSchema } from "../schemas/alert"
|
||||
import {
|
||||
infoCardBlockSchema,
|
||||
transformInfoCardBlock,
|
||||
@@ -410,85 +408,6 @@ export const headerSchema = z
|
||||
}
|
||||
})
|
||||
|
||||
export const alertSchema = z
|
||||
.object({
|
||||
type: z.nativeEnum(AlertTypeEnum),
|
||||
text: z.string(),
|
||||
heading: z.string(),
|
||||
phone_contact: z.object({
|
||||
display_text: z.string(),
|
||||
phone_number: z.string().nullable(),
|
||||
footnote: z.string().nullable(),
|
||||
}),
|
||||
has_link: z.boolean(),
|
||||
link: linkAndTitleSchema,
|
||||
has_sidepeek_button: z.boolean(),
|
||||
sidepeek_button: z.object({
|
||||
cta_text: z.string(),
|
||||
}),
|
||||
sidepeek_content: z.object({
|
||||
heading: z.string(),
|
||||
content: z.object({
|
||||
json: z.any(),
|
||||
embedded_itemsConnection: z.object({
|
||||
edges: z.array(
|
||||
z.object({
|
||||
node: linkUnionSchema.transform((data) => {
|
||||
const link = transformPageLink(data)
|
||||
if (link) {
|
||||
return link
|
||||
}
|
||||
return data
|
||||
}),
|
||||
})
|
||||
),
|
||||
}),
|
||||
}),
|
||||
}),
|
||||
visible_on: z.array(z.string()).nullish().default([]),
|
||||
})
|
||||
.transform(
|
||||
({
|
||||
type,
|
||||
heading,
|
||||
text,
|
||||
phone_contact,
|
||||
has_link,
|
||||
link,
|
||||
has_sidepeek_button,
|
||||
sidepeek_button,
|
||||
sidepeek_content,
|
||||
visible_on,
|
||||
}) => {
|
||||
const hasLink = has_link && link.link
|
||||
return {
|
||||
type,
|
||||
text,
|
||||
heading,
|
||||
visible_on,
|
||||
phoneContact:
|
||||
phone_contact.display_text && phone_contact.phone_number
|
||||
? {
|
||||
displayText: phone_contact.display_text,
|
||||
phoneNumber: phone_contact.phone_number,
|
||||
footnote: phone_contact.footnote,
|
||||
}
|
||||
: null,
|
||||
hasSidepeekButton: !!has_sidepeek_button,
|
||||
link: hasLink
|
||||
? {
|
||||
url: link.link.url,
|
||||
title: link.title,
|
||||
}
|
||||
: null,
|
||||
sidepeekButton:
|
||||
!hasLink && has_sidepeek_button ? sidepeek_button : null,
|
||||
sidepeekContent:
|
||||
!hasLink && has_sidepeek_button ? sidepeek_content : null,
|
||||
}
|
||||
}
|
||||
)
|
||||
|
||||
export const siteConfigSchema = z
|
||||
.object({
|
||||
all_site_config: z.object({
|
||||
@@ -503,7 +422,7 @@ export const siteConfigSchema = z
|
||||
alertConnection: z.object({
|
||||
edges: z.array(
|
||||
z.object({
|
||||
node: alertSchema,
|
||||
node: transformedAlertSchema,
|
||||
})
|
||||
),
|
||||
}),
|
||||
|
||||
@@ -5,11 +5,11 @@ import { logger } from "@scandic-hotels/common/logger"
|
||||
|
||||
import { getValueFromContactConfig } from "../../../utils/contactConfig"
|
||||
|
||||
import type { AlertOutput } from "../../../types/siteConfig"
|
||||
import type { Alert } from "../schemas/alert"
|
||||
import type { ContactConfig } from "./output"
|
||||
|
||||
export function getAlertPhoneContactData(
|
||||
alert: AlertOutput,
|
||||
alert: Alert,
|
||||
contactConfig: ContactConfig
|
||||
) {
|
||||
if (alert.phoneContact) {
|
||||
|
||||
@@ -4,6 +4,7 @@ import { transformedImageVaultAssetSchema } from "@scandic-hotels/common/utils/i
|
||||
|
||||
import { CollectionPageEnum } from "../../../types/collectionPage"
|
||||
import { discriminatedUnionArray } from "../../../utils/discriminatedUnion"
|
||||
import { alertBlockSchema } from "../schemas/blocks/alert"
|
||||
import { cardsGridSchema } from "../schemas/blocks/cardsGrid"
|
||||
import { dynamicContentSchema as blockDynamicContentSchema } from "../schemas/blocks/dynamicContent"
|
||||
import { shortcutsSchema } from "../schemas/blocks/shortcuts"
|
||||
@@ -47,12 +48,19 @@ export const collectionPageVideoCard = z
|
||||
})
|
||||
.merge(videoCardSchema)
|
||||
|
||||
export const collectionPageAlert = z
|
||||
.object({
|
||||
__typename: z.literal(CollectionPageEnum.ContentStack.blocks.Alert),
|
||||
})
|
||||
.merge(alertBlockSchema)
|
||||
|
||||
export const blocksSchema = z.discriminatedUnion("__typename", [
|
||||
collectionPageCards,
|
||||
collectionPageDynamicContent,
|
||||
collectionPageShortcuts,
|
||||
collectionPageUspGrid,
|
||||
collectionPageVideoCard,
|
||||
collectionPageAlert,
|
||||
])
|
||||
|
||||
const navigationLinksSchema = z
|
||||
|
||||
@@ -5,6 +5,7 @@ import { transformedImageVaultAssetSchema } from "@scandic-hotels/common/utils/i
|
||||
import { ContentPageEnum } from "../../../types/contentPage"
|
||||
import { discriminatedUnionArray } from "../../../utils/discriminatedUnion"
|
||||
import { accordionSchema } from "../schemas/blocks/accordion"
|
||||
import { alertBlockSchema } from "../schemas/blocks/alert"
|
||||
import { cardsGridSchema } from "../schemas/blocks/cardsGrid"
|
||||
import { contentSchema as blockContentSchema } from "../schemas/blocks/content"
|
||||
import { dynamicContentSchema as blockDynamicContentSchema } from "../schemas/blocks/dynamicContent"
|
||||
@@ -101,6 +102,12 @@ export const contentPageVideo = z
|
||||
})
|
||||
.merge(videoBlockSchema)
|
||||
|
||||
export const contentPageAlert = z
|
||||
.object({
|
||||
__typename: z.literal(ContentPageEnum.ContentStack.blocks.Alert),
|
||||
})
|
||||
.merge(alertBlockSchema)
|
||||
|
||||
export const blocksSchema = z.discriminatedUnion("__typename", [
|
||||
contentPageAccordion,
|
||||
contentPageCards,
|
||||
@@ -114,6 +121,7 @@ export const blocksSchema = z.discriminatedUnion("__typename", [
|
||||
contentPageHotelListing,
|
||||
contentPageVideoCard,
|
||||
contentPageVideo,
|
||||
contentPageAlert,
|
||||
])
|
||||
|
||||
export const contentPageSidebarContent = z
|
||||
|
||||
92
packages/trpc/lib/routers/contentstack/schemas/alert.ts
Normal file
92
packages/trpc/lib/routers/contentstack/schemas/alert.ts
Normal file
@@ -0,0 +1,92 @@
|
||||
import z from "zod"
|
||||
|
||||
import { AlertTypeEnum } from "@scandic-hotels/common/constants/alert"
|
||||
|
||||
import { linkAndTitleSchema } from "./linkConnection"
|
||||
import { linkUnionSchema, transformPageLink } from "./pageLinks"
|
||||
import { systemSchema } from "./system"
|
||||
|
||||
export const alertSchema = z.object({
|
||||
type: z.nativeEnum(AlertTypeEnum),
|
||||
text: z.string(),
|
||||
heading: z.string(),
|
||||
phone_contact: z.object({
|
||||
display_text: z.string(),
|
||||
phone_number: z.string().nullish(),
|
||||
footnote: z.string().nullish(),
|
||||
}),
|
||||
has_link: z.boolean(),
|
||||
link: linkAndTitleSchema,
|
||||
has_sidepeek_button: z.boolean(),
|
||||
sidepeek_button: z.object({
|
||||
cta_text: z.string(),
|
||||
}),
|
||||
sidepeek_content: z.object({
|
||||
heading: z.string(),
|
||||
content: z.object({
|
||||
json: z.any(),
|
||||
embedded_itemsConnection: z.object({
|
||||
edges: z.array(
|
||||
z.object({
|
||||
node: linkUnionSchema.transform((data) => {
|
||||
const link = transformPageLink(data)
|
||||
if (link) {
|
||||
return link
|
||||
}
|
||||
return data
|
||||
}),
|
||||
})
|
||||
),
|
||||
}),
|
||||
}),
|
||||
}),
|
||||
visible_on: z.array(z.string()).nullish().default([]),
|
||||
system: systemSchema,
|
||||
})
|
||||
|
||||
export const transformedAlertSchema =
|
||||
alertSchema.transform(transformAlertSchema)
|
||||
|
||||
export function transformAlertSchema(data: typeof alertSchema._type) {
|
||||
const {
|
||||
type,
|
||||
heading,
|
||||
text,
|
||||
phone_contact,
|
||||
has_link,
|
||||
link,
|
||||
has_sidepeek_button,
|
||||
sidepeek_button,
|
||||
sidepeek_content,
|
||||
visible_on,
|
||||
system,
|
||||
} = data
|
||||
|
||||
const hasLink = has_link && link.link
|
||||
return {
|
||||
type,
|
||||
text,
|
||||
heading,
|
||||
visible_on,
|
||||
phoneContact:
|
||||
phone_contact.display_text && phone_contact.phone_number
|
||||
? {
|
||||
displayText: phone_contact.display_text,
|
||||
phoneNumber: phone_contact.phone_number,
|
||||
footnote: phone_contact.footnote,
|
||||
}
|
||||
: null,
|
||||
hasSidepeekButton: !!has_sidepeek_button,
|
||||
link: hasLink
|
||||
? {
|
||||
url: link.link.url,
|
||||
title: link.title,
|
||||
}
|
||||
: null,
|
||||
sidepeekButton: !hasLink && has_sidepeek_button ? sidepeek_button : null,
|
||||
sidepeekContent: !hasLink && has_sidepeek_button ? sidepeek_content : null,
|
||||
system,
|
||||
}
|
||||
}
|
||||
|
||||
export type Alert = z.output<typeof transformedAlertSchema>
|
||||
@@ -0,0 +1,25 @@
|
||||
import { z } from "zod"
|
||||
|
||||
import { BlocksEnums } from "../../../../types/blocksEnum"
|
||||
import { transformedAlertSchema } from "../alert"
|
||||
|
||||
export const alertBlockSchema = z.object({
|
||||
typename: z.literal(BlocksEnums.block.Alert).default(BlocksEnums.block.Alert),
|
||||
alert: z
|
||||
.object({
|
||||
alertConnection: z.object({
|
||||
edges: z.array(
|
||||
z.object({
|
||||
node: transformedAlertSchema,
|
||||
})
|
||||
),
|
||||
}),
|
||||
})
|
||||
.transform((data) => {
|
||||
const alert = data.alertConnection.edges[0]?.node
|
||||
if (!alert) {
|
||||
return null
|
||||
}
|
||||
return alert
|
||||
}),
|
||||
})
|
||||
@@ -1,6 +1,8 @@
|
||||
import { z } from "zod"
|
||||
|
||||
import { BlocksEnums } from "../../../../types/blocksEnum"
|
||||
import { ContentEnum } from "../../../../types/content"
|
||||
import { alertSchema, transformAlertSchema } from "../alert"
|
||||
import { rawLinkUnionSchema, transformPageLink } from "../pageLinks"
|
||||
import { imageContainerSchema } from "./imageContainer"
|
||||
import { sysAssetSchema } from "./sysAsset"
|
||||
@@ -22,6 +24,11 @@ export const contentSchema = z.object({
|
||||
.discriminatedUnion("__typename", [
|
||||
imageContainerSchema,
|
||||
sysAssetSchema,
|
||||
alertSchema.merge(
|
||||
z.object({
|
||||
__typename: z.literal(ContentEnum.blocks.Alert),
|
||||
})
|
||||
),
|
||||
...rawLinkUnionSchema.options,
|
||||
])
|
||||
.transform((data) => {
|
||||
@@ -29,6 +36,12 @@ export const contentSchema = z.object({
|
||||
if (link) {
|
||||
return link
|
||||
}
|
||||
if (data.__typename === ContentEnum.blocks.Alert) {
|
||||
return {
|
||||
__typename: data.__typename,
|
||||
...transformAlertSchema(data),
|
||||
}
|
||||
}
|
||||
return data
|
||||
}),
|
||||
})
|
||||
|
||||
Reference in New Issue
Block a user