|
11 | 11 | */
|
12 | 12 |
|
13 | 13 | /* eslint-env browser */
|
14 |
| - |
15 |
| -/** |
16 |
| - * log RUM if part of the sample. |
17 |
| - * @param {string} checkpoint identifies the checkpoint in funnel |
18 |
| - * @param {Object} data additional data for RUM sample |
19 |
| - * @param {string} data.source DOM node that is the source of a checkpoint event, |
20 |
| - * identified by #id or .classname |
21 |
| - * @param {string} data.target subject of the checkpoint event, |
22 |
| - * for instance the href of a link, or a search term |
23 |
| - */ |
24 |
| -function sampleRUM(checkpoint, data = {}) { |
| 14 | +function sampleRUM(checkpoint, data) { |
| 15 | + // eslint-disable-next-line max-len |
| 16 | + const timeShift = () => (window.performance ? window.performance.now() : Date.now() - window.hlx.rum.firstReadTime); |
25 | 17 | const SESSION_STORAGE_KEY = 'aem-rum';
|
26 |
| - sampleRUM.baseURL = sampleRUM.baseURL |
27 |
| - || new URL(window.RUM_BASE == null ? 'https://rum.hlx.page' : window.RUM_BASE, window.location); |
28 |
| - sampleRUM.defer = sampleRUM.defer || []; |
29 |
| - const defer = (fnname) => { |
30 |
| - sampleRUM[fnname] = sampleRUM[fnname] || ((...args) => sampleRUM.defer.push({ fnname, args })); |
31 |
| - }; |
32 |
| - sampleRUM.drain = sampleRUM.drain |
33 |
| - || ((dfnname, fn) => { |
34 |
| - sampleRUM[dfnname] = fn; |
35 |
| - sampleRUM.defer |
36 |
| - .filter(({ fnname }) => dfnname === fnname) |
37 |
| - .forEach(({ fnname, args }) => sampleRUM[fnname](...args)); |
38 |
| - }); |
39 |
| - sampleRUM.always = sampleRUM.always || []; |
40 |
| - sampleRUM.always.on = (chkpnt, fn) => { |
41 |
| - sampleRUM.always[chkpnt] = fn; |
42 |
| - }; |
43 |
| - sampleRUM.on = (chkpnt, fn) => { |
44 |
| - sampleRUM.cases[chkpnt] = fn; |
45 |
| - }; |
46 |
| - defer('observe'); |
47 |
| - defer('cwv'); |
48 | 18 | try {
|
49 | 19 | window.hlx = window.hlx || {};
|
50 | 20 | if (!window.hlx.rum) {
|
51 |
| - const usp = new URLSearchParams(window.location.search); |
52 |
| - const weight = usp.get('rum') === 'on' ? 1 : 100; // with parameter, weight is 1. Defaults to 100. |
| 21 | + // eslint-disable-next-line max-len |
| 22 | + const rumStorage = sessionStorage.getItem(SESSION_STORAGE_KEY) |
| 23 | + ? JSON.parse(sessionStorage.getItem(SESSION_STORAGE_KEY)) |
| 24 | + : {}; |
| 25 | + rumStorage.pages = (rumStorage.pages ?? 0) + (Math.floor(Math.random() * 20) - 10) + 1; |
| 26 | + sessionStorage.setItem(SESSION_STORAGE_KEY, JSON.stringify(rumStorage)); |
| 27 | + sampleRUM.baseURL = sampleRUM.baseURL |
| 28 | + || new URL( |
| 29 | + window.RUM_BASE == null ? 'https://rum.hlx.page' : window.RUM_BASE, |
| 30 | + window.location, |
| 31 | + ); |
| 32 | + const weight = new URLSearchParams(window.location.search).get('rum') === 'on' ? 1 : 100; |
53 | 33 | const id = Array.from({ length: 75 }, (_, i) => String.fromCharCode(48 + i))
|
54 | 34 | .filter((a) => /\d|[A-Z]/i.test(a))
|
55 | 35 | .filter(() => Math.random() * 75 > 70)
|
56 | 36 | .join('');
|
57 |
| - const random = Math.random(); |
58 |
| - const isSelected = random * weight < 1; |
59 |
| - const firstReadTime = window.performance ? window.performance.timeOrigin : Date.now(); |
60 |
| - const urlSanitizers = { |
61 |
| - full: () => window.location.href, |
62 |
| - origin: () => window.location.origin, |
63 |
| - path: () => window.location.href.replace(/\?.*$/, ''), |
64 |
| - }; |
65 |
| - // eslint-disable-next-line max-len |
66 |
| - const rumSessionStorage = sessionStorage.getItem(SESSION_STORAGE_KEY) |
67 |
| - ? JSON.parse(sessionStorage.getItem(SESSION_STORAGE_KEY)) |
68 |
| - : {}; |
69 |
| - // eslint-disable-next-line max-len |
70 |
| - rumSessionStorage.pages = (rumSessionStorage.pages ? rumSessionStorage.pages : 0) |
71 |
| - + 1 |
72 |
| - /* noise */ + (Math.floor(Math.random() * 20) - 10); |
73 |
| - sessionStorage.setItem(SESSION_STORAGE_KEY, JSON.stringify(rumSessionStorage)); |
| 37 | + const isSelected = Math.random() * weight < 1; |
74 | 38 | // eslint-disable-next-line object-curly-newline, max-len
|
75 | 39 | window.hlx.rum = {
|
76 | 40 | weight,
|
77 | 41 | id,
|
78 |
| - random, |
79 | 42 | isSelected,
|
80 |
| - firstReadTime, |
| 43 | + firstReadTime: window.performance ? window.performance.timeOrigin : Date.now(), |
81 | 44 | sampleRUM,
|
82 |
| - sanitizeURL: urlSanitizers[window.hlx.RUM_MASK_URL || 'path'], |
83 |
| - rumSessionStorage, |
| 45 | + queue: [], |
| 46 | + collector: (...args) => window.hlx.rum.queue.push(args), |
84 | 47 | };
|
85 |
| - } |
86 |
| - |
87 |
| - const { weight, id, firstReadTime } = window.hlx.rum; |
88 |
| - if (window.hlx && window.hlx.rum && window.hlx.rum.isSelected) { |
89 |
| - const knownProperties = [ |
90 |
| - 'weight', |
91 |
| - 'id', |
92 |
| - 'referer', |
93 |
| - 'checkpoint', |
94 |
| - 't', |
95 |
| - 'source', |
96 |
| - 'target', |
97 |
| - 'cwv', |
98 |
| - 'CLS', |
99 |
| - 'FID', |
100 |
| - 'LCP', |
101 |
| - 'INP', |
102 |
| - 'TTFB', |
103 |
| - ]; |
104 |
| - const sendPing = (pdata = data) => { |
105 |
| - // eslint-disable-next-line max-len |
106 |
| - const t = Math.round( |
107 |
| - window.performance ? window.performance.now() : Date.now() - firstReadTime, |
108 |
| - ); |
109 |
| - // eslint-disable-next-line object-curly-newline, max-len, no-use-before-define |
110 |
| - const body = JSON.stringify( |
111 |
| - { |
112 |
| - weight, id, referer: window.hlx.rum.sanitizeURL(), checkpoint, t, ...data, |
113 |
| - }, |
114 |
| - knownProperties, |
115 |
| - ); |
| 48 | + if (isSelected) { |
| 49 | + // eslint-disable-next-line object-curly-newline, max-len |
| 50 | + const body = JSON.stringify({ |
| 51 | + weight, |
| 52 | + id, |
| 53 | + referer: window.location.href, |
| 54 | + checkpoint: 'top', |
| 55 | + t: timeShift(), |
| 56 | + target: document.visibilityState, |
| 57 | + }); |
116 | 58 | const url = new URL(`.rum/${weight}`, sampleRUM.baseURL).href;
|
117 | 59 | navigator.sendBeacon(url, body);
|
118 |
| - // eslint-disable-next-line no-console |
119 |
| - console.debug(`ping:${checkpoint}`, pdata); |
120 |
| - }; |
121 |
| - sampleRUM.cases = sampleRUM.cases || { |
122 |
| - load: () => sampleRUM('pagesviewed', { source: window.hlx.rum.rumSessionStorage.pages }) || true, |
123 |
| - cwv: () => sampleRUM.cwv(data) || true, |
124 |
| - lazy: () => { |
125 |
| - // use classic script to avoid CORS issues |
126 |
| - const script = document.createElement('script'); |
127 |
| - script.src = new URL( |
128 |
| - '.rum/@adobe/helix-rum-enhancer@^1/src/index.js', |
129 |
| - sampleRUM.baseURL, |
130 |
| - ).href; |
131 |
| - document.head.appendChild(script); |
132 |
| - return true; |
133 |
| - }, |
134 |
| - }; |
135 |
| - sendPing(data); |
136 |
| - if (sampleRUM.cases[checkpoint]) { |
137 |
| - sampleRUM.cases[checkpoint](); |
| 60 | + // eslint-disable-next-line max-statements-per-line, brace-style |
| 61 | + window.addEventListener('load', () => { |
| 62 | + sampleRUM('load'); |
| 63 | + import(new URL('.rum/@adobe/helix-rum-enhancer@^2/src/index.js', sampleRUM.baseURL)); |
| 64 | + }); |
138 | 65 | }
|
139 | 66 | }
|
140 |
| - if (sampleRUM.always[checkpoint]) { |
141 |
| - sampleRUM.always[checkpoint](data); |
| 67 | + if (window.hlx.rum && window.hlx.rum.isSelected && checkpoint) { |
| 68 | + window.hlx.rum.collector(checkpoint, data, timeShift()); |
142 | 69 | }
|
| 70 | + document.dispatchEvent(new CustomEvent('rum', { detail: { checkpoint, data } })); |
143 | 71 | } catch (error) {
|
144 | 72 | // something went wrong
|
145 | 73 | }
|
|
0 commit comments