diff --git a/libs/blocks/caas-config/caas-config.js b/libs/blocks/caas-config/caas-config.js index 2387e9c599..13a8b595c8 100644 --- a/libs/blocks/caas-config/caas-config.js +++ b/libs/blocks/caas-config/caas-config.js @@ -98,8 +98,6 @@ const defaultOptions = { '14257-chimera.adobeioruntime.net/api/v1/web/chimera-0.0.1/collection', '14257-chimera-stage.adobeioruntime.net/api/v1/web/chimera-0.0.1/collection': '14257-chimera-stage.adobeioruntime.net/api/v1/web/chimera-0.0.1/collection', - '14257-chimera-dev.adobeioruntime.net/api/v1/web/chimera-0.0.1/collection': - '14257-chimera-dev.adobeioruntime.net/api/v1/web/chimera-0.0.1/collection', }, filterBuildPanel: { automatic: 'Automatic', diff --git a/libs/blocks/caas/caas.js b/libs/blocks/caas/caas.js index b0c7c0aeef..2014e3f153 100644 --- a/libs/blocks/caas/caas.js +++ b/libs/blocks/caas/caas.js @@ -1,7 +1,9 @@ -import { initCaas, loadCaasFiles, loadStrings } from './utils.js'; -import { parseEncodedConfig, createIntersectionObserver } from '../../utils/utils.js'; +import { initCaas, loadCaasFiles, loadStrings, fgHeaderValue } from './utils.js'; +import { parseEncodedConfig, createIntersectionObserver, getMetadata, getConfig, b64ToUtf8 } from '../../utils/utils.js'; const ROOT_MARGIN = 1000; +const P_CAAS_AIO = b64ToUtf8('MTQyNTctY2hpbWVyYS5hZG9iZWlvcnVudGltZS5uZXQvYXBpL3YxL3dlYi9jaGltZXJhLTAuMC4xL2NvbGxlY3Rpb24='); +const S_CAAS_AIO = b64ToUtf8('MTQyNTctY2hpbWVyYS1zdGFnZS5hZG9iZWlvcnVudGltZS5uZXQvYXBpL3YxL3dlYi9jaGltZXJhLTAuMC4xL2NvbGxlY3Rpb24='); const getCaasStrings = (placeholderUrl) => new Promise((resolve) => { if (placeholderUrl) { @@ -30,6 +32,28 @@ const loadCaas = async (a) => { a.insertAdjacentElement('afterend', block); a.remove(); + const floodGateColor = getMetadata('floodgatecolor') || ''; + if (floodGateColor === fgHeaderValue) { + state.fetchCardsFromFloodgateTree = true; + } + + const { env } = getConfig(); + const { host } = window.location; + let chimeraEndpoint = 'www.adobe.com/chimera-api/collection'; + + if (host.includes('stage.adobe') || env?.name === 'local') { + chimeraEndpoint = S_CAAS_AIO; + } else if (host.includes('.hlx.')) { + // If invoking URL is not an Acom URL, then switch to AIO + chimeraEndpoint = P_CAAS_AIO; + } + + if (host.includes('hlx.page') || env?.name === 'local') { + state.draftDb = true; + } + + state.endpoint = chimeraEndpoint; + initCaas(state, caasStrs, block); }; diff --git a/libs/blocks/caas/utils.js b/libs/blocks/caas/utils.js index ecc5423dc2..d8799499df 100644 --- a/libs/blocks/caas/utils.js +++ b/libs/blocks/caas/utils.js @@ -3,6 +3,8 @@ import { loadScript, loadStyle, getConfig as pageConfigHelper } from '../../util import { fetchWithTimeout } from '../utils/utils.js'; const URL_ENCODED_COMMA = '%2C'; +export const fgHeaderName = 'X-Adobe-Floodgate'; +export const fgHeaderValue = 'pink'; const pageConfig = pageConfigHelper(); const pageLocales = Object.keys(pageConfig.locales || {}); @@ -291,13 +293,10 @@ const findTupleIndex = (fgHeader) => { * @returns requestHeaders */ const addFloodgateHeader = (state) => { - const fgHeader = 'X-Adobe-Floodgate'; - const fgHeaderValue = 'pink'; - // Delete FG header if already exists, before adding pink to avoid duplicates in requestHeaders - requestHeaders.splice(findTupleIndex(fgHeader, 1)); + requestHeaders.splice(findTupleIndex(fgHeaderName, 1)); if (state.fetchCardsFromFloodgateTree) { - requestHeaders.push([fgHeader, fgHeaderValue]); + requestHeaders.push([fgHeaderName, fgHeaderValue]); } return requestHeaders; }; @@ -557,7 +556,7 @@ export const defaultState = { contentTypeTags: [], country: 'caas:country/us', customCard: '', - ctaAction: '_blank', + ctaAction: '_self', doNotLazyLoad: false, disableBanners: false, draftDb: false, diff --git a/libs/blocks/faas/utils.js b/libs/blocks/faas/utils.js index 5ac88f98b2..94a9ef96f0 100644 --- a/libs/blocks/faas/utils.js +++ b/libs/blocks/faas/utils.js @@ -352,7 +352,11 @@ export const initFaas = (config, targetEl) => { if (state.complete) { if (state.js) { Object.keys(state.js).forEach((key) => { - state[key] = state.js[key]; + if (key === 'd') { + state[key] = localizeLink(state.js[key]); + } else { + state[key] = state.js[key]; + } }); delete state.js; } diff --git a/libs/blocks/global-footer/global-footer.js b/libs/blocks/global-footer/global-footer.js index ea1ce14d02..1757c5aaae 100644 --- a/libs/blocks/global-footer/global-footer.js +++ b/libs/blocks/global-footer/global-footer.js @@ -98,7 +98,7 @@ class Footer { await task(); } - this.footerEl.setAttribute('daa-lh', `gnav|${getExperienceName()}|footer`); + this.footerEl.setAttribute('daa-lh', `gnav|${getExperienceName()}|footer|${document.body.dataset.mep}`); this.footerEl.append(this.elements.footer); }; diff --git a/libs/blocks/marketo/marketo.css b/libs/blocks/marketo/marketo.css index 9e1c803894..878d04a95a 100644 --- a/libs/blocks/marketo/marketo.css +++ b/libs/blocks/marketo/marketo.css @@ -43,12 +43,20 @@ display: flex; flex-flow: row wrap; justify-content: space-between; + column-gap: 4.6%; align-items: flex-start; visibility: visible; opacity: 1; transition: opacity 1s ease-in, height 1s ease-in; } +.marketo .mktoFormRow.mktoFormRowTop.comments, +.marketo .mktoFormRow.mktoFormRowTop.demo, +.marketo .mktoFormRow.mktoFormRowTop.name { + display: flex; + width: 100%; +} + .marketo .mktoFormRow { transition: height 0.5s ease-in; height: auto; @@ -63,12 +71,24 @@ margin-bottom: 11px; } +.marketo fieldset.mktoFormCol { + display: none; +} + +.marketo fieldset.mktoFormCol.mktoVisible { + display: block; +} + .marketo .mktoFormRow fieldset.mktoFormCol { border: none; margin: 0; padding: 0; } +.marketo > .mktoFormRow.mktoFormRowTop > .mktoFormCol > .mktoFormRow > .mktoFormCol.mktoVisible > .mktoFieldWrap { + width: auto; +} + .marketo .mktoFormRow.demo fieldset.mktoFormCol { width: 100%; margin: 24px 0; @@ -228,7 +248,7 @@ color: var(--marketo-form-text); } -.marketo .mktoFormRow.adobe-privacy .mktoFormCol:not(fieldset) { +.marketo .mktoFormRow[class*="adobe-privacy"] .mktoFormCol:not(fieldset) { margin-top: 21px; } @@ -385,7 +405,7 @@ width: 100%; } -.dialog-modal .marketo .mktoFormRow.adobe-privacy { +.dialog-modal .marketo .mktoFormRow[class*="adobe-privacy"] { width: 100%; } @@ -425,29 +445,67 @@ margin-left: 0; } +.marketo .mktoFormRowTop[class*="adobe-privacy"] { + display: flex; + width: 100%; +} + @media screen and (min-width: 600px) { .marketo .marketo-form-wrapper { padding: var(--spacing-xxl); } - .marketo .mktoFormCol.mktoVisible { - width: 47.7%; - } - - .marketo [class*="adobe-privacy"] fieldset.mktoFormCol.mktoVisible { + .marketo .mktoFormRowTop[class*="adobe-privacy"] { + display: grid; width: 100%; } - .marketo .adobe-privacy .mktoFormCol.mktoVisible, + .marketo [class*="adobe-privacy"], .marketo .msg-error .mktoFormCol.mktoVisible, .marketo .mktoFormCol.mktoVisible .mktoFormCol.mktoVisible { width: 100%; + grid-column: span 2; } .marketo .mktoForm.show-warnings .mktoError { width: 50%; margin-left: 50%; } + + .marketo form.mktoForm--fade-in.mktoVisible { + display: grid; + grid-template-columns: 1fr 1fr; + } + + .marketo .mktoFormRow.mktoFormRowTop.name > .mktoFormCol { + display: grid; + grid-template-columns: 1fr 1fr; + grid-template-areas: "salutation ." "firstName lastName"; + column-gap: 4.6%; + } + + .marketo .mktoFormRow.mktoFormRowTop.comments, + .marketo .mktoFormRow.mktoFormRowTop.demo, + .marketo .mktoFormRow.mktoFormRowTop.name { + display: block; + grid-column: span 2; + } + + .marketo .mktoFormRow.mktoFormRowTop.name .mktoFormRow[data-mktofield="Salutation"] { + grid-area: salutation; + } + + .marketo .mktoFormRow.mktoFormRowTop.name .mktoFormRow[data-mktofield="FirstName"] { + grid-area: firstName; + } + + .marketo .mktoFormRow.mktoFormRowTop.name .mktoFormRow[data-mktofield="LastName"] { + grid-area: lastName; + } + + .marketo .mktoForm .mktoButtonRow { + grid-column: span 2; + } } @media screen and (min-width: 900px) { diff --git a/libs/blocks/merch-card/img/checkmark-white-small.svg b/libs/blocks/merch-card/img/checkmark-white-small.svg new file mode 100644 index 0000000000..b7e8978ccc --- /dev/null +++ b/libs/blocks/merch-card/img/checkmark-white-small.svg @@ -0,0 +1,10 @@ + + + + + + diff --git a/libs/blocks/merch-card/img/ellipsis.svg b/libs/blocks/merch-card/img/ellipsis.svg new file mode 100644 index 0000000000..56416384c2 --- /dev/null +++ b/libs/blocks/merch-card/img/ellipsis.svg @@ -0,0 +1,6 @@ + + + + + + diff --git a/libs/blocks/merch-card/img/secure-transaction.svg b/libs/blocks/merch-card/img/secure-transaction.svg new file mode 100644 index 0000000000..461460b91b --- /dev/null +++ b/libs/blocks/merch-card/img/secure-transaction.svg @@ -0,0 +1,10 @@ + + + + + + + + diff --git a/libs/blocks/merch-card/merch-card.css b/libs/blocks/merch-card/merch-card.css index 6a9a37ed6c..e69de29bb2 100644 --- a/libs/blocks/merch-card/merch-card.css +++ b/libs/blocks/merch-card/merch-card.css @@ -1,256 +0,0 @@ -/* stylelint-disable selector-class-pattern */ -.merch-card hr { - background-color: var(--color-gray-200); - border: none; - height: 1px; - width: 100%; - margin-bottom: var(--spacing-xs); -} - -.merch-card p { - font-size: var(--type-body-xs-size); - font-weight: 400; - line-height: 1.5; - margin-bottom: var(--spacing-xxs); - margin-top: 0; - color: var(--color-black); -} - -.merch-card h1, -.merch-card h2, -.merch-card h3, -.merch-card h4, -.merch-card h5, -.merch-card h6 { - line-height: 1.25; - margin-top: 0; - color: var(--color-black); -} - -.merch-card h2 { - font-size: var(--type-heading-l-size); - margin-bottom: var(--spacing-xxs); -} - -.merch-card h3, -.merch-card h4 { - font-size: var(--type-heading-xs-size); - margin-bottom: var(--spacing-xxs); -} - -.merch-card h5 { - font-size: var(--type-heading-xs-size); -} - -.merch-card .consonant-MerchCard-ProductIcon { - background-size: contain; - background-repeat: no-repeat; - position: relative; - margin-right: var(--spacing-xxs); - margin-bottom: var(--spacing-xxs); - display: block; - float: left; - width: 40px; - height: 40px; -} - -.merch-card div[class$="-title"] { - width: 100%; - font-size: var(--type-heading-xs-lh); - font-weight: var(--type-heading-all-weight); - align-self: flex-start; - max-height: max-content; - flex: none; -} - -.merch-card h4.consonant-SpecialOffers-title { - text-transform: uppercase; -} - -.merch-card h2.consonant-PlansCard-title { - font-size: var(--type-heading-m-size); - line-height: var(--type-heading-l-lh); -} - -.merch-card h3.consonant-SpecialOffers-title, -.merch-card h3.consonant-PlansCard-title { - margin-bottom: 0; -} - -.merch-card h3.consonant-PlansCard-title { - margin-bottom: var(--spacing-xxs); - line-height: var(--type-heading-s-lh); -} - -.merch-card h4.consonant-PlansCard-title { - font-size: var(--type-body-xxs-size); - font-style: italic; -} - -.merch-card h5[class$="-title"] { - font-size: var(--type-heading-xxs-size); - font-weight: 500; -} - -.merch-card.segment { - position: relative; - display: flex; - flex-direction: column; - min-height: 222px; - width: 100%; - flex: 1; - min-width: 378px; - max-width: 378px; -} - -.merch-card.special-offers, -.merch-card.segment, -.merch-card.plans { - border-radius: 16px; -} - -.merch-card.special-offers.full-width { - min-width: 100%; - max-width: 100%; - width: 1200px; -} - -.merch-card.special-offers.center { - text-align: center; -} - -.merch-card div[class$="-inner"] { - display: flex; - flex-direction: column; - flex-grow: 1; - padding: 16px 16px 20px; - border-radius: 4px; - background-color: var(--color-white); - text-decoration: none; -} - -.merch-card .consonant-PlansCard-inner { - padding: var(--spacing-xs); -} - -.merch-card div[class$="-prices"] { - font-size: var(--type-body-s-size); - line-height: 24px; - margin-bottom: var(--spacing-xxs); -} - -.merch-card div[class$="-description"] { - width: 100%; - font-size: var(--type-heading-xs-size); - line-height: 1.5; - margin-top: 0; - align-self: flex-start; - flex-grow: 1; -} - -.merch-card .consonant-SegmentBlade-description span.placeholder-resolved, -.merch-card .consonant-SpecialOffers-description span.placeholder-resolved, -.merch-card .consonant-PlansCard-description span.placeholder-resolved { - font-size: var(--type-heading-xs-size);; -} - -.merch-card .consonant-SegmentBlade-description span.placeholder-resolved[data-template="priceStrikethrough"], -.merch-card .consonant-SpecialOffers-description span.placeholder-resolved[data-template="priceStrikethrough"], -.merch-card .consonant-PlansCard-description span.placeholder-resolved[data-template="priceStrikethrough"] { - font-size: var(--type-body-xs-size); -} - -.merch-card.consonant-SpecialOffers-Card { - border-radius: 16px; -} - -.merch-card .consonant-SpecialOffers-img, -.merch-card .consonant-PlansCard-img { - flex-grow: 1; - position: relative; - width: 100%; - min-height: 213px; - max-height: 213px; - background-color: var(--background-color); - background-position: 50% 50%; - background-repeat: no-repeat; - background-size: cover; -} - -.merch-card div[class$="-ribbon"] { - position: absolute; - top: 16px; - right: 0; - font-size: var(--type-heading-xxs-size); - font-weight: 500; - max-width: 150px; - line-height: 16px; - text-align: center; - padding: 8px 11px; - border-radius: 5px 0 0 5px; -} - -.merch-card .consonant-SpecialOffers-ribbon { - text-transform: uppercase; -} - -.merch-card .consonant-SpecialOffers-inner, -.merch-card .consonant-PlansCard-inner { - justify-content: center; - height: 100%; -} - -.merch-card.special-offers .consonant-SpecialOffers-description p, -.merch-card.special-offers .consonant-PlansCard-description p { - font-size: var(--type-body-xs-size); -} - -.merch-card .consonant-SpecialOffers-description em, -.merch-card .consonant-PlansCard-description em { - color: var(--color-gray-600); -} - -.merch-card.special-offers h4 { - font-size: var(--type-body-xxs-size); - text-transform: uppercase; - letter-spacing: 1px; -} - -.merch-card .checkbox-container { - cursor: pointer; - margin-bottom: var(--spacing-xs); -} - -.merch-card.has-divider hr { - margin: var(--spacing-xxs) 0; -} - -.merch-card.has-divider .consonant-CardFooter hr { - display: none; -} - -.merch-card.background-opacity-70 { - background-color: rgba(255 255 255 / 70%); -} - -.merch-card.background-opacity-70 div[class$="-inner"] { - background-color: transparent; -} - -.merch-card.inline-heading .consonant-SegmentBlade-inner { - display: grid; - column-gap: 12px; - align-items: center; - grid-template-columns: 40px 1fr; -} - -.merch-card.inline-heading .consonant-SegmentBlade-description, -.merch-card.inline-heading .consonant-CardFooter { - grid-column: span 2; -} - -.dark .merch-card .consonant-CardFooter .con-button.outline { - border-color: var(--color-black); - color: var(--color-black); -} - diff --git a/libs/blocks/merch-card/merch-card.js b/libs/blocks/merch-card/merch-card.js index 70341f28a9..48124a62ff 100644 --- a/libs/blocks/merch-card/merch-card.js +++ b/libs/blocks/merch-card/merch-card.js @@ -97,21 +97,62 @@ const returnRibbonStyle = (ribbonMetadata) => { return { style, value }; }; +const getActionMenuContent = (el, ribbonMetadata) => { + if (ribbonMetadata !== null) { + if (el.childElementCount === 3) { + const actionMenuContentWrapper = el.children[1]; + const actionMenuContent = actionMenuContentWrapper.children[0]; + actionMenuContentWrapper.remove(); + return actionMenuContent; + } else return null; + } else { + if (el.childElementCount === 2) { + const actionMenuContentWrapper = el.children[0]; + const actionMenuContent = actionMenuContentWrapper.children[0]; + actionMenuContentWrapper.remove(); + return actionMenuContent; + } else return null; + } +}; + +const getMerchCardRows = (rows, ribbonMetadata, cardType, actionMenuContent) => { + if (cardType === 'catalog') { + if (ribbonMetadata !== null) { + if (actionMenuContent !== null) { + return rows[2]; + } else { + return rows[1]; + } + } else { + if (actionMenuContent !== null) { + return rows[1]; + } else { + return rows[0]; + } + } + } else { + return rows[ribbonMetadata === null ? 0 : 1]; + } +}; + const init = (el) => { + const section = el.closest('.section'); + section.classList.add('merch-card-collection'); const headings = el.querySelectorAll('h1, h2, h3, h4, h5, h6'); decorateLinkAnalytics(el, headings); const images = el.querySelectorAll('picture'); let image; const icons = []; const rows = el.querySelectorAll(':scope > *'); + const styles = [...el.classList]; + const cardType = getPodType(styles); const ribbonMetadata = rows[0].children?.length === 2 ? rows[0].children : null; - const row = rows[ribbonMetadata === null ? 0 : 1]; + const actionMenuContent = cardType === 'catalog' ? getActionMenuContent(el, ribbonMetadata) : null; + const row = getMerchCardRows(rows, ribbonMetadata, cardType, actionMenuContent); const altCta = rows[rows.length - 1].children?.length === 2 ? rows[rows.length - 1].children : null; const allPElems = row.querySelectorAll('p'); const ctas = allPElems[allPElems.length - 1]; - const styles = [...el.classList]; - const cardType = getPodType(styles); decorateBlockHrs(el); images.forEach((img) => { const imgNode = img.querySelector('img'); @@ -135,6 +176,12 @@ const init = (el) => { merchCard.setAttribute('badge', JSON.stringify(badge)); } } + + if (actionMenuContent !== null) { + merchCard.setAttribute('actionmenu', true); + merchCard.append(createTag('div', { slot: 'actionMenuContent' }, actionMenuContent.innerHTML)); + } + if (image !== undefined) { merchCard.setAttribute('image', image.querySelector('img').src); image?.parentElement.remove(); diff --git a/libs/blocks/merch/merch.js b/libs/blocks/merch/merch.js index 4c46799fe8..aeeb5d2820 100644 --- a/libs/blocks/merch/merch.js +++ b/libs/blocks/merch/merch.js @@ -74,6 +74,7 @@ export async function getPriceContext(el, params) { const displayPerUnit = params.get('seat'); const displayRecurrence = params.get('term'); const displayTax = params.get('tax'); + const forceTaxExclusive = params.get('exclusive'); const type = params.get('type'); const template = type === 'price' ? undefined : type; return { @@ -82,6 +83,7 @@ export async function getPriceContext(el, params) { displayPerUnit, displayRecurrence, displayTax, + forceTaxExclusive, template, }; } diff --git a/libs/blocks/ost/ost.js b/libs/blocks/ost/ost.js index c1154262bf..ed3ecf04c2 100644 --- a/libs/blocks/ost/ost.js +++ b/libs/blocks/ost/ost.js @@ -56,10 +56,11 @@ export const createLinkMarkup = (defaults) => ( params.set('workflowStep', workflowStep); } } else { - const { displayRecurrence, displayPerUnit, displayTax } = options; + const { displayRecurrence, displayPerUnit, displayTax, forceTaxExclusive } = options; params.set('term', displayRecurrence); params.set('seat', displayPerUnit); params.set('tax', displayTax); + params.set('exclusive', forceTaxExclusive); } const { location } = window; return `${location.protocol + location.host}/tools/ost?${params.toString()}`; diff --git a/libs/blocks/quiz-results/quiz-results.css b/libs/blocks/quiz-results/quiz-results.css index c6f37879a7..7a414a4490 100644 --- a/libs/blocks/quiz-results/quiz-results.css +++ b/libs/blocks/quiz-results/quiz-results.css @@ -16,14 +16,13 @@ } .quiz-results .quiz-card-list { - align-items: center; - display: flex; - gap: var(--spacing-s); + display: grid; justify-content: center; - margin: 0 auto; - padding: var(--spacing-s) 0; - position: relative; - flex-wrap: wrap; + width: 100%; + max-width: 100%; + grid-template-columns: repeat(auto-fit,minmax(300px,max-content)); + gap: 32px; + padding-bottom: 32px; } @media screen and (min-width: 600px) { diff --git a/libs/features/personalization/personalization.js b/libs/features/personalization/personalization.js index baf7ca5a2a..dd6941eaf7 100644 --- a/libs/features/personalization/personalization.js +++ b/libs/features/personalization/personalization.js @@ -49,19 +49,23 @@ const DATA_TYPE = { TEXT: 'text', }; -const createFrag = (url, manifestId) => { +const createFrag = (el, url, manifestId) => { const a = createTag('a', { href: url }, url); if (manifestId) a.dataset.manifestId = manifestId; - const p = createTag('p', undefined, a); + let frag = createTag('p', undefined, a); + const isSection = el.parentElement.nodeName === 'MAIN'; + if (isSection) { + frag = createTag('div', undefined, frag); + } loadLink(`${url}.plain.html`, { as: 'fetch', crossorigin: 'anonymous', rel: 'preload' }); - return p; + return frag; }; const COMMANDS = { insertcontentafter: (el, target, manifestId) => el - .insertAdjacentElement('afterend', createFrag(target, manifestId)), + .insertAdjacentElement('afterend', createFrag(el, target, manifestId)), insertcontentbefore: (el, target, manifestId) => el - .insertAdjacentElement('beforebegin', createFrag(target, manifestId)), + .insertAdjacentElement('beforebegin', createFrag(el, target, manifestId)), removecontent: (el, target, manifestId) => { if (target === 'false') return; if (manifestId) { @@ -72,7 +76,7 @@ const COMMANDS = { }, replacecontent: (el, target, manifestId) => { if (el.classList.contains(CLASS_EL_REPLACE)) return; - el.insertAdjacentElement('beforebegin', createFrag(target, manifestId)); + el.insertAdjacentElement('beforebegin', createFrag(el, target, manifestId)); el.classList.add(CLASS_EL_DELETE, CLASS_EL_REPLACE); }, }; @@ -181,11 +185,8 @@ function handleCommands(commands, manifestId, rootEl = document) { commands.forEach((cmd) => { if (VALID_COMMANDS.includes(cmd.action)) { try { - let selectorEl = rootEl.querySelector(cmd.selector); + const selectorEl = rootEl.querySelector(cmd.selector); if (!selectorEl) return; - if (selectorEl.classList[0] === 'section-metadata') { - selectorEl = selectorEl.parentElement || selectorEl; - } COMMANDS[cmd.action](selectorEl, cmd.target, manifestId); } catch (e) { console.log('Invalid selector: ', cmd.selector); @@ -259,7 +260,7 @@ export function parseConfig(data) { /* c8 ignore start */ function parsePlaceholders(placeholders, config, selectedVariantName = '') { - if (!placeholders?.length || selectedVariantName === 'no changes') return config; + if (!placeholders?.length || selectedVariantName === 'default') return config; const valueNames = [ 'value', selectedVariantName.toLowerCase(), @@ -440,9 +441,9 @@ export async function getPersConfig(name, variantLabel, manifestData, manifestPa config.selectedVariantName = selectedVariantName; config.selectedVariant = config.variants[selectedVariantName]; } else { - /* c8 ignore next */ - config.selectedVariantName = 'no changes'; - config.selectedVariant = 'no changes'; + /* c8 ignore next 2 */ + config.selectedVariantName = 'default'; + config.selectedVariant = 'default'; } if (placeholders) { @@ -480,7 +481,7 @@ export async function runPersonalization(info, config) { const { selectedVariant } = experiment; if (!selectedVariant) return {}; - if (selectedVariant === 'no changes') { + if (selectedVariant === 'default') { return { experiment }; } diff --git a/libs/features/personalization/preview.js b/libs/features/personalization/preview.js index 9927088caf..7d3c775653 100644 --- a/libs/features/personalization/preview.js +++ b/libs/features/personalization/preview.js @@ -153,11 +153,11 @@ function createPreviewPill(manifests) { if (!manifest.variantNames.includes(manifest.selectedVariantName)) { checked.attribute = 'checked="checked"'; checked.class = 'class="mep-manifest-selected-variant"'; - manifestParameter.push(`${manifest.manifest}--NoChanges`); + manifestParameter.push(`${manifest.manifest}--default`); } radio += `
- - + +
`; const targetTitle = manifest.name ? `${manifest.name}
${manifest.manifest}` : manifest.manifest; manifestList += `
diff --git a/libs/scripts/taxonomy.js b/libs/scripts/taxonomy.js index e2825da94a..9dd68a22bd 100644 --- a/libs/scripts/taxonomy.js +++ b/libs/scripts/taxonomy.js @@ -67,7 +67,7 @@ async function fetchTaxonomy(target) { return fetch(target).then((response) => response.json()); } -function parseTaxonomyJson(data, root) { +function parseTaxonomyJson(data, root, route) { let level1; let level2; return data?.reduce((taxonomy, row) => { const level3 = removeLineBreaks(row[TAXONOMY_FIELDS.level3]); @@ -94,7 +94,7 @@ function parseTaxonomyJson(data, root) { ? new URL([row[TAXONOMY_FIELDS.link]]) : generateUri(name); const path = taxLink.pathname - ? taxLink.pathname?.replace('.html', '').split('/topics/').pop() + ? taxLink.pathname?.replace('.html', '').split(`${route}/`).pop() : taxLink; const link = `${root}/${path}`; const hidden = !!row[TAXONOMY_FIELDS.hidden]?.trim(); @@ -164,7 +164,7 @@ export default async (config, route, target) => { return fetchTaxonomy(path) .then((json) => { - const taxonomy = parseTaxonomyJson(json.data, root); + const taxonomy = parseTaxonomyJson(json.data, root, route); return { CATEGORIES, diff --git a/libs/utils/utils.js b/libs/utils/utils.js index 9d640c2c2a..80cf597e1e 100644 --- a/libs/utils/utils.js +++ b/libs/utils/utils.js @@ -1027,7 +1027,7 @@ export async function loadArea(area = document) { areaBlocks.push(...sectionBlocks); areaBlocks.forEach((block) => { - block.dataset.block = ''; + if (!block.className.includes('metadata')) block.dataset.block = ''; }); } diff --git a/test/blocks/caas-config/caas-config.test.html b/test/blocks/caas-config/caas-config.test.html index 9203d5ecb0..a2e2ac1f31 100644 --- a/test/blocks/caas-config/caas-config.test.html +++ b/test/blocks/caas-config/caas-config.test.html @@ -193,7 +193,7 @@ expectedConfig.hideCtaIds = ['hide-cta-id']; expect(config).to.eql(expectedConfig); }); - + it('Can add tags to use for hiding ctas', async() => { await tagSelectorModalChoose('Tags that should hide CTAS', [ @@ -285,7 +285,7 @@ copyBtn.click(); await delay(50); const copyTextArea = document.querySelector('.copy-text'); - expect(copyTextArea.value.split('#')[1]).to.equal('eyJhZGRpdGlvbmFsUmVxdWVzdFBhcmFtcyI6W10sImFuYWx5dGljc0NvbGxlY3Rpb25OYW1lIjoiIiwiYW5hbHl0aWNzVHJhY2tJbXByZXNzaW9uIjpmYWxzZSwiYW5kTG9naWNUYWdzIjpbXSwiYXV0b0NvdW50cnlMYW5nIjpmYWxzZSwiYm9va21hcmtJY29uU2VsZWN0IjoiIiwiYm9va21hcmtJY29uVW5zZWxlY3QiOiIiLCJjYXJkU3R5bGUiOiJoYWxmLWhlaWdodCIsImNhcmRUaXRsZUFjY2Vzc2liaWxpdHlMZXZlbCI6NiwiY29sbGVjdGlvbkJ0blN0eWxlIjoicHJpbWFyeSIsImNvbGxlY3Rpb25OYW1lIjoiIiwiY29sbGVjdGlvblRpdGxlIjoiIiwiY29sbGVjdGlvblNpemUiOiIiLCJjb250YWluZXIiOiIxMjAwTWF4V2lkdGgiLCJjb250ZW50VHlwZVRhZ3MiOltdLCJjb3VudHJ5IjoiY2Fhczpjb3VudHJ5L3VzIiwiY3VzdG9tQ2FyZCI6IiIsImN0YUFjdGlvbiI6Il9ibGFuayIsImRvTm90TGF6eUxvYWQiOmZhbHNlLCJkaXNhYmxlQmFubmVycyI6ZmFsc2UsImRyYWZ0RGIiOmZhbHNlLCJlbmRwb2ludCI6Ind3dy5hZG9iZS5jb20vY2hpbWVyYS1hcGkvY29sbGVjdGlvbiIsImVudmlyb25tZW50IjoiIiwiZXhjbHVkZWRDYXJkcyI6W10sImV4Y2x1ZGVUYWdzIjpbXSwiZmFsbGJhY2tFbmRwb2ludCI6IiIsImZlYXR1cmVkQ2FyZHMiOltdLCJmaWx0ZXJFdmVudCI6IiIsImZpbHRlckJ1aWxkUGFuZWwiOiJhdXRvbWF0aWMiLCJmaWx0ZXJMb2NhdGlvbiI6ImxlZnQiLCJmaWx0ZXJMb2dpYyI6Im9yIiwiZmlsdGVycyI6W10sImZpbHRlcnNDdXN0b20iOltdLCJmaWx0ZXJzU2hvd0VtcHR5IjpmYWxzZSwiZ3V0dGVyIjoiNHgiLCJoZWFkZXJzIjpbXSwiaGlkZUN0YUlkcyI6W10sImhpZGVDdGFUYWdzIjpbXSwiaW5jbHVkZVRhZ3MiOltdLCJsYW5ndWFnZSI6ImNhYXM6bGFuZ3VhZ2UvZW4iLCJsYXlvdXRUeXBlIjoiNHVwIiwibG9hZE1vcmVCdG5TdHlsZSI6InByaW1hcnkiLCJvbmx5U2hvd0Jvb2ttYXJrZWRDYXJkcyI6ZmFsc2UsIm9yTG9naWNUYWdzIjpbXSwicGFnaW5hdGlvbkFuaW1hdGlvblN0eWxlIjoicGFnZWQiLCJwYWdpbmF0aW9uRW5hYmxlZCI6ZmFsc2UsInBhZ2luYXRpb25RdWFudGl0eVNob3duIjpmYWxzZSwicGFnaW5hdGlvblR5cGUiOiJwYWdpbmF0b3IiLCJwYWdpbmF0aW9uVXNlVGhlbWUzIjpmYWxzZSwicGxhY2Vob2xkZXJVcmwiOiIiLCJyZXN1bHRzUGVyUGFnZSI6NSwic2VhcmNoRmllbGRzIjpbXSwic2V0Q2FyZEJvcmRlcnMiOmZhbHNlLCJzaG93Qm9va21hcmtzRmlsdGVyIjpmYWxzZSwic2hvd0Jvb2ttYXJrc09uQ2FyZHMiOmZhbHNlLCJzaG93RmlsdGVycyI6ZmFsc2UsInNob3dTZWFyY2giOmZhbHNlLCJzaG93VG90YWxSZXN1bHRzIjpmYWxzZSwic29ydERhdGVBc2MiOmZhbHNlLCJzb3J0RGF0ZURlc2MiOmZhbHNlLCJzb3J0RGF0ZU1vZGlmaWVkIjpmYWxzZSwic29ydERlZmF1bHQiOiJkYXRlRGVzYyIsInNvcnRFbmFibGVQb3B1cCI6ZmFsc2UsInNvcnRFbmFibGVSYW5kb21TYW1wbGluZyI6ZmFsc2UsInNvcnRFdmVudFNvcnQiOmZhbHNlLCJzb3J0RmVhdHVyZWQiOmZhbHNlLCJzb3J0TW9kaWZpZWRBc2MiOmZhbHNlLCJzb3J0TW9kaWZpZWREZXNjIjpmYWxzZSwic29ydFJhbmRvbSI6ZmFsc2UsInNvcnRSZXNlcnZvaXJQb29sIjoxMDAwLCJzb3J0UmVzZXJ2b2lyU2FtcGxlIjozLCJzb3J0VGl0bGVBc2MiOmZhbHNlLCJzb3J0VGl0bGVEZXNjIjpmYWxzZSwic291cmNlIjpbImhhd2tzIl0sInRhZ3NVcmwiOiJ3d3cuYWRvYmUuY29tL2NoaW1lcmEtYXBpL3RhZ3MiLCJ0YXJnZXRBY3Rpdml0eSI6IiIsInRhcmdldEVuYWJsZWQiOmZhbHNlLCJ0aGVtZSI6ImxpZ2h0ZXN0IiwiZGV0YWlsc1RleHRPcHRpb24iOiJkZWZhdWx0IiwidGl0bGVIZWFkaW5nTGV2ZWwiOiJoMyIsInRvdGFsQ2FyZHNUb1Nob3ciOjEwLCJ1c2VMaWdodFRleHQiOmZhbHNlLCJ1c2VPdmVybGF5TGlua3MiOmZhbHNlLCJjb2xsZWN0aW9uQnV0dG9uU3R5bGUiOiJwcmltYXJ5IiwidXNlckluZm8iOltdfQ==') + expect(copyTextArea.value.split('#')[1]).to.equal('eyJhZGRpdGlvbmFsUmVxdWVzdFBhcmFtcyI6W10sImFuYWx5dGljc0NvbGxlY3Rpb25OYW1lIjoiIiwiYW5hbHl0aWNzVHJhY2tJbXByZXNzaW9uIjpmYWxzZSwiYW5kTG9naWNUYWdzIjpbXSwiYXV0b0NvdW50cnlMYW5nIjpmYWxzZSwiYm9va21hcmtJY29uU2VsZWN0IjoiIiwiYm9va21hcmtJY29uVW5zZWxlY3QiOiIiLCJjYXJkU3R5bGUiOiJoYWxmLWhlaWdodCIsImNhcmRUaXRsZUFjY2Vzc2liaWxpdHlMZXZlbCI6NiwiY29sbGVjdGlvbkJ0blN0eWxlIjoicHJpbWFyeSIsImNvbGxlY3Rpb25OYW1lIjoiIiwiY29sbGVjdGlvblRpdGxlIjoiIiwiY29sbGVjdGlvblNpemUiOiIiLCJjb250YWluZXIiOiIxMjAwTWF4V2lkdGgiLCJjb250ZW50VHlwZVRhZ3MiOltdLCJjb3VudHJ5IjoiY2Fhczpjb3VudHJ5L3VzIiwiY3VzdG9tQ2FyZCI6IiIsImN0YUFjdGlvbiI6Il9zZWxmIiwiZG9Ob3RMYXp5TG9hZCI6ZmFsc2UsImRpc2FibGVCYW5uZXJzIjpmYWxzZSwiZHJhZnREYiI6ZmFsc2UsImVuZHBvaW50Ijoid3d3LmFkb2JlLmNvbS9jaGltZXJhLWFwaS9jb2xsZWN0aW9uIiwiZW52aXJvbm1lbnQiOiIiLCJleGNsdWRlZENhcmRzIjpbXSwiZXhjbHVkZVRhZ3MiOltdLCJmYWxsYmFja0VuZHBvaW50IjoiIiwiZmVhdHVyZWRDYXJkcyI6W10sImZpbHRlckV2ZW50IjoiIiwiZmlsdGVyQnVpbGRQYW5lbCI6ImF1dG9tYXRpYyIsImZpbHRlckxvY2F0aW9uIjoibGVmdCIsImZpbHRlckxvZ2ljIjoib3IiLCJmaWx0ZXJzIjpbXSwiZmlsdGVyc0N1c3RvbSI6W10sImZpbHRlcnNTaG93RW1wdHkiOmZhbHNlLCJndXR0ZXIiOiI0eCIsImhlYWRlcnMiOltdLCJoaWRlQ3RhSWRzIjpbXSwiaGlkZUN0YVRhZ3MiOltdLCJpbmNsdWRlVGFncyI6W10sImxhbmd1YWdlIjoiY2FhczpsYW5ndWFnZS9lbiIsImxheW91dFR5cGUiOiI0dXAiLCJsb2FkTW9yZUJ0blN0eWxlIjoicHJpbWFyeSIsIm9ubHlTaG93Qm9va21hcmtlZENhcmRzIjpmYWxzZSwib3JMb2dpY1RhZ3MiOltdLCJwYWdpbmF0aW9uQW5pbWF0aW9uU3R5bGUiOiJwYWdlZCIsInBhZ2luYXRpb25FbmFibGVkIjpmYWxzZSwicGFnaW5hdGlvblF1YW50aXR5U2hvd24iOmZhbHNlLCJwYWdpbmF0aW9uVHlwZSI6InBhZ2luYXRvciIsInBhZ2luYXRpb25Vc2VUaGVtZTMiOmZhbHNlLCJwbGFjZWhvbGRlclVybCI6IiIsInJlc3VsdHNQZXJQYWdlIjo1LCJzZWFyY2hGaWVsZHMiOltdLCJzZXRDYXJkQm9yZGVycyI6ZmFsc2UsInNob3dCb29rbWFya3NGaWx0ZXIiOmZhbHNlLCJzaG93Qm9va21hcmtzT25DYXJkcyI6ZmFsc2UsInNob3dGaWx0ZXJzIjpmYWxzZSwic2hvd1NlYXJjaCI6ZmFsc2UsInNob3dUb3RhbFJlc3VsdHMiOmZhbHNlLCJzb3J0RGF0ZUFzYyI6ZmFsc2UsInNvcnREYXRlRGVzYyI6ZmFsc2UsInNvcnREYXRlTW9kaWZpZWQiOmZhbHNlLCJzb3J0RGVmYXVsdCI6ImRhdGVEZXNjIiwic29ydEVuYWJsZVBvcHVwIjpmYWxzZSwic29ydEVuYWJsZVJhbmRvbVNhbXBsaW5nIjpmYWxzZSwic29ydEV2ZW50U29ydCI6ZmFsc2UsInNvcnRGZWF0dXJlZCI6ZmFsc2UsInNvcnRNb2RpZmllZEFzYyI6ZmFsc2UsInNvcnRNb2RpZmllZERlc2MiOmZhbHNlLCJzb3J0UmFuZG9tIjpmYWxzZSwic29ydFJlc2Vydm9pclBvb2wiOjEwMDAsInNvcnRSZXNlcnZvaXJTYW1wbGUiOjMsInNvcnRUaXRsZUFzYyI6ZmFsc2UsInNvcnRUaXRsZURlc2MiOmZhbHNlLCJzb3VyY2UiOlsiaGF3a3MiXSwidGFnc1VybCI6Ind3dy5hZG9iZS5jb20vY2hpbWVyYS1hcGkvdGFncyIsInRhcmdldEFjdGl2aXR5IjoiIiwidGFyZ2V0RW5hYmxlZCI6ZmFsc2UsInRoZW1lIjoibGlnaHRlc3QiLCJkZXRhaWxzVGV4dE9wdGlvbiI6ImRlZmF1bHQiLCJ0aXRsZUhlYWRpbmdMZXZlbCI6ImgzIiwidG90YWxDYXJkc1RvU2hvdyI6MTAsInVzZUxpZ2h0VGV4dCI6ZmFsc2UsInVzZU92ZXJsYXlMaW5rcyI6ZmFsc2UsImNvbGxlY3Rpb25CdXR0b25TdHlsZSI6InByaW1hcnkiLCJ1c2VySW5mbyI6W119') }); it('Clones an object', () => { diff --git a/test/blocks/caas-config/expectedConfigs/defaultConfig.js b/test/blocks/caas-config/expectedConfigs/defaultConfig.js index 21be703400..1711b2883f 100644 --- a/test/blocks/caas-config/expectedConfigs/defaultConfig.js +++ b/test/blocks/caas-config/expectedConfigs/defaultConfig.js @@ -34,7 +34,7 @@ const defaultConfig = { useLightText: false, disableBanners: false, reservoir: { sample: 3, pool: 1000 }, - ctaAction: '_blank', + ctaAction: '_self', additionalRequestParams: {}, }, headers: [], diff --git a/test/blocks/caas/mocks/utils.js b/test/blocks/caas/mocks/utils.js index 45890ab7be..81d347ed5a 100644 --- a/test/blocks/caas/mocks/utils.js +++ b/test/blocks/caas/mocks/utils.js @@ -8,6 +8,14 @@ export const loadScript = stub(); export const utf8ToB64 = (str) => window.btoa(unescape(encodeURIComponent(str))); +export const b64ToUtf8 = (str) => decodeURIComponent(escape(window.atob(str))); + +export function getMetadata(name, doc = document) { + const attr = name && name.includes(':') ? 'property' : 'name'; + const meta = doc.head.querySelector(`meta[${attr}="${name}"]`); + return meta && meta.content; +} + export function createIntersectionObserver({ el, callback /* , once = true, options = {} */ }) { // fire immediately callback(el, { target: el }); diff --git a/test/blocks/caas/utils.test.js b/test/blocks/caas/utils.test.js index 7643f3dfcf..7b83c03203 100644 --- a/test/blocks/caas/utils.test.js +++ b/test/blocks/caas/utils.test.js @@ -166,11 +166,11 @@ describe('getConfig', () => { collectionButtonStyle: 'primary', resultsPerPage: 5, endpoint: - 'https://www.adobe.com/chimera-api/collection/myTargetActivity.json?originSelection=hawks&contentTypeTags=&collectionTags=&excludeContentWithTags=&language=en&country=us&complexQuery=((%22caas%3Aproducts%2Findesign%22%2BAND%2B%22caas%3Aproducts%2Freader%22)%2BAND%2B(%22caas%3Acountry%2Fbr%22%2BOR%2B%22caas%3Acountry%2Fca%22))%2BAND%2B((%22caas%3Acontent-type%2Fvideo%22%2BAND%2B%22caas%3Acontent-type%2Fblog%22))&excludeIds=¤tEntityId=&featuredCards=a%2Cb&environment=&draft=false&size=10&flatFile=false', + 'https://www.adobe.com/chimera-api/collection/myTargetActivity.json?originSelection=hawks&contentTypeTags=&collectionTags=&excludeContentWithTags=&language=en&country=us&complexQuery=((%22caas%3Aproducts%2Findesign%22%2BAND%2B%22caas%3Aproducts%2Freader%22)%2BAND%2B(%22caas%3Acountry%2Fbr%22%2BOR%2B%22caas%3Acountry%2Fca%22))%2BAND%2B((%22caas%3Acontent-type%2Fvideo%22%2BAND%2B%22caas%3Acontent-type%2Fblog%22))&excludeIds=¤tEntityId=&featuredCards=a%2Cb&environment=&draft=true&size=10&flatFile=false', fallbackEndpoint: '', totalCardsToShow: 10, cardStyle: 'half-height', - ctaAction: '_blank', + ctaAction: '_self', detailsTextOption: 'default', showTotalResults: false, i18n: { @@ -197,7 +197,7 @@ describe('getConfig', () => { reservoir: { sample: 3, pool: 1000 }, }, featuredCards: ['a', 'b'], - headers: [], + headers: [['X-Adobe-Floodgate', 'pink']], hideCtaIds: [''], hideCtaTags: [], filterPanel: { @@ -361,11 +361,11 @@ describe('getConfig', () => { collectionButtonStyle: 'primary', resultsPerPage: 5, endpoint: - 'https://www.adobe.com/chimera-api/collection/myTargetActivity.json?originSelection=hawks&contentTypeTags=&collectionTags=&excludeContentWithTags=&language=fr&country=be&complexQuery=((%22caas%3Aproducts%2Findesign%22%2BAND%2B%22caas%3Aproducts%2Freader%22)%2BAND%2B(%22caas%3Acountry%2Fbr%22%2BOR%2B%22caas%3Acountry%2Fca%22))%2BAND%2B((%22caas%3Acontent-type%2Fvideo%22%2BAND%2B%22caas%3Acontent-type%2Fblog%22))&excludeIds=¤tEntityId=&featuredCards=a%2Cb&environment=&draft=false&size=10&flatFile=false', + 'https://www.adobe.com/chimera-api/collection/myTargetActivity.json?originSelection=hawks&contentTypeTags=&collectionTags=&excludeContentWithTags=&language=fr&country=be&complexQuery=((%22caas%3Aproducts%2Findesign%22%2BAND%2B%22caas%3Aproducts%2Freader%22)%2BAND%2B(%22caas%3Acountry%2Fbr%22%2BOR%2B%22caas%3Acountry%2Fca%22))%2BAND%2B((%22caas%3Acontent-type%2Fvideo%22%2BAND%2B%22caas%3Acontent-type%2Fblog%22))&excludeIds=¤tEntityId=&featuredCards=a%2Cb&environment=&draft=true&size=10&flatFile=false', fallbackEndpoint: '', totalCardsToShow: 10, cardStyle: 'half-height', - ctaAction: '_blank', + ctaAction: '_self', detailsTextOption: 'default', showTotalResults: false, i18n: { @@ -392,7 +392,7 @@ describe('getConfig', () => { reservoir: { sample: 3, pool: 1000 }, }, featuredCards: ['a', 'b'], - headers: [], + headers: [['X-Adobe-Floodgate', 'pink']], hideCtaIds: [''], hideCtaTags: [], filterPanel: { @@ -597,3 +597,193 @@ describe('getCountryAndLang', () => { }); }); }); + +describe('getFloodgateCaasConfig', () => { + const caasFgState = defaultState; + caasFgState.fetchCardsFromFloodgateTree = true; + caasFgState.draftDb = true; + + it('should return a floodgate enabled caas config object', async () => { + const caasFgConfig = await getConfig(caasFgState, strings); + expect(caasFgConfig).to.be.eql({ + collection: { + mode: 'lightest', + layout: { type: '4up', gutter: '4x', container: '1200MaxWidth' }, + button: { style: 'primary' }, + collectionButtonStyle: 'primary', + resultsPerPage: 5, + endpoint: + 'https://www.adobe.com/chimera-api/collection/myTargetActivity.json?originSelection=hawks&contentTypeTags=&collectionTags=&excludeContentWithTags=&language=en&country=us&complexQuery=((%22caas%3Aproducts%2Findesign%22%2BAND%2B%22caas%3Aproducts%2Freader%22)%2BAND%2B(%22caas%3Acountry%2Fbr%22%2BOR%2B%22caas%3Acountry%2Fca%22))%2BAND%2B((%22caas%3Acontent-type%2Fvideo%22%2BAND%2B%22caas%3Acontent-type%2Fblog%22))&excludeIds=¤tEntityId=&featuredCards=a%2Cb&environment=&draft=true&size=10&flatFile=false', + fallbackEndpoint: '', + totalCardsToShow: 10, + cardStyle: 'half-height', + ctaAction: '_blank', + detailsTextOption: 'default', + showTotalResults: false, + i18n: { + cardTitleAccessibilityLevel: 6, + lastModified: 'Last modified {date}', + prettyDateIntervalFormat: '{ddd}, {LLL} {dd} | {timeRange} {timeZone}', + totalResultsText: '{total} Results', + title: '', + onErrorTitle: 'Error Loading Title', + onErrorDescription: 'Error Desc', + titleHeadingLevel: 'h3', + }, + setCardBorders: false, + useOverlayLinks: false, + additionalRequestParams: {}, + banner: { + register: { description: 'Sign Up', url: '#registration' }, + upcoming: { description: 'Upcoming' }, + live: { description: 'Live' }, + onDemand: { description: 'On Demand' }, + }, + useLightText: false, + disableBanners: false, + reservoir: { sample: 3, pool: 1000 }, + }, + featuredCards: ['a', 'b'], + headers: [['X-Adobe-Floodgate', 'pink']], + hideCtaIds: [''], + hideCtaTags: [], + filterPanel: { + enabled: true, + eventFilter: '', + type: 'left', + showEmptyFilters: false, + filters: [ + { + group: 'Life Sciences', + id: 'caas:industry/life-sciences', + items: [], + openedOnLoad: true, + }, + { + group: 'Journey Phase', + icon: '/path/to/icon.svg', + id: 'caas:journey-phase', + items: [ + { + id: 'caas:journey-phase/acceleration', + label: 'Acceleration', + }, + { + id: 'caas:journey-phase/acquisition', + label: 'Acquisition', + }, + { + id: 'caas:journey-phase/discover', + label: 'Discover', + }, + { + id: 'caas:journey-phase/evaluate', + label: 'Evaluate', + }, + { + id: 'caas:journey-phase/explore', + label: 'Explore', + }, + { + id: 'caas:journey-phase/retention', + label: 'Retention', + }, + ], + openedOnLoad: false, + }, + ], + filterLogic: 'or', + i18n: { + leftPanel: { + header: 'Refine Your Results', + clearAllFiltersText: 'Clear All', + mobile: { + filtersBtnLabel: 'Filters', + panel: { + header: 'Filter by', + totalResultsText: '{total} Results', + applyBtnText: 'Apply', + clearFilterText: 'Clear', + doneBtnText: 'Done', + }, + group: { + totalResultsText: '{total} Results', + applyBtnText: 'Apply', + clearFilterText: 'Clear', + doneBtnText: 'Done', + }, + }, + }, + topPanel: { + groupLabel: 'Filters:', + clearAllFiltersText: 'Clear All', + moreFiltersBtnText: 'More Filters +', + mobile: { + group: { + totalResultsText: '{total} Results', + applyBtnText: 'Apply', + clearFilterText: 'Clear', + doneBtnText: 'Done', + }, + }, + }, + }, + }, + sort: { + enabled: false, + defaultSort: 'dateDesc', + options: [], + }, + pagination: { + animationStyle: 'paged', + enabled: false, + resultsQuantityShown: false, + loadMoreButton: { style: 'primary', useThemeThree: false }, + type: 'paginator', + i18n: { + loadMore: { btnText: 'Load More', resultsQuantityText: '{start} of {end} displayed' }, + paginator: { + resultsQuantityText: '{start} - {end} of {total} results', + prevLabel: 'Prev', + nextLabel: 'Next', + }, + }, + }, + bookmarks: { + showOnCards: false, + leftFilterPanel: { + bookmarkOnlyCollection: false, + showBookmarksFilter: false, + selectBookmarksIcon: '', + unselectBookmarksIcon: '', + }, + i18n: { + leftFilterPanel: { filterTitle: 'My favorites' }, + card: { saveText: 'Save Card', unsaveText: 'Unsave Card' }, + }, + }, + search: { + enabled: false, + searchFields: [], + i18n: { + noResultsTitle: 'No Results Found', + noResultsDescription: 'Try checking your spelling or broadening your search.', + leftFilterPanel: { searchTitle: 'Search', searchPlaceholderText: 'Search Here' }, + topFilterPanel: { searchPlaceholderText: 'Search Here' }, + filterInfo: { searchPlaceholderText: 'Search Here' }, + }, + }, + language: 'en', + country: 'us', + customCard: [ + 'card', + 'return ``', + ], + analytics: { trackImpressions: '', collectionIdentifier: '' }, + target: { + enabled: true, + lastViewedSession: '', + }, + }); + }); +}); diff --git a/test/blocks/merch/merch.test.js b/test/blocks/merch/merch.test.js index 3f0795a0ce..78616d1347 100644 --- a/test/blocks/merch/merch.test.js +++ b/test/blocks/merch/merch.test.js @@ -17,6 +17,28 @@ const config = { env: { name: 'prod' }, }; +/** + * utility function that tests Price spans against mock HTML + * + * @param {util} selector price span selector + * @param {*} expectedAttributes { : + * } + */ +const validatePriceSpan = async (selector, expectedAttributes) => { + const el = await merch(document.querySelector( + selector, + )); + const { nodeName, dataset } = await el.onceSettled(); + expect(nodeName).to.equal('SPAN'); + if (!expectedAttributes.template) { + expect(dataset.template).to.be.undefined; + } + Object.keys(expectedAttributes).forEach((key) => { + const value = expectedAttributes[key]; + expect(dataset[key], ` ${key} should equal ${value}`).to.equal(value); + }); +}; + describe('Merch Block', () => { after(async () => { delete window.lana; @@ -48,156 +70,72 @@ describe('Merch Block', () => { }); describe('Prices', () => { - it('renders merch link to price without term', async () => { - const el = await merch(document.querySelector( - '.merch.price.hide-term', - )); - const { nodeName, dataset } = await el.onceSettled(); - expect(nodeName).to.equal('SPAN'); - expect(dataset.template).to.be.undefined; - expect(dataset.displayRecurrence).to.equal('false'); + it('renders merch link to price without term (new)', async () => { + await validatePriceSpan('.merch.price.hide-term', { displayRecurrence: 'false' }); }); it('renders merch link to price with term', async () => { - const el = await merch(document.querySelector( - '.merch.price.term', - )); - const { nodeName, dataset } = await el.onceSettled(); - expect(nodeName).to.equal('SPAN'); - expect(dataset.template).to.be.undefined; - expect(dataset.displayRecurrence).to.be.undefined; + await validatePriceSpan('.merch.price.term', { displayRecurrence: undefined }); }); it('renders merch link to price with term and seat', async () => { - const el = await merch(document.querySelector( - '.merch.price.seat', - )); - const { nodeName, dataset } = await el.onceSettled(); - expect(nodeName).to.equal('SPAN'); - expect(dataset.template).to.be.undefined; - expect(dataset.displayPerUnit).to.equal('true'); + await validatePriceSpan('.merch.price.seat', { displayPerUnit: 'true' }); }); it('renders merch link to price with term and tax', async () => { - const el = await merch(document.querySelector( - '.merch.price.tax', - )); - const { nodeName, dataset } = await el.onceSettled(); - expect(nodeName).to.equal('SPAN'); - expect(dataset.template).to.be.undefined; - expect(dataset.displayTax).to.equal('true'); + await validatePriceSpan('.merch.price.tax', { displayTax: 'true' }); }); it('renders merch link to price with term, seat and tax', async () => { - const el = await merch(document.querySelector( - '.merch.price.seat.tax', - )); - const { nodeName, dataset } = await el.onceSettled(); - expect(nodeName).to.equal('SPAN'); - expect(dataset.template).to.be.undefined; - expect(dataset.displayTax).to.equal('true'); + await validatePriceSpan('.merch.price.seat.tax', { displayTax: 'true' }); }); it('renders merch link to strikethrough price with term, seat and tax', async () => { - const el = await merch(document.querySelector( - '.merch.price.strikethrough', - )); - const { nodeName, dataset } = await el.onceSettled(); - expect(nodeName).to.equal('SPAN'); - expect(dataset.template).to.equal('strikethrough'); + await validatePriceSpan('.merch.price.strikethrough', { template: 'strikethrough' }); }); it('renders merch link to optical price with term, seat and tax', async () => { - const el = await merch(document.querySelector( - '.merch.price.optical', - )); - const { nodeName, dataset } = await el.onceSettled(); - expect(nodeName).to.equal('SPAN'); - expect(dataset.template).to.equal('optical'); + await validatePriceSpan('.merch.price.optical', { template: 'optical' }); + }); + + it('renders merch link to tax exclusive price with tax exclusive attribute', async () => { + await validatePriceSpan('.merch.price.tax-exclusive', { forceTaxExclusive: 'true' }); }); }); describe('Promo Prices', () => { it('renders merch link to promo price with discount', async () => { - const el = await merch(document.querySelector( - '.merch.price.oldprice', - )); - const { nodeName, dataset } = await el.onceSettled(); - expect(nodeName).to.equal('SPAN'); - expect(dataset.template).to.be.undefined; - expect(dataset.promotionCode).to.equal(undefined); + await validatePriceSpan('.merch.price.oldprice', { promotionCode: undefined }); }); it('renders merch link to promo price without discount', async () => { - const el = await merch(document.querySelector( - '.merch.strikethrough.oldprice', - )); - const { nodeName, dataset } = await el.onceSettled(); - expect(nodeName).to.equal('SPAN'); - expect(dataset.template).to.equal('strikethrough'); - expect(dataset.promotionCode).to.equal(undefined); + await validatePriceSpan('.merch.strikethrough.oldprice', { template: 'strikethrough', promotionCode: undefined }); }); it('renders merch link to promo price with discount', async () => { - const el = await merch(document.querySelector( - '.merch.price.promo', - )); - const { nodeName, dataset } = await el.onceSettled(); - expect(nodeName).to.equal('SPAN'); - expect(dataset.template).to.be.undefined; - expect(dataset.promotionCode).to.equal('nicopromo'); + await validatePriceSpan('.merch.price.promo', { promotionCode: 'nicopromo' }); }); it('renders merch link to full promo price', async () => { - const el = await merch(document.querySelector( - '.merch.price.promo', - )); - const { nodeName, dataset } = await el.onceSettled(); - expect(nodeName).to.equal('SPAN'); - expect(dataset.template).to.be.undefined; - expect(dataset.promotionCode).to.equal('nicopromo'); + await validatePriceSpan('.merch.price.promo', { promotionCode: 'nicopromo' }); }); }); describe('Promo Prices in a fragment', () => { it('renders merch link to promo price with discount', async () => { - const el = await merch(document.querySelector( - '.fragment .merch.price.oldprice', - )); - const { nodeName, dataset } = await el.onceSettled(); - expect(nodeName).to.equal('SPAN'); - expect(dataset.template).to.be.undefined; - expect(dataset.promotionCode).to.equal(undefined); + await validatePriceSpan('.fragment .merch.price.oldprice', { promotionCode: undefined }); }); it('renders merch link to promo price without discount', async () => { - const el = await merch(document.querySelector( - '.fragment .merch.strikethrough.oldprice', - )); - const { nodeName, dataset } = await el.onceSettled(); - expect(nodeName).to.equal('SPAN'); - expect(dataset.template).to.equal('strikethrough'); - expect(dataset.promotionCode).to.equal(undefined); + await validatePriceSpan('.fragment .merch.strikethrough.oldprice', { template: 'strikethrough', promotionCode: undefined }); }); it('renders merch link to promo price with discount', async () => { - const el = await merch(document.querySelector( - '.fragment .merch.price.promo', - )); - const { nodeName, dataset } = await el.onceSettled(); - expect(nodeName).to.equal('SPAN'); - expect(dataset.template).to.be.undefined; - expect(dataset.promotionCode).to.equal('nicopromo'); + await validatePriceSpan('.fragment .merch.price.promo', { promotionCode: 'nicopromo' }); }); it('renders merch link to full promo price', async () => { - const el = await merch(document.querySelector( - '.fragment .merch.price.promo', - )); - const { nodeName, dataset } = await el.onceSettled(); - expect(nodeName).to.equal('SPAN'); - expect(dataset.template).to.be.undefined; - expect(dataset.promotionCode).to.equal('nicopromo'); + await validatePriceSpan('.fragment .merch.price.promo', { promotionCode: 'nicopromo' }); }); }); diff --git a/test/blocks/merch/mocks/body.html b/test/blocks/merch/mocks/body.html index 973997bed1..02229bb355 100644 --- a/test/blocks/merch/mocks/body.html +++ b/test/blocks/merch/mocks/body.html @@ -15,6 +15,9 @@

Regular prices

Hide term: Price - 632B3ADD940A7FBB7864AA5AD19B8D28 - All Apps

+

Force tax to be exclusive: Price - 632B3ADD940A7FBB7864AA5AD19B8D28 - All Apps +

Display term and seat texts: Price - 632B3ADD940A7FBB7864AA5AD19B8D28 - All Apps diff --git a/test/blocks/ost/ost.test.js b/test/blocks/ost/ost.test.js index 5652f8d6cb..598bcb0497 100644 --- a/test/blocks/ost/ost.test.js +++ b/test/blocks/ost/ost.test.js @@ -80,11 +80,19 @@ describe('function "createLinkMarkup"', () => { const displayRecurrence = true; const displayPerUnit = true; const displayTax = true; - const link = createLink({ displayRecurrence, displayPerUnit, displayTax, type }); + const forceTaxExclusive = true; + const link = createLink({ + displayRecurrence, + displayPerUnit, + displayTax, + forceTaxExclusive, + type, + }); assertLink(link, perpM2M, { term: displayRecurrence, seat: displayPerUnit, tax: displayTax, + exclusive: forceTaxExclusive, osi, type, }); diff --git a/tools/send-to-caas/send-utils.js b/tools/send-to-caas/send-utils.js index ce1b31f97a..aec500379b 100644 --- a/tools/send-to-caas/send-utils.js +++ b/tools/send-to-caas/send-utils.js @@ -416,7 +416,7 @@ const props = { cardimage: () => getCardImageUrl(), cardimagealttext: (s) => s || getCardImageAltText(), contentid: (_, options) => { - const floodGateColor = getMetadata('floodGateColor') || ''; + const floodGateColor = getMetadata('floodgatecolor') || ''; return getUuid(`${options.prodUrl}${floodGateColor}`); }, contenttype: (s) => s || getMetaContent('property', 'og:type') || getConfig().contentType, @@ -459,7 +459,7 @@ const props = { eventduration: 0, eventend: (s) => getDateProp(s, `Invalid Event End Date: ${s}`), eventstart: (s) => getDateProp(s, `Invalid Event Start Date: ${s}`), - floodgatecolor: (s) => s || getMetadata('floodGateColor') || 'default', + floodgatecolor: (s) => s || getMetadata('floodgatecolor') || 'default', lang: async (s, options) => { if (s) return s; const { lang } = await getCountryAndLang(options); diff --git a/tools/sidekick/config.json b/tools/sidekick/config.json index 58df0abdde..9f07415da8 100644 --- a/tools/sidekick/config.json +++ b/tools/sidekick/config.json @@ -32,6 +32,17 @@ "excludePaths": [ "/**" ], "includePaths": [ "**/:x**" ] }, + { + "containerId": "tools", + "id": "localize-v2", + "title": "Localize project (V2)", + "environments": [ "edit" ], + "url": "https://locui--milo--adobecom.hlx.page/tools/loc", + "passReferrer": true, + "passConfig": true, + "excludePaths": [ "/**" ], + "includePaths": [ "**/:x**" ] + }, { "containerId": "tools", "id": "floodgate",