Skip to content

Commit

Permalink
cleanup decision id enricher
Browse files Browse the repository at this point in the history
  • Loading branch information
mschuwalow committed Sep 19, 2023
1 parent 1abf1b7 commit 1de9941
Show file tree
Hide file tree
Showing 5 changed files with 81 additions and 117 deletions.
23 changes: 0 additions & 23 deletions src/enrichers/cache.ts

This file was deleted.

65 changes: 63 additions & 2 deletions src/enrichers/decisions.ts
Original file line number Diff line number Diff line change
@@ -1,13 +1,74 @@
import { Enricher, EventBus } from '../types'
import { getQueryParameter, ParsedParam } from '../utils/url'
import { trim, isUUID, expiresInDays } from 'live-connect-common'
import { WrappedStorageHandler } from '../handlers/storage-handler'
import { resolve } from '../manager/decisions'

type Input = { pageUrl?: string, domain: string }
type Output = { decisionIds: string[] }

const DEFAULT_DECISION_ID_COOKIE_EXPIRES = expiresInDays(30)
const DECISION_ID_QUERY_PARAM_NAME = 'li_did'
const DECISION_ID_COOKIE_NAMESPACE = 'lidids.'

const _onlyUnique = (value: string, index: number, self: string[]) => self.indexOf(value) === index
const _nonEmpty = (value: string) => value && trim(value).length > 0

export function enrichDecisionIds(
storageHandler: WrappedStorageHandler,
eventBus: EventBus
): Enricher<Input, Output> {
return state => ({ ...state, ...resolve(state, storageHandler, eventBus) })
return state => {
function _addDecisionId(key: string, cookieDomain?: string) {
if (key) {
storageHandler.setCookie(
`${DECISION_ID_COOKIE_NAMESPACE}${key}`,
key,
DEFAULT_DECISION_ID_COOKIE_EXPIRES,
'Lax',
cookieDomain)
}
}

function _orElseEmpty<A>(errorDescription: string, f: () => A[]): A[] {
try {
return f()
} catch (e) {
eventBus.emitErrorWithMessage('DecisionsResolve', errorDescription, e)
return []
}
}

const freshDecisions = _orElseEmpty(
'Error while extracting new decision ids',
() => {
const extractedFreshDecisions = ([] as ParsedParam[]).concat((state.pageUrl && getQueryParameter(state.pageUrl, DECISION_ID_QUERY_PARAM_NAME)) || [])
return extractedFreshDecisions
.map(trim)
.filter(_nonEmpty)
.filter(isUUID)
.filter(_onlyUnique)
}
)

const storedDecisions = _orElseEmpty(
'Error while retrieving stored decision ids',
() => {
const extractedStoredDecisions = storageHandler.findSimilarCookies(DECISION_ID_COOKIE_NAMESPACE)
return extractedStoredDecisions
.map(trim)
.filter(_nonEmpty)
.filter(isUUID)
}
)

freshDecisions.forEach(decision => {
try {
_addDecisionId(decision, state.domain)
} catch (e) {
eventBus.emitErrorWithMessage('DecisionsResolve', 'Error while storing new decision id', e)
}
})

return { ...state, decisionIds: freshDecisions.concat(storedDecisions).filter(_onlyUnique) }
}
}
66 changes: 0 additions & 66 deletions src/manager/decisions.ts

This file was deleted.

14 changes: 1 addition & 13 deletions src/pixel/fiddler.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { Enricher, State } from '../types'
import { State } from '../types'
import { extractEmail } from '../utils/email'
import { decodeValue } from '../utils/url'
import { extractHashValue, hashEmail, isHash } from '../utils/hash'
Expand Down Expand Up @@ -75,15 +75,3 @@ export function mergeObjects<A extends object, B extends object>(obj1: A, obj2:
})
return res
}

export class EnrichmentContext<A extends object> {
data: A

constructor (state: A) {
this.data = state
}

via<B extends object>(enricher: Enricher<A, B>): EnrichmentContext<A & B> {
return new EnrichmentContext({ ...this.data, ...enricher(this.data) })
}
}
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import { expect, use } from 'chai'
import * as decisions from '../../../src/manager/decisions'
import { enrichDecisionIds } from '../../../src/enrichers/decisions'
import { DefaultStorageHandler } from 'live-connect-handlers'
// @ts-expect-error
import uuid from 'tiny-uuid4'
Expand All @@ -18,6 +18,8 @@ describe('DecisionsManager for stored decisions', () => {
let externalStorage: DefaultStorageHandler
let storage: WrappedStorageHandler

const domain = 'example.com'

beforeEach(() => {
eventBus = LocalEventBus()
externalStorage = new DefaultStorageHandler(eventBus)
Expand All @@ -29,34 +31,34 @@ describe('DecisionsManager for stored decisions', () => {
})

it('should return an empty string if nothing is in the cookie jar', () => {
const resolutionResult = decisions.resolve({}, storage, eventBus)
const resolutionResult = enrichDecisionIds(storage, eventBus)({ domain })
expect(resolutionResult.decisionIds).to.eql([])
})

it('should return an empty string if the cookie jar has invalid uuids', () => {
storage.setCookie('lidids.', '2134')
const resolutionResult = decisions.resolve({}, storage, eventBus)
const resolutionResult = enrichDecisionIds(storage, eventBus)({ domain })
expect(resolutionResult.decisionIds).to.eql([])
})

it('should return the stored decision', () => {
const decisionId = uuid()
storage.setCookie('lidids.123', decisionId)
const resolutionResult = decisions.resolve({}, storage, eventBus)
const resolutionResult = enrichDecisionIds(storage, eventBus)({ domain })
expect(resolutionResult.decisionIds).to.eql([decisionId])
})

it('should not return empty values', () => {
storage.setCookie('lidids.', '')
const resolutionResult = decisions.resolve({}, storage, eventBus)
const resolutionResult = enrichDecisionIds(storage, eventBus)({ domain })
expect(resolutionResult.decisionIds.length).to.eql(0)
})

it('should return unique decision ids', () => {
const decisionId = uuid()
storage.setCookie('lidids.123', decisionId, undefined, undefined, 'something.example.com')
storage.setCookie('lidids.123', decisionId, undefined, undefined, 'www.something.example.com')
const resolutionResult = decisions.resolve({}, storage, eventBus)
const resolutionResult = enrichDecisionIds(storage, eventBus)({ domain })
expect(resolutionResult.decisionIds).to.eql([decisionId])
})
})
Expand All @@ -67,6 +69,8 @@ describe('DecisionsManager for new decisions', () => {
let externalStorage: DefaultStorageHandler
let storage: WrappedStorageHandler

const domain = 'example.com'

beforeEach(() => {
sandbox = sinon.createSandbox()
eventBus = LocalEventBus()
Expand All @@ -80,29 +84,29 @@ describe('DecisionsManager for new decisions', () => {

it('should return the new decision id, and store it', () => {
const decisionId = uuid()
const resolutionResult = decisions.resolve({ pageUrl: `http://subdomain.tests.example.com/cake?li_did=${decisionId}` }, storage, eventBus)
const resolutionResult = enrichDecisionIds(storage, eventBus)({ domain, pageUrl: `http://subdomain.tests.example.com/cake?li_did=${decisionId}` })
expect(resolutionResult.decisionIds).to.eql([decisionId])
expect(storage.getCookie(`lidids.${decisionId}`)).to.eq(decisionId)
})

it('should return the new decision id, and store it', () => {
const decisionId = uuid()
const resolutionResult = decisions.resolve({ pageUrl: `http://subdomain.tests.example.com/cake?li_did=${decisionId}` }, storage, eventBus)
const resolutionResult = enrichDecisionIds(storage, eventBus)({ domain, pageUrl: `http://subdomain.tests.example.com/cake?li_did=${decisionId}` })
expect(resolutionResult.decisionIds).to.eql([decisionId])
expect(storage.getCookie(`lidids.${decisionId}`)).to.eq(decisionId)
})

it('should not return the new decision id if its not a uuid', () => {
const decisionId = `${uuid()}sometghing`
const resolutionResult = decisions.resolve({ pageUrl: `http://subdomain.tests.example.com/cake?li_did=${decisionId}` }, storage, eventBus)
const resolutionResult = enrichDecisionIds(storage, eventBus)({ domain, pageUrl: `http://subdomain.tests.example.com/cake?li_did=${decisionId}` })
expect(resolutionResult.decisionIds).to.eql([])
})

it('should combine the new cookie and the stored one', () => {
const decisionIdOne = uuid()
const decisionIdTwo = uuid()
storage.setCookie('lidids.123', decisionIdOne)
const resolutionResult = decisions.resolve({ pageUrl: `http://subdomain.tests.example.com/cake?li_did= ${decisionIdTwo}` }, storage, eventBus)
const resolutionResult = enrichDecisionIds(storage, eventBus)({ domain, pageUrl: `http://subdomain.tests.example.com/cake?li_did= ${decisionIdTwo}` })
expect(resolutionResult.decisionIds).to.eql([decisionIdTwo, decisionIdOne])
expect(storage.getCookie(`lidids.${decisionIdTwo}`)).to.eq(decisionIdTwo)
})
Expand All @@ -112,7 +116,7 @@ describe('DecisionsManager for new decisions', () => {
const decisionIdTwo = uuid()
const decisionIdThree = uuid()
storage.setCookie('lidids.123', decisionIdOne)
const resolutionResult = decisions.resolve({ pageUrl: `http://subdomain.tests.example.com/cake?li_did=${decisionIdTwo}&li_did=${decisionIdThree}` }, storage, eventBus)
const resolutionResult = enrichDecisionIds(storage, eventBus)({ domain, pageUrl: `http://subdomain.tests.example.com/cake?li_did=${decisionIdTwo}&li_did=${decisionIdThree}` })
expect(resolutionResult.decisionIds).to.eql([decisionIdTwo, decisionIdThree, decisionIdOne])
expect(storage.getCookie(`lidids.${decisionIdTwo}`)).to.eq(decisionIdTwo)
expect(storage.getCookie(`lidids.${decisionIdThree}`)).to.eq(decisionIdThree)
Expand All @@ -133,7 +137,7 @@ describe('DecisionsManager for new decisions', () => {
stub => stub.restore(),
() => {
expect(errorEmitted).to.eq(false)
const resolutionResult = decisions.resolve({ pageUrl: `http://subdomain.tests.example.com/cake?li_did=${decisionIdTwo}&li_did=${decisionIdThree}` }, storage, eventBus)
const resolutionResult = enrichDecisionIds(storage, eventBus)({ domain, pageUrl: `http://subdomain.tests.example.com/cake?li_did=${decisionIdTwo}&li_did=${decisionIdThree}` })
expect(resolutionResult.decisionIds).to.eql([decisionIdTwo, decisionIdThree])
expect(storage.getCookie(`lidids.${decisionIdTwo}`)).to.eq(decisionIdTwo)
expect(storage.getCookie(`lidids.${decisionIdThree}`)).to.eq(decisionIdThree)
Expand All @@ -156,7 +160,7 @@ describe('DecisionsManager for new decisions', () => {
stub => stub.restore(),
() => {
expect(errorEmitted).to.eq(false)
const resolutionResult = decisions.resolve({ pageUrl: `http://subdomain.tests.example.com/cake?li_did=${decisionIdTwo}&li_did=${decisionIdThree}` }, storage, eventBus)
const resolutionResult = enrichDecisionIds(storage, eventBus)({ domain, pageUrl: `http://subdomain.tests.example.com/cake?li_did=${decisionIdTwo}&li_did=${decisionIdThree}` })
expect(resolutionResult.decisionIds).to.eql([decisionIdTwo, decisionIdThree, decisionIdOne])
expect(errorEmitted).to.eq(true)
})
Expand Down

0 comments on commit 1de9941

Please sign in to comment.