From 9ef6c136b053ccc81a20384e062b1abefe6b9f86 Mon Sep 17 00:00:00 2001 From: Eoghan Murray Date: Mon, 9 Aug 2021 12:58:26 +0100 Subject: [PATCH] Record the `href` target on anchor (and area) elements as a first step in distinguishing navigational clicks from other clicks. Part of #503 --- packages/rrweb/src/record/observer.ts | 24 +++++++++++++++++-- packages/rrweb/src/types.ts | 8 +++++-- .../__snapshots__/integration.test.ts.snap | 1 + packages/rrweb/test/html/link.html | 13 ++++++++++ 4 files changed, 42 insertions(+), 4 deletions(-) create mode 100644 packages/rrweb/test/html/link.html diff --git a/packages/rrweb/src/record/observer.ts b/packages/rrweb/src/record/observer.ts index bd4ecca4f5..5a7d0ebc91 100644 --- a/packages/rrweb/src/record/observer.ts +++ b/packages/rrweb/src/record/observer.ts @@ -23,6 +23,8 @@ import { mousemoveCallBack, mousePosition, mouseInteractionCallBack, + mouseInteractionParam, + clickParam, MouseInteractions, listenerHandler, scrollCallback, @@ -286,12 +288,30 @@ function initMouseInteractionObserver( } const id = mirror.getId(target as INode); const { clientX, clientY } = e; - cb({ + let emissionEvent: mouseInteractionParam | clickParam = { type: MouseInteractions[eventKey], id, x: clientX, y: clientY, - }); + } + const htarget = (target as Element); + if (MouseInteractions[eventKey] === MouseInteractions.Click) { + let href: string | null = null; + if (htarget.tagName.toLowerCase() === 'a' && + (htarget as HTMLAnchorElement).href) { + href = (htarget as HTMLAnchorElement).href; + } else if (htarget.tagName.toLowerCase() === 'area' && + (htarget as HTMLAreaElement).href) { + href = (htarget as HTMLAreaElement).href; + } + if (href !== null) { + emissionEvent = { + ...emissionEvent, + href: href, + }; + } + } + cb(emissionEvent); }; }; Object.keys(MouseInteractions) diff --git a/packages/rrweb/src/types.ts b/packages/rrweb/src/types.ts index 463f9293a4..d24ef280a7 100644 --- a/packages/rrweb/src/types.ts +++ b/packages/rrweb/src/types.ts @@ -365,14 +365,18 @@ export enum MouseInteractions { TouchEnd, } -type mouseInteractionParam = { +export type mouseInteractionParam = { type: MouseInteractions; id: number; x: number; y: number; }; -export type mouseInteractionCallBack = (d: mouseInteractionParam) => void; +export type clickParam = mouseInteractionParam & { + href?: string; +}; + +export type mouseInteractionCallBack = (d: mouseInteractionParam | clickParam) => void; export type scrollPosition = { id: number; diff --git a/packages/rrweb/test/__snapshots__/integration.test.ts.snap b/packages/rrweb/test/__snapshots__/integration.test.ts.snap index 807494e163..437f8b8480 100644 --- a/packages/rrweb/test/__snapshots__/integration.test.ts.snap +++ b/packages/rrweb/test/__snapshots__/integration.test.ts.snap @@ -2992,6 +2992,7 @@ exports[`link 1`] = ` \\"source\\": 2, \\"type\\": 2, \\"id\\": 21, + \\"href\\": \\"about:blank#clicked\\" } } ]" diff --git a/packages/rrweb/test/html/link.html b/packages/rrweb/test/html/link.html new file mode 100644 index 0000000000..852c5be376 --- /dev/null +++ b/packages/rrweb/test/html/link.html @@ -0,0 +1,13 @@ + + + + + + + Link click + + + not link + link + +