From 78ea7fb6274cb150241e5f3dd6ab6d90b07b1985 Mon Sep 17 00:00:00 2001 From: Marcus Hof <13001502+MarconLP@users.noreply.github.com> Date: Wed, 30 Oct 2024 11:37:04 +0100 Subject: [PATCH] feat(cdp): add option to run a hog function per person per event (#25874) --- .../filters/HogFunctionFilters.tsx | 4 ++ plugin-server/tests/cdp/examples.ts | 12 +++++- plugin-server/tests/cdp/hog-masker.test.ts | 37 +++++++++++++++---- 3 files changed, 43 insertions(+), 10 deletions(-) diff --git a/frontend/src/scenes/pipeline/hogfunctions/filters/HogFunctionFilters.tsx b/frontend/src/scenes/pipeline/hogfunctions/filters/HogFunctionFilters.tsx index 9dee4c767cc5e..ed98f0f3de14b 100644 --- a/frontend/src/scenes/pipeline/hogfunctions/filters/HogFunctionFilters.tsx +++ b/frontend/src/scenes/pipeline/hogfunctions/filters/HogFunctionFilters.tsx @@ -161,6 +161,10 @@ export function HogFunctionFilters(): JSX.Element { value: '{person.id}', label: 'Run once per person per interval', }, + { + value: '{concat(person.id, event.event)}', + label: 'Run once per person per event per interval', + }, ]} value={value?.hash ?? null} onChange={(val) => diff --git a/plugin-server/tests/cdp/examples.ts b/plugin-server/tests/cdp/examples.ts index fafafce472e3d..f92dd9ed4f97a 100644 --- a/plugin-server/tests/cdp/examples.ts +++ b/plugin-server/tests/cdp/examples.ts @@ -708,8 +708,16 @@ export const HOG_MASK_EXAMPLES: Record> person: { masking: { ttl: 30, - hash: '{person.uuid}', - bytecode: ['_h', 32, 'uuid', 32, 'person', 1, 2], + hash: '{person.id}', + bytecode: ['_h', 32, 'id', 32, 'person', 1, 2], + threshold: null, + }, + }, + personAndEvent: { + masking: { + ttl: 30, + hash: '{concat(person.id, event.event)}', + bytecode: ['_H', 1, 32, 'id', 32, 'person', 1, 2, 32, 'event', 32, 'event', 1, 2, 2, 'concat', 2], threshold: null, }, }, diff --git a/plugin-server/tests/cdp/hog-masker.test.ts b/plugin-server/tests/cdp/hog-masker.test.ts index df05043290e63..a3c7a955574db 100644 --- a/plugin-server/tests/cdp/hog-masker.test.ts +++ b/plugin-server/tests/cdp/hog-masker.test.ts @@ -118,6 +118,7 @@ describe('HogMasker', () => { describe('ttl', () => { let hogFunctionPerson: HogFunctionType let hogFunctionAll: HogFunctionType + let hogFunctionPersonAndEvent: HogFunctionType beforeEach(() => { hogFunctionPerson = createHogFunction({ @@ -127,6 +128,13 @@ describe('HogMasker', () => { }, }) + hogFunctionPersonAndEvent = createHogFunction({ + masking: { + ...HOG_MASK_EXAMPLES.personAndEvent.masking!, + ttl: 1, + }, + }) + hogFunctionAll = createHogFunction({ masking: { ...HOG_MASK_EXAMPLES.all.masking!, @@ -145,20 +153,33 @@ describe('HogMasker', () => { }) it('should mask with custom hog hash', async () => { - const globalsPerson1 = createHogExecutionGlobals({ person: { uuid: '1' } as any }) - const globalsPerson2 = createHogExecutionGlobals({ person: { uuid: '2' } as any }) + const globals1 = createHogExecutionGlobals({ + person: { id: '1' } as any, + event: { event: '$pageview' } as any, + }) + const globals2 = createHogExecutionGlobals({ + person: { id: '2' } as any, + event: { event: '$autocapture' } as any, + }) + const globals3 = createHogExecutionGlobals({ + person: { id: '2' } as any, + event: { event: '$pageview' } as any, + }) const invocations = [ - createInvocation(hogFunctionPerson, globalsPerson1), - createInvocation(hogFunctionAll, globalsPerson1), - createInvocation(hogFunctionPerson, globalsPerson2), - createInvocation(hogFunctionAll, globalsPerson2), + createInvocation(hogFunctionPerson, globals1), + createInvocation(hogFunctionAll, globals1), + createInvocation(hogFunctionPersonAndEvent, globals1), + createInvocation(hogFunctionPerson, globals2), + createInvocation(hogFunctionAll, globals2), + createInvocation(hogFunctionPersonAndEvent, globals2), + createInvocation(hogFunctionPersonAndEvent, globals3), ] const res = await masker.filterByMasking(invocations) expect(res.masked.length).toEqual(1) - expect(res.notMasked.length).toEqual(3) + expect(res.notMasked.length).toEqual(6) const res2 = await masker.filterByMasking(invocations) - expect(res2.masked.length).toEqual(4) + expect(res2.masked.length).toEqual(7) expect(res2.notMasked.length).toEqual(0) })