From 1184d8143f18ab7cb6d5245f43ee589299215e49 Mon Sep 17 00:00:00 2001 From: Kiko Ruiz Date: Mon, 21 Oct 2024 16:19:26 +0200 Subject: [PATCH] feat(packages/sui-segment-wrapper): set ga user id on identify --- .../src/repositories/googleRepository.js | 10 +++++++ .../sui-segment-wrapper/src/segmentWrapper.js | 4 ++- .../test/segmentWrapperSpec.js | 30 ++++++++++++++++++- packages/sui-segment-wrapper/test/stubs.js | 14 ++++++--- 4 files changed, 52 insertions(+), 6 deletions(-) diff --git a/packages/sui-segment-wrapper/src/repositories/googleRepository.js b/packages/sui-segment-wrapper/src/repositories/googleRepository.js index 9c135b97d..9871e144a 100644 --- a/packages/sui-segment-wrapper/src/repositories/googleRepository.js +++ b/packages/sui-segment-wrapper/src/repositories/googleRepository.js @@ -52,3 +52,13 @@ const getGoogleField = async field => { export const getGoogleClientID = () => getGoogleField(FIELDS.clientId) export const getGoogleSessionID = () => getGoogleField(FIELDS.sessionId) + +export const sendGoogleUserId = userId => { + const googleAnalyticsMeasurementId = getConfig('googleAnalyticsMeasurementId') + + if (!googleAnalyticsMeasurementId || !userId) return + + window.gtag?.('set', googleAnalyticsMeasurementId, { + user_id: userId + }) +} diff --git a/packages/sui-segment-wrapper/src/segmentWrapper.js b/packages/sui-segment-wrapper/src/segmentWrapper.js index 517d2b869..4f3eec603 100644 --- a/packages/sui-segment-wrapper/src/segmentWrapper.js +++ b/packages/sui-segment-wrapper/src/segmentWrapper.js @@ -1,7 +1,7 @@ // @ts-check import {getAdobeMCVisitorID} from './repositories/adobeRepository.js' -import {getGoogleClientID, getGoogleSessionID} from './repositories/googleRepository.js' +import {getGoogleClientID, getGoogleSessionID, sendGoogleUserId} from './repositories/googleRepository.js' import {getConfig} from './config.js' import {checkAnalyticsGdprIsAccepted, getGdprPrivacyValue} from './tcf.js' import {getXandrId} from './repositories/xandrRepository.js' @@ -208,6 +208,8 @@ const track = (event, properties, context = {}, callback) => const identify = async (userId, traits, options, callback) => { const gdprPrivacyValue = await getGdprPrivacyValue() + sendGoogleUserId(userId) + return window.analytics.identify( userId, checkAnalyticsGdprIsAccepted(gdprPrivacyValue) ? traits : {}, diff --git a/packages/sui-segment-wrapper/test/segmentWrapperSpec.js b/packages/sui-segment-wrapper/test/segmentWrapperSpec.js index 6d91a678b..a668abd9c 100644 --- a/packages/sui-segment-wrapper/test/segmentWrapperSpec.js +++ b/packages/sui-segment-wrapper/test/segmentWrapperSpec.js @@ -2,7 +2,7 @@ import {expect} from 'chai' import sinon from 'sinon' import {getAdobeVisitorData} from '../src/repositories/adobeRepository.js' -import {setConfig} from '../src/config.js' +import {setConfig, getConfig} from '../src/config.js' import suiAnalytics from '../src/index.js' import {defaultContextProperties} from '../src/middlewares/source/defaultContextProperties.js' import {pageReferrer} from '../src/middlewares/source/pageReferrer.js' @@ -220,6 +220,7 @@ describe('Segment Wrapper', function () { it('should send Google Analytics integration with true if user declined consents', async () => { // Add the needed config to enable Google Analytics setConfig('googleAnalyticsMeasurementId', 123) + await simulateUserDeclinedConsents() await suiAnalytics.track( @@ -310,6 +311,7 @@ describe('Segment Wrapper', function () { describe('when the identify event is called', () => { const DEFAULT_SEGMENT_CALLBACK_TIMEOUT = 350 + it('should call sdk identify of users that accepts consents', async function () { await simulateUserAcceptConsents() @@ -319,6 +321,7 @@ describe('Segment Wrapper', function () { await waitUntil(() => spy.callCount, { timeout: DEFAULT_SEGMENT_CALLBACK_TIMEOUT }) + expect(spy.callCount).to.equal(1) }) @@ -331,8 +334,33 @@ describe('Segment Wrapper', function () { await waitUntil(() => spy.callCount, { timeout: DEFAULT_SEGMENT_CALLBACK_TIMEOUT }).catch(() => null) + expect(spy.callCount).to.equal(1) }) + + describe('and GA Measurment ID is set', () => { + beforeEach(() => { + setConfig('googleAnalyticsMeasurementId', 123) + }) + + it('should set the user id into `gtag` properly', async function () { + await simulateUserAcceptConsents() + await suiAnalytics.identify('myTestUserId') + + const googleAnalyticsMeasurementId = getConfig('googleAnalyticsMeasurementId') + + const getGaUserId = async () => + new Promise(resolve => { + window.gtag('get', googleAnalyticsMeasurementId, 'user_id', userId => { + resolve(userId) + }) + }) + + const gaUserId = await getGaUserId() + + expect(gaUserId).to.equal('myTestUserId') + }) + }) }) describe('when TCF is present on the page', () => { diff --git a/packages/sui-segment-wrapper/test/stubs.js b/packages/sui-segment-wrapper/test/stubs.js index 13b1738d3..7a866e05d 100644 --- a/packages/sui-segment-wrapper/test/stubs.js +++ b/packages/sui-segment-wrapper/test/stubs.js @@ -43,14 +43,20 @@ export const stubFetch = ({responses = [{urlRe: /^http/, fetchResponse: {}}]} = } export const stubGoogleAnalytics = () => { - const mockClientId = 'fakeClientId' - const mockSessionId = 'fakeSessionId' + const savedFields = { + client_id: 'fakeClientId', + session_id: 'fakeSessionId' + } window.gtag = (key, id, fieldName, done) => { if (key === 'get') { - const value = fieldName === 'client_id' ? mockClientId : mockSessionId + return done(savedFields?.[fieldName]) + } - return done(value) + if (key === 'set' && typeof fieldName === 'object') { + Object.keys(fieldName).forEach(field => { + savedFields[field] = fieldName[field] + }) } } }