diff --git a/src/lib/auth.ts b/src/lib/auth.ts index 5da98ab8e..73c563032 100644 --- a/src/lib/auth.ts +++ b/src/lib/auth.ts @@ -1,6 +1,7 @@ import axios from 'axios'; import { PromoCodeProps } from './types'; import { PASSWORD_REGEX } from '@/components/cloud-object-storage/integrated-checkout/components/InputsComponent'; +import { isCelloExpired } from '@/lib/cookies'; export const IFRAME_AUTH_ENABLED = false; export const REDIRECT_AUTH_ENABLED = true; @@ -265,13 +266,15 @@ export function checkout({ planId, promoCodeId, planType, mode, currency, gclid mode && params.set('mode', mode ? mode : 'subscription'); gclid && params.set('gclid', gclid); - const currentParams = new URLSearchParams(globalThis.location.search); - const celloProductId = currentParams.get('productId'); - const celloUcc = currentParams.get('ucc'); - const celloN = currentParams.get('celloN'); - if (celloProductId) params.set('productId', celloProductId); - if (celloUcc) params.set('ucc', celloUcc); - if (celloN) params.set('celloN', celloN); + if (!isCelloExpired()) { + const currentParams = new URLSearchParams(globalThis.location.search); + const celloProductId = currentParams.get('productId'); + const celloUcc = currentParams.get('ucc'); + const celloN = currentParams.get('celloN'); + if (celloProductId) params.set('productId', celloProductId); + if (celloUcc) params.set('ucc', celloUcc); + if (celloN) params.set('celloN', celloN); + } window.location.href = AUTH_FLOW_URL + `${pathname}?${params.toString()}`; } diff --git a/src/lib/cookies.ts b/src/lib/cookies.ts index f317dd49c..6893b09af 100644 --- a/src/lib/cookies.ts +++ b/src/lib/cookies.ts @@ -6,6 +6,7 @@ const url = require('url'); const queryString = require('querystring'); const GCLID_COOKIE_LIFESPAN_DAYS = 90; +const CELLO_EXPIRATION_DAYS = 30; const MILLISECONDS_PER_DAY = 24 * 60 * 60 * 1000; function parseUri(ctx: GetServerSidePropsContext) { @@ -88,10 +89,31 @@ export const getGclidFromURL = (): string | null => { return params.get('gclid'); }; +export const saveCelloFirstVisit = (): void => { + if (typeof window === 'undefined') return; + if (localStorage.getItem('cello_first_visit') === null) { + localStorage.setItem('cello_first_visit', new Date().toISOString()); + } +}; + +export const getCelloFirstVisitDate = (): string | null => { + if (typeof window === 'undefined') return null; + return localStorage.getItem('cello_first_visit'); +}; + +export const isCelloExpired = (): boolean => { + const storedDate = getCelloFirstVisitDate(); + if (!storedDate) return false; + return Date.now() - new Date(storedDate).getTime() > CELLO_EXPIRATION_DAYS * MILLISECONDS_PER_DAY; +}; + export default { parseUri, setCookie, getCookie, setReferralCookie, setPublicCookie, + saveCelloFirstVisit, + getCelloFirstVisitDate, + isCelloExpired, }; diff --git a/src/pages/specialoffer.tsx b/src/pages/specialoffer.tsx index 7db0a67d5..5b3a5addb 100644 --- a/src/pages/specialoffer.tsx +++ b/src/pages/specialoffer.tsx @@ -1,7 +1,9 @@ +import { useEffect, useState } from 'react'; import Layout from '@/components/layout/Layout'; import Script from 'next/script'; import { PromoCodeName } from '@/lib/types'; +import { saveCelloFirstVisit, isCelloExpired } from '@/lib/cookies'; import Footer from '@/components/layout/footers/Footer'; import usePricing from '@/hooks/usePricing'; @@ -30,6 +32,13 @@ function SpecialOffer({ footerLang, navbarLang, }: SpecialOfferProps): JSX.Element { + const [isCelloAttributionExpired, setIsCelloAttributionExpired] = useState(true); + + useEffect(() => { + saveCelloFirstVisit(); + setIsCelloAttributionExpired(isCelloExpired()); + }, []); + const metatags = metatagsDescriptions.filter((desc) => desc.id === 'special-offer'); const { @@ -84,7 +93,13 @@ function SpecialOffer({ return ( -