Skip to content

Instantly share code, notes, and snippets.

@TimoWestland
Created March 12, 2021 13:19
Show Gist options
  • Save TimoWestland/42941fb219b4a749f8ec903561847963 to your computer and use it in GitHub Desktop.
Save TimoWestland/42941fb219b4a749f8ec903561847963 to your computer and use it in GitHub Desktop.
import * as React from 'react'
import { useBloomreach } from '../context'
import { BrComponentModel, BrImage, BrInstructions, BrModal, BrUspItem } from '../types'
import { getComponentByPath, getContentByRef } from '../utils'
// Add this one to the bloomreach types:
// export interface BrModal extends Identifiable, Named, Versioned {
// readonly type: 'richText'
// readonly localeString: string
// readonly content: BrRichText
// }
type ProductDetailDocument = {
id: string
name: string
type: string
usps: BrUspItem[]
additionalUsps: BrUspItem[]
packshotTypes: string[]
noAddonsImage?: BrImage
instructions?: BrInstructions
}
export type ProductDetailContent = {
modalContent?: string
packshotTypes?: string[]
instructions?: {
id: string
value: string
textColor: string
backgroundColor: string
}
usps?: Array<{
text: string
icon?: string
}>
additionalUsps?: Array<{
text: string
icon?: string
}>
prescriptionGlasses: {
noAddonsImage?: BrImage
}
}
const emptyContent: ProductDetailContent = {
prescriptionGlasses: {},
}
export function useBloomreachPdpContent(): ProductDetailContent {
const { pageModel } = useBloomreach()
if (!pageModel?.page?.models) {
return emptyContent
}
const mainComponent = getComponentByPath('main', pageModel)
const ref = mainComponent?.models?.document.$ref
const content = getContentByRef<ProductDetailDocument>(ref, pageModel)
if (!content) {
console.warn(
`Cannot find main content for ProductDetail pageModel. Got: ${content} for $ref: ${ref}`
)
return emptyContent
}
const { usps, instructions, packshotTypes, noAddonsImage, additionalUsps } = content
const modal = getModalContent(mainComponent)
return React.useMemo(
() => ({
packshotTypes,
modalContent: modal?.content?.value ?? '',
instructions: instructions && {
id: instructions.id,
value: instructions.html,
textColor: instructions.textColor,
backgroundColor: instructions.backgroundColor,
},
usps: usps.map(({ icon, text }) => ({ icon, text })),
additionalUsps: additionalUsps.map(({ icon, text }) => ({ icon, text })),
prescriptionGlasses: { noAddonsImage },
}),
[packshotTypes, instructions, usps, noAddonsImage, additionalUsps]
)
}
function getModalContent(main: BrComponentModel | undefined) {
const components = main?.components?.reduce<BrComponentModel[]>((acc, cur) => {
return cur?.components ? [...acc, ...cur?.components] : acc
}, [])
const modal = (components || []).find(
(c) => c.name === 'richtext' && c._meta?.params?.template === 'modal'
)
return modal && getContentByRef<BrModal>(modal?.models?.document.$ref)
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment