0
Fork 0
mirror of https://github.com/TryGhost/Ghost.git synced 2025-03-18 02:21:47 -05:00

Added urlHistory on sign in and checkout (#256)

refs https://github.com/TryGhost/Team/issues/1797
refs https://github.com/TryGhost/Team/issues/1798

Context: we've added a new attribution script here: https://github.com/TryGhost/Ghost/pull/15242
Backend implementation: https://github.com/TryGhost/Ghost/pull/15243

- The member attribution script stores the history in the ghost-history localStorage value
- We need to pass this to the backend when signing in or checking out with Stripe
- Removed `getAnalyticsMetadata`, as this is no longer used in the backend (removed flag and implementation)

To merge after https://github.com/TryGhost/Ghost/pull/15243 (backend implementation)
This commit is contained in:
Simon Backx 2022-08-18 17:39:24 +02:00 committed by GitHub
parent 8cb4387d2a
commit 54480438a6
3 changed files with 71 additions and 25 deletions

View file

@ -1,16 +1,4 @@
import {transformApiSiteData, transformApiTiersData} from './helpers';
function getAnalyticsMetadata() {
const analyticsTag = document.querySelector('meta[name=ghost-analytics-id]');
const analyticsId = analyticsTag?.content;
if (analyticsTag) {
return {
entry_id: analyticsId,
source_url: window.location.href
};
}
return null;
}
import {transformApiSiteData, transformApiTiersData, getUrlHistory} from './helpers';
function setupGhostApi({siteUrl = window.location.origin, apiUrl, apiKey}) {
const apiPath = 'members/api';
@ -188,10 +176,6 @@ function setupGhostApi({siteUrl = window.location.origin, apiUrl, apiKey}) {
body.enable_comment_notifications = enableCommentNotifications;
}
const analyticsData = getAnalyticsMetadata();
if (analyticsData) {
body.metadata = analyticsData;
}
return makeRequest({
url,
method: 'PUT',
@ -219,10 +203,11 @@ function setupGhostApi({siteUrl = window.location.origin, apiUrl, apiKey}) {
labels,
requestSrc: 'portal'
};
const analyticsData = getAnalyticsMetadata();
if (analyticsData) {
body.metadata = analyticsData;
const urlHistory = getUrlHistory();
if (urlHistory) {
body.urlHistory = urlHistory;
}
return makeRequest({
url,
method: 'POST',
@ -334,6 +319,7 @@ function setupGhostApi({siteUrl = window.location.origin, apiUrl, apiKey}) {
newsletters: JSON.stringify(newsletters),
requestSrc: 'portal',
fp_tid: (window.FPROM || window.$FPROM)?.data?.tid,
urlHistory: getUrlHistory(),
...metadata
};
@ -439,10 +425,6 @@ function setupGhostApi({siteUrl = window.location.origin, apiUrl, apiKey}) {
identity: identity,
priceId: planId
};
const analyticsData = getAnalyticsMetadata();
if (body) {
body.metadata = analyticsData;
}
if (tierId && cadence) {
delete body.priceId;

View file

@ -791,3 +791,28 @@ export const transformApiTiersData = ({tiers}) => {
};
});
};
/**
* Returns the member attribution URL history, which is stored in localStorage, if there is any.
* @returns {Object[]|undefined}
*/
export function getUrlHistory() {
const STORAGE_KEY = 'ghost-history';
try {
const historyString = localStorage.getItem(STORAGE_KEY);
if (historyString) {
const parsed = JSON.parse(historyString);
if (Array.isArray(parsed)) {
return parsed;
}
}
} catch (error) {
// Failed to access localStorage or something related to that.
// Log a warning, as this shouldn't happen on a modern browser.
/* eslint-disable no-console */
console.warn(`[Portal] Failed to load member URL history:`, error);
}
}

View file

@ -1,4 +1,4 @@
import {getCurrencySymbol, getFreeProduct, getMemberName, getMemberSubscription, getPriceFromSubscription, getPriceIdFromPageQuery, getSupportAddress, hasMultipleProducts, isActiveOffer, isInviteOnlySite, isPaidMember, isSameCurrency, transformApiTiersData} from './helpers';
import {getCurrencySymbol, getFreeProduct, getMemberName, getMemberSubscription, getPriceFromSubscription, getPriceIdFromPageQuery, getSupportAddress, getUrlHistory, hasMultipleProducts, isActiveOffer, isInviteOnlySite, isPaidMember, isSameCurrency, transformApiTiersData} from './helpers';
import * as Fixtures from './fixtures-generator';
import {site as FixturesSite, member as FixtureMember, offer as FixtureOffer, transformTierFixture as TransformFixtureTiers} from '../utils/test-fixtures';
import {isComplimentaryMember} from '../utils/helpers';
@ -255,4 +255,43 @@ describe('Helpers - ', () => {
expect(transformedTiers[1].benefits).toHaveLength(3);
});
});
describe('getUrlHistory', () => {
beforeEach(() => {
jest.spyOn(console, 'warn').mockImplementation(() => {
// don't log for these tests
});
});
afterEach(() => {
jest.restoreAllMocks();
});
test('returns valid history ', () => {
jest.spyOn(Storage.prototype, 'getItem').mockReturnValue(JSON.stringify([
{
path: '/',
time: 0
}
]));
const urlHistory = getUrlHistory();
expect(localStorage.getItem).toHaveBeenCalled();
expect(urlHistory).toHaveLength(1);
});
test('ignores invalid history ', () => {
jest.spyOn(Storage.prototype, 'getItem').mockReturnValue('invalid');
const urlHistory = getUrlHistory();
expect(localStorage.getItem).toHaveBeenCalled();
expect(urlHistory).toBeUndefined();
});
test('doesn\'t throw if localStorage is disabled', () => {
jest.spyOn(Storage.prototype, 'getItem').mockImplementation(() => {
throw new Error('LocalStorage disabled');
});
const urlHistory = getUrlHistory();
expect(localStorage.getItem).toHaveBeenCalled();
expect(urlHistory).toBeUndefined();
});
});
});