@pendo/agent 2.328.0 → 2.328.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/dom.esm.js +14 -6
- package/dist/pendo.module.js +305 -259
- package/dist/pendo.module.min.js +28 -8
- package/dist/servers.json +7 -7
- package/package.json +1 -1
package/dist/pendo.module.js
CHANGED
|
@@ -2916,7 +2916,15 @@ var ConfigReader = (function () {
|
|
|
2916
2916
|
addOption('disableAutoInitialize');
|
|
2917
2917
|
/**
|
|
2918
2918
|
* If set to `true` the web SDK will wait for the host application to be both loaded and visible before
|
|
2919
|
-
* starting the initialization process.
|
|
2919
|
+
* starting the initialization process. Only the first call to `initialize` is honored while waiting
|
|
2920
|
+
* for visibility; subsequent calls are rejected and logged. This setting takes precedence over
|
|
2921
|
+
* `initializeImmediately`.
|
|
2922
|
+
*
|
|
2923
|
+
* This is a server-delivered setting and cannot be provided through the options passed to
|
|
2924
|
+
* `pendo.initialize`: the visibility gate runs before those options are read.
|
|
2925
|
+
*
|
|
2926
|
+
* This relies on the Page Visibility API. In browsers that do not support `document.visibilityState`,
|
|
2927
|
+
* enabling this option will defer initialization indefinitely.
|
|
2920
2928
|
*
|
|
2921
2929
|
* @access public
|
|
2922
2930
|
* @category Config/Core
|
|
@@ -2924,7 +2932,7 @@ var ConfigReader = (function () {
|
|
|
2924
2932
|
* @default false
|
|
2925
2933
|
* @type {boolean}
|
|
2926
2934
|
*/
|
|
2927
|
-
addOption('initializeWhenVisible', [
|
|
2935
|
+
addOption('initializeWhenVisible', [PENDO_CONFIG_SRC], false);
|
|
2928
2936
|
/**
|
|
2929
2937
|
* Although the name refers to cookies, if set to `true` the web SDK will not persist any data in local
|
|
2930
2938
|
* storage or cookies and will rely only on memory.
|
|
@@ -4002,8 +4010,8 @@ let SERVER = '';
|
|
|
4002
4010
|
let ASSET_HOST = '';
|
|
4003
4011
|
let ASSET_PATH = '';
|
|
4004
4012
|
let DESIGNER_SERVER = '';
|
|
4005
|
-
let VERSION = '2.328.
|
|
4006
|
-
let PACKAGE_VERSION = '2.328.
|
|
4013
|
+
let VERSION = '2.328.2_';
|
|
4014
|
+
let PACKAGE_VERSION = '2.328.2';
|
|
4007
4015
|
let LOADER = 'xhr';
|
|
4008
4016
|
/* eslint-enable web-sdk-eslint-rules/no-gulp-env-references */
|
|
4009
4017
|
/**
|
|
@@ -4726,7 +4734,7 @@ var agentStorage = (function () {
|
|
|
4726
4734
|
function read(name, isPlain, cookieSuffix) {
|
|
4727
4735
|
isPlain = registry.getKeyConfig(name, 'isPlain', isPlain);
|
|
4728
4736
|
cookieSuffix = registry.getKeyConfig(name, 'cookieSuffix', cookieSuffix);
|
|
4729
|
-
let keyLocalStorageOnly = registry.getKeyConfig(name, 'localStorageOnly'
|
|
4737
|
+
let keyLocalStorageOnly = registry.getKeyConfig(name, 'localStorageOnly');
|
|
4730
4738
|
var key = !isPlain ? getPendoCookieKey(name, cookieSuffix) : name;
|
|
4731
4739
|
let rawValue;
|
|
4732
4740
|
const deserialize = registry.getKeyDeserializer(name);
|
|
@@ -4796,7 +4804,7 @@ var agentStorage = (function () {
|
|
|
4796
4804
|
isPlain = registry.getKeyConfig(name, 'isPlain', isPlain);
|
|
4797
4805
|
isSecure = registry.getKeyConfig(name, 'isSecure', isSecure);
|
|
4798
4806
|
cookieSuffix = registry.getKeyConfig(name, 'cookieSuffix', cookieSuffix);
|
|
4799
|
-
let keyLocalStorageOnly = registry.getKeyConfig(name, 'localStorageOnly'
|
|
4807
|
+
let keyLocalStorageOnly = registry.getKeyConfig(name, 'localStorageOnly');
|
|
4800
4808
|
val = registry.getKeySerializer(name)(val);
|
|
4801
4809
|
var key = !isPlain ? getPendoCookieKey(name, cookieSuffix) : name;
|
|
4802
4810
|
resetCache(storageAvailable);
|
|
@@ -4837,7 +4845,7 @@ var agentStorage = (function () {
|
|
|
4837
4845
|
function clear(name, isPlain, cookieSuffix) {
|
|
4838
4846
|
isPlain = registry.getKeyConfig(name, 'isPlain', isPlain);
|
|
4839
4847
|
cookieSuffix = registry.getKeyConfig(name, 'cookieSuffix', cookieSuffix);
|
|
4840
|
-
let keyLocalStorageOnly = registry.getKeyConfig(name, 'localStorageOnly'
|
|
4848
|
+
let keyLocalStorageOnly = registry.getKeyConfig(name, 'localStorageOnly');
|
|
4841
4849
|
var key = !isPlain ? getPendoCookieKey(name, cookieSuffix) : name;
|
|
4842
4850
|
if (storageIsDisabled()) {
|
|
4843
4851
|
delete inMemoryStorage[key];
|
|
@@ -12497,6 +12505,22 @@ class SendQueue {
|
|
|
12497
12505
|
|
|
12498
12506
|
const UNSENT_EVENTS_KEY = 'unsentEvents';
|
|
12499
12507
|
const UNSENT_EVENTS_MAX_AGE = 7 * 24 * 60 * 60 * 1000; // 7 days
|
|
12508
|
+
function mergeEvents(target, source) {
|
|
12509
|
+
_.each(source, (requests, key) => {
|
|
12510
|
+
target[key] = (target[key] || []).concat(requests);
|
|
12511
|
+
});
|
|
12512
|
+
return target;
|
|
12513
|
+
}
|
|
12514
|
+
function migrateLegacyCookieEvents(events) {
|
|
12515
|
+
const cookieValue = get_pendo_cookie(UNSENT_EVENTS_KEY);
|
|
12516
|
+
if (cookieValue) {
|
|
12517
|
+
try {
|
|
12518
|
+
mergeEvents(events, JSON.parse(cookieValue));
|
|
12519
|
+
}
|
|
12520
|
+
catch (e) { }
|
|
12521
|
+
clearCookie(getPendoCookieKey(UNSENT_EVENTS_KEY));
|
|
12522
|
+
}
|
|
12523
|
+
}
|
|
12500
12524
|
class LocalStorageEventBuffer {
|
|
12501
12525
|
constructor() {
|
|
12502
12526
|
this.events = {};
|
|
@@ -12527,14 +12551,18 @@ class LocalStorageEventBuffer {
|
|
|
12527
12551
|
* @access public
|
|
12528
12552
|
* @label UNSENT_EVENTS_KEY
|
|
12529
12553
|
*/
|
|
12530
|
-
storage.registry.addLocal(UNSENT_EVENTS_KEY
|
|
12554
|
+
storage.registry.addLocal(UNSENT_EVENTS_KEY, {
|
|
12555
|
+
localStorageOnly: true,
|
|
12556
|
+
duration: UNSENT_EVENTS_MAX_AGE
|
|
12557
|
+
});
|
|
12531
12558
|
try {
|
|
12532
12559
|
this.events = JSON.parse(storage.read(UNSENT_EVENTS_KEY) || '{}');
|
|
12533
|
-
storage.clear(UNSENT_EVENTS_KEY);
|
|
12534
12560
|
}
|
|
12535
12561
|
catch (e) {
|
|
12536
12562
|
this.events = {};
|
|
12537
12563
|
}
|
|
12564
|
+
migrateLegacyCookieEvents(this.events);
|
|
12565
|
+
storage.clear(UNSENT_EVENTS_KEY);
|
|
12538
12566
|
}
|
|
12539
12567
|
write(storage) {
|
|
12540
12568
|
if (_.size(this.events) > 0) {
|
|
@@ -22069,22 +22097,6 @@ var whenLoadedCall = function (callback, win) {
|
|
|
22069
22097
|
}
|
|
22070
22098
|
return _.noop;
|
|
22071
22099
|
};
|
|
22072
|
-
const whenVisibleCall = (callback, win = window) => {
|
|
22073
|
-
const { document } = win;
|
|
22074
|
-
const waitForVis = ConfigReader.get('initializeWhenVisible', false);
|
|
22075
|
-
if (!waitForVis || document.visibilityState === 'visible') {
|
|
22076
|
-
callback();
|
|
22077
|
-
return _.noop;
|
|
22078
|
-
}
|
|
22079
|
-
const stopVisListener = attachEventInternal(document, 'visibilitychange', () => {
|
|
22080
|
-
if (document.visibilityState === 'visible') {
|
|
22081
|
-
callback();
|
|
22082
|
-
// need to shut this down immediately as visibility can continue to change
|
|
22083
|
-
stopVisListener();
|
|
22084
|
-
}
|
|
22085
|
-
});
|
|
22086
|
-
return stopVisListener;
|
|
22087
|
-
};
|
|
22088
22100
|
|
|
22089
22101
|
class GuideTypeIdentifier {
|
|
22090
22102
|
constructor(identificationFn, typeName) {
|
|
@@ -23003,7 +23015,7 @@ function advanceGuide(eventType, step, pendo) {
|
|
|
23003
23015
|
step.attachEvent(btn, eventType, onEvent);
|
|
23004
23016
|
}
|
|
23005
23017
|
function attachBBAdvanceActions(step, pendo) {
|
|
23006
|
-
let advanceActions = pendo._.get(step, 'attributes.advanceActions', {});
|
|
23018
|
+
let advanceActions = pendo._.get(step, 'attributes.advanceActions', {}) || {};
|
|
23007
23019
|
if (advanceActions.elementHover) {
|
|
23008
23020
|
advanceGuide('mouseover', step, pendo);
|
|
23009
23021
|
}
|
|
@@ -28996,6 +29008,44 @@ function applyDoNotTrackConfigOverrides(options) {
|
|
|
28996
29008
|
// ----------------------------------------------------------------------------------
|
|
28997
29009
|
let initializeCounter = 0;
|
|
28998
29010
|
const initializeImmediately = 'initializeImmediately';
|
|
29011
|
+
const initializeWhenVisible = 'initializeWhenVisible';
|
|
29012
|
+
const teardownFns = [];
|
|
29013
|
+
// State for the visibility gate. Only the first gated initialize() call is
|
|
29014
|
+
// honored — it attaches the single visibilitychange listener and its arguments
|
|
29015
|
+
// replay once the document becomes visible. Any later calls while the gate is
|
|
29016
|
+
// pending are rejected and ignored. Must live at module scope so later
|
|
29017
|
+
// initialize() calls can see a gate is active; null when no gate is active.
|
|
29018
|
+
let pendingInitializeArgs = null;
|
|
29019
|
+
function shouldGateOnVisibility() {
|
|
29020
|
+
return ConfigReader.get(initializeWhenVisible, false) &&
|
|
29021
|
+
typeof document !== 'undefined' &&
|
|
29022
|
+
document.visibilityState !== 'visible';
|
|
29023
|
+
}
|
|
29024
|
+
function gateInitializeOnVisibility(args) {
|
|
29025
|
+
if (pendingInitializeArgs !== null) {
|
|
29026
|
+
log.warn('pendo.initialize call rejected: an earlier call is already waiting for the document to become visible.');
|
|
29027
|
+
return;
|
|
29028
|
+
}
|
|
29029
|
+
pendingInitializeArgs = args;
|
|
29030
|
+
let stopVisibilityListener = attachEvent(document, 'visibilitychange', () => {
|
|
29031
|
+
if (document.visibilityState !== 'visible')
|
|
29032
|
+
return;
|
|
29033
|
+
if (stopVisibilityListener) {
|
|
29034
|
+
stopVisibilityListener();
|
|
29035
|
+
stopVisibilityListener = null;
|
|
29036
|
+
}
|
|
29037
|
+
const pendingArgs = pendingInitializeArgs;
|
|
29038
|
+
pendingInitializeArgs = null;
|
|
29039
|
+
initialize.apply(null, pendingArgs);
|
|
29040
|
+
});
|
|
29041
|
+
teardownFns.push(() => {
|
|
29042
|
+
if (stopVisibilityListener) {
|
|
29043
|
+
stopVisibilityListener();
|
|
29044
|
+
stopVisibilityListener = null;
|
|
29045
|
+
}
|
|
29046
|
+
pendingInitializeArgs = null;
|
|
29047
|
+
});
|
|
29048
|
+
}
|
|
28999
29049
|
/**
|
|
29000
29050
|
* Initializes the Pendo Web SDK in a browser window. This function only needs to be called once per page load. Any subsequent calls, without first having called `teardown`, will be ignored.
|
|
29001
29051
|
* Once the web SDK has been initialized, any updates to identity or metadata should be done using `identify` or `updateOptions`.
|
|
@@ -29028,8 +29078,16 @@ const initializeImmediately = 'initializeImmediately';
|
|
|
29028
29078
|
}
|
|
29029
29079
|
});
|
|
29030
29080
|
*/
|
|
29031
|
-
const teardownFns = [];
|
|
29032
29081
|
function initialize(options) {
|
|
29082
|
+
if (shouldGateOnVisibility()) {
|
|
29083
|
+
try {
|
|
29084
|
+
gateInitializeOnVisibility(_.toArray(arguments));
|
|
29085
|
+
}
|
|
29086
|
+
catch (e) {
|
|
29087
|
+
log.critical('pendo.initialize failed while gating on visibility.', e);
|
|
29088
|
+
}
|
|
29089
|
+
return;
|
|
29090
|
+
}
|
|
29033
29091
|
if (document.readyState !== 'complete' && !(_.get(options, initializeImmediately) || ConfigReader.get(initializeImmediately))) {
|
|
29034
29092
|
try {
|
|
29035
29093
|
enqueueCall(pendo$1, 'initialize', arguments);
|
|
@@ -29283,9 +29341,7 @@ function startup(callQueue, autoInitialize) {
|
|
|
29283
29341
|
autoInitialize();
|
|
29284
29342
|
}
|
|
29285
29343
|
else {
|
|
29286
|
-
teardownFns.push(whenLoadedCall(
|
|
29287
|
-
teardownFns.push(whenVisibleCall(autoInitialize));
|
|
29288
|
-
}));
|
|
29344
|
+
teardownFns.push(whenLoadedCall(autoInitialize));
|
|
29289
29345
|
}
|
|
29290
29346
|
}
|
|
29291
29347
|
/**
|
|
@@ -41550,8 +41606,6 @@ function removeMarkdownSyntax(element, textToReplace, replacementText, pendo) {
|
|
|
41550
41606
|
// This prevents us from removing the message for the conditionally rendered elements
|
|
41551
41607
|
element.innerHTML = (_a = element.innerHTML) === null || _a === void 0 ? void 0 : _a.replace(textToReplace, replacementText);
|
|
41552
41608
|
}
|
|
41553
|
-
if (element.localName === 'div')
|
|
41554
|
-
return;
|
|
41555
41609
|
if (element.localName === 'button' ||
|
|
41556
41610
|
element.localName === 'label' ||
|
|
41557
41611
|
element.localName === 'a') {
|
|
@@ -41589,20 +41643,20 @@ function getZoneSafeMethod(_, method, target) {
|
|
|
41589
41643
|
}
|
|
41590
41644
|
|
|
41591
41645
|
// Does not support submit and go to
|
|
41592
|
-
|
|
41593
|
-
|
|
41646
|
+
const goToRegex = new RegExp(guideMarkdownUtil.goToString);
|
|
41647
|
+
const PollBranching = {
|
|
41594
41648
|
name: 'PollBranching',
|
|
41595
|
-
script
|
|
41596
|
-
|
|
41597
|
-
|
|
41649
|
+
script(step, guide, pendo) {
|
|
41650
|
+
let isAdvanceIntercepted = false;
|
|
41651
|
+
const branchingQuestions = initialBranchingSetup(step, pendo);
|
|
41598
41652
|
if (branchingQuestions) {
|
|
41599
41653
|
// If there are too many branching questions saved, exit and run the guide normally.
|
|
41600
41654
|
if (pendo._.size(branchingQuestions) > 1)
|
|
41601
41655
|
return;
|
|
41602
|
-
this.on('beforeAdvance',
|
|
41603
|
-
|
|
41604
|
-
|
|
41605
|
-
|
|
41656
|
+
this.on('beforeAdvance', (evt) => {
|
|
41657
|
+
const noResponseSelected = step.guideElement.find('[branching] .pendo-radio:checked').length === 0;
|
|
41658
|
+
const responseLabel = step.guideElement.find('[branching] .pendo-radio:checked + label')[0];
|
|
41659
|
+
let noGotoLabel;
|
|
41606
41660
|
if (responseLabel) {
|
|
41607
41661
|
noGotoLabel = pendo._.isNull(responseLabel.getAttribute('goToStep'));
|
|
41608
41662
|
}
|
|
@@ -41613,58 +41667,58 @@ var PollBranching = {
|
|
|
41613
41667
|
});
|
|
41614
41668
|
}
|
|
41615
41669
|
},
|
|
41616
|
-
test
|
|
41670
|
+
test(step, guide, pendo) {
|
|
41617
41671
|
var _a;
|
|
41618
|
-
|
|
41672
|
+
let branchingQuestions = (_a = step.guideElement) === null || _a === void 0 ? void 0 : _a.find('._pendo-multi-choice-poll-question:contains("{branching/}")');
|
|
41619
41673
|
return !pendo._.isUndefined(branchingQuestions) && pendo._.size(branchingQuestions);
|
|
41620
41674
|
},
|
|
41621
|
-
designerListener
|
|
41622
|
-
|
|
41623
|
-
|
|
41675
|
+
designerListener(pendo) {
|
|
41676
|
+
const target = pendo.dom.getBody();
|
|
41677
|
+
const config = {
|
|
41624
41678
|
attributeFilter: ['data-layout'],
|
|
41625
41679
|
attributes: true,
|
|
41626
41680
|
childList: true,
|
|
41627
41681
|
characterData: true,
|
|
41628
41682
|
subtree: true
|
|
41629
41683
|
};
|
|
41630
|
-
|
|
41631
|
-
|
|
41684
|
+
const MutationObserver = getZoneSafeMethod(pendo._, 'MutationObserver');
|
|
41685
|
+
const observer = new MutationObserver(applyBranchingIndicators);
|
|
41632
41686
|
observer.observe(target, config);
|
|
41633
41687
|
function applyBranchingIndicators(mutations) {
|
|
41634
41688
|
pendo._.each(mutations, function (mutation) {
|
|
41635
41689
|
var _a;
|
|
41636
|
-
|
|
41690
|
+
const nodeHasQuerySelector = pendo._.isFunction((_a = mutation.addedNodes[0]) === null || _a === void 0 ? void 0 : _a.querySelector);
|
|
41637
41691
|
if (mutation.addedNodes.length && nodeHasQuerySelector) {
|
|
41638
41692
|
if (mutation.addedNodes[0].querySelector('._pendo-multi-choice-poll-select-border')) {
|
|
41639
41693
|
if (pendo._.size(pendo.dom('._pendo-multi-choice-poll-question:contains("{branching/}")'))) {
|
|
41640
41694
|
pendo
|
|
41641
41695
|
.dom('._pendo-multi-choice-poll-question:contains("{branching/}")')
|
|
41642
|
-
.each(
|
|
41643
|
-
pendo._.each(pendo.dom(
|
|
41696
|
+
.each((question, index) => {
|
|
41697
|
+
pendo._.each(pendo.dom(`#${question.id} *`), (element) => {
|
|
41644
41698
|
guideMarkdownUtil.removeMarkdownSyntax(element, '{branching/}', '', pendo);
|
|
41645
41699
|
});
|
|
41646
41700
|
pendo
|
|
41647
|
-
.dom(
|
|
41701
|
+
.dom(`#${question.id} p`)
|
|
41648
41702
|
.css({ display: 'inline-block !important' })
|
|
41649
41703
|
.append(branchingIcon('#999', '20px'))
|
|
41650
41704
|
.attr({ title: 'Custom Branching Added' });
|
|
41651
|
-
|
|
41652
|
-
if (pendo.dom(
|
|
41705
|
+
let dataPendoPollId = question.getAttribute('data-pendo-poll-id');
|
|
41706
|
+
if (pendo.dom(`._pendo-multi-choice-poll-question[data-pendo-poll-id=${dataPendoPollId}]`)[0]) {
|
|
41653
41707
|
// eslint-disable-next-line @typescript-eslint/no-unused-vars
|
|
41654
41708
|
pendo
|
|
41655
|
-
.dom(
|
|
41709
|
+
.dom(`._pendo-multi-choice-poll-question[data-pendo-poll-id=${dataPendoPollId}]`)[0]
|
|
41656
41710
|
.textContent.trim();
|
|
41657
41711
|
}
|
|
41658
|
-
|
|
41712
|
+
let pollLabels = pendo.dom(`label[for*=${dataPendoPollId}]`);
|
|
41659
41713
|
if (pendo._.size(pollLabels)) {
|
|
41660
|
-
pendo._.forEach(pollLabels,
|
|
41714
|
+
pendo._.forEach(pollLabels, (label) => {
|
|
41661
41715
|
if (goToRegex.test(label.textContent)) {
|
|
41662
|
-
|
|
41716
|
+
let labelTitle = goToRegex.exec(label.textContent)[2];
|
|
41663
41717
|
guideMarkdownUtil.removeMarkdownSyntax(label, goToRegex, '', pendo);
|
|
41664
41718
|
pendo
|
|
41665
41719
|
.dom(label)
|
|
41666
41720
|
.append(branchingIcon('#999', '14px'))
|
|
41667
|
-
.attr({ title:
|
|
41721
|
+
.attr({ title: `Branching to step ${labelTitle}` });
|
|
41668
41722
|
}
|
|
41669
41723
|
});
|
|
41670
41724
|
}
|
|
@@ -41672,9 +41726,9 @@ var PollBranching = {
|
|
|
41672
41726
|
pendo
|
|
41673
41727
|
.dom(question)
|
|
41674
41728
|
.append(branchingErrorHTML(question.dataset.pendoPollId));
|
|
41675
|
-
pendo.dom(
|
|
41729
|
+
pendo.dom(`#${question.id} #pendo-ps-branching-svg`).remove();
|
|
41676
41730
|
pendo
|
|
41677
|
-
.dom(
|
|
41731
|
+
.dom(`#${question.id} p`)
|
|
41678
41732
|
.css({ display: 'inline-block !important' })
|
|
41679
41733
|
.append(branchingIcon('red', '20px'))
|
|
41680
41734
|
.attr({ title: 'Unsupported Branching configuration' });
|
|
@@ -41686,31 +41740,49 @@ var PollBranching = {
|
|
|
41686
41740
|
});
|
|
41687
41741
|
}
|
|
41688
41742
|
function branchingErrorHTML(dataPendoPollId) {
|
|
41689
|
-
return
|
|
41743
|
+
return `<div style="text-align:lrft; font-size: 14px; color: red;
|
|
41744
|
+
font-style: italic; margin-top: 0px;" class="branching-wrapper"
|
|
41745
|
+
name="${dataPendoPollId}">
|
|
41746
|
+
* Branching Error: Multiple branching polls not supported</div>`;
|
|
41690
41747
|
}
|
|
41691
41748
|
function branchingIcon(color, size) {
|
|
41692
|
-
return
|
|
41749
|
+
return `<svg id="pendo-ps-branching-svg" viewBox="0 0 24 24" fill="none"
|
|
41750
|
+
style="margin-left: 5px;
|
|
41751
|
+
height:${size}; width:${size}; display:inline; vertical-align:middle;" xmlns="http://www.w3.org/2000/svg">
|
|
41752
|
+
<g stroke-width="0"></g>
|
|
41753
|
+
<g stroke-linecap="round" stroke-linejoin="round"></g>
|
|
41754
|
+
<g> <circle cx="4" cy="7" r="2" stroke="${color}"
|
|
41755
|
+
stroke-width="2" stroke-linecap="round" stroke-linejoin="round"></circle>
|
|
41756
|
+
<circle cx="20" cy="7" r="2" stroke="${color}"
|
|
41757
|
+
stroke-width="2" stroke-linecap="round" stroke-linejoin="round"></circle>
|
|
41758
|
+
<circle cx="20" cy="17" r="2" stroke="${color}" stroke-width="2"
|
|
41759
|
+
stroke-linecap="round" stroke-linejoin="round"></circle>
|
|
41760
|
+
<path d="M18 7H6" stroke="${color}" stroke-width="2"
|
|
41761
|
+
stroke-linecap="round" stroke-linejoin="round"></path>
|
|
41762
|
+
<path d="M7 7V7C8.65685 7 10 8.34315 10 10V15C10 16.1046 10.8954 17 12 17H18"
|
|
41763
|
+
stroke="${color}" stroke-width="2" stroke-linecap="round"
|
|
41764
|
+
stroke-linejoin="round"></path> </g></svg>`;
|
|
41693
41765
|
}
|
|
41694
41766
|
}
|
|
41695
41767
|
};
|
|
41696
41768
|
function initialBranchingSetup(step, pendo) {
|
|
41697
|
-
|
|
41698
|
-
pendo._.forEach(questions,
|
|
41699
|
-
|
|
41700
|
-
pendo._.each(step.guideElement.find(
|
|
41769
|
+
const questions = step.guideElement.find('._pendo-multi-choice-poll-question:contains("{branching/}")');
|
|
41770
|
+
pendo._.forEach(questions, (question) => {
|
|
41771
|
+
let dataPendoPollId = question.getAttribute('data-pendo-poll-id');
|
|
41772
|
+
pendo._.each(step.guideElement.find(`#${question.id} *`), (element) => {
|
|
41701
41773
|
guideMarkdownUtil.removeMarkdownSyntax(element, '{branching/}', '', pendo);
|
|
41702
41774
|
});
|
|
41703
|
-
|
|
41704
|
-
pendo._.forEach(pollLabels,
|
|
41775
|
+
let pollLabels = step.guideElement.find(`label[for*=${dataPendoPollId}]`);
|
|
41776
|
+
pendo._.forEach(pollLabels, (label) => {
|
|
41705
41777
|
if (pendo._.isNull(goToRegex.exec(label.textContent))) {
|
|
41706
41778
|
return;
|
|
41707
41779
|
}
|
|
41708
|
-
|
|
41709
|
-
|
|
41780
|
+
let gotoSubstring = goToRegex.exec(label.textContent)[1];
|
|
41781
|
+
let gotoIndex = goToRegex.exec(label.textContent)[2];
|
|
41710
41782
|
label.setAttribute('goToStep', gotoIndex);
|
|
41711
41783
|
guideMarkdownUtil.removeMarkdownSyntax(label, gotoSubstring, '', pendo);
|
|
41712
41784
|
});
|
|
41713
|
-
|
|
41785
|
+
let pollChoiceContainer = step.guideElement.find(`[data-pendo-poll-id=${dataPendoPollId}]._pendo-multi-choice-poll-select-border`);
|
|
41714
41786
|
if (pollChoiceContainer && pollChoiceContainer.length) {
|
|
41715
41787
|
pollChoiceContainer[0].setAttribute('branching', '');
|
|
41716
41788
|
}
|
|
@@ -41719,15 +41791,15 @@ function initialBranchingSetup(step, pendo) {
|
|
|
41719
41791
|
}
|
|
41720
41792
|
function branchingGoToStep(event, step, guide, pendo) {
|
|
41721
41793
|
var _a;
|
|
41722
|
-
|
|
41723
|
-
|
|
41724
|
-
|
|
41725
|
-
|
|
41794
|
+
let checkedPollInputId = (_a = step.guideElement.find('[branching] input.pendo-radio[data-pendo-poll-id]:checked')[0]) === null || _a === void 0 ? void 0 : _a.id;
|
|
41795
|
+
let checkedPollLabel = step.guideElement.find(`label[for="${checkedPollInputId}"]`)[0];
|
|
41796
|
+
let checkedPollLabelStepIndex = checkedPollLabel === null || checkedPollLabel === void 0 ? void 0 : checkedPollLabel.getAttribute('goToStep');
|
|
41797
|
+
let pollStepIndex = checkedPollLabelStepIndex - 1;
|
|
41726
41798
|
if (pollStepIndex < 0)
|
|
41727
41799
|
return;
|
|
41728
|
-
|
|
41800
|
+
const destinationObject = {
|
|
41729
41801
|
destinationStepId: guide.steps[pollStepIndex].id,
|
|
41730
|
-
step
|
|
41802
|
+
step
|
|
41731
41803
|
};
|
|
41732
41804
|
pendo.goToStep(destinationObject);
|
|
41733
41805
|
event.cancel = true;
|
|
@@ -49696,17 +49768,6 @@ var SessionRecorderBuffer = /** @class */ (function () {
|
|
|
49696
49768
|
return SessionRecorderBuffer;
|
|
49697
49769
|
}());
|
|
49698
49770
|
|
|
49699
|
-
var __assign = function() {
|
|
49700
|
-
__assign = Object.assign || function __assign(t) {
|
|
49701
|
-
for (var s, i = 1, n = arguments.length; i < n; i++) {
|
|
49702
|
-
s = arguments[i];
|
|
49703
|
-
for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p)) t[p] = s[p];
|
|
49704
|
-
}
|
|
49705
|
-
return t;
|
|
49706
|
-
};
|
|
49707
|
-
return __assign.apply(this, arguments);
|
|
49708
|
-
};
|
|
49709
|
-
|
|
49710
49771
|
function __rest(s, e) {
|
|
49711
49772
|
var t = {};
|
|
49712
49773
|
for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p) && e.indexOf(p) < 0)
|
|
@@ -51871,7 +51932,7 @@ function includes(str, substring) {
|
|
|
51871
51932
|
function getResourceType(blockedURI, directive) {
|
|
51872
51933
|
if (!directive || typeof directive !== 'string')
|
|
51873
51934
|
return 'resource';
|
|
51874
|
-
|
|
51935
|
+
const d = directive.toLowerCase();
|
|
51875
51936
|
if (blockedURI === 'inline') {
|
|
51876
51937
|
if (includes(d, 'script-src-attr')) {
|
|
51877
51938
|
return 'inline event handler';
|
|
@@ -51930,12 +51991,11 @@ function getResourceType(blockedURI, directive) {
|
|
|
51930
51991
|
function getDirective(policy, directiveName) {
|
|
51931
51992
|
if (!policy || !directiveName)
|
|
51932
51993
|
return '';
|
|
51933
|
-
|
|
51934
|
-
for (
|
|
51935
|
-
|
|
51936
|
-
|
|
51937
|
-
|
|
51938
|
-
if (lower === needle || lower.startsWith("".concat(needle, " "))) {
|
|
51994
|
+
const needle = directiveName.toLowerCase();
|
|
51995
|
+
for (const directive of policy.split(';')) {
|
|
51996
|
+
const trimmed = directive.trim();
|
|
51997
|
+
const lower = trimmed.toLowerCase();
|
|
51998
|
+
if (lower === needle || lower.startsWith(`${needle} `)) {
|
|
51939
51999
|
return trimmed;
|
|
51940
52000
|
}
|
|
51941
52001
|
}
|
|
@@ -51957,7 +52017,7 @@ function getDirective(policy, directiveName) {
|
|
|
51957
52017
|
function getArticle(phrase) {
|
|
51958
52018
|
if (!phrase || typeof phrase !== 'string')
|
|
51959
52019
|
return 'A';
|
|
51960
|
-
|
|
52020
|
+
const c = phrase.trim().charAt(0).toLowerCase();
|
|
51961
52021
|
return includes('aeiou', c) ? 'An' : 'A';
|
|
51962
52022
|
}
|
|
51963
52023
|
/**
|
|
@@ -52000,47 +52060,46 @@ function createCspViolationMessage(blockedURI, directive, isReportOnly, original
|
|
|
52000
52060
|
return 'Content Security Policy: Unknown violation occurred.';
|
|
52001
52061
|
}
|
|
52002
52062
|
try {
|
|
52003
|
-
|
|
52063
|
+
const reportOnlyText = isReportOnly ? ' (Report-Only)' : '';
|
|
52004
52064
|
// special case for frame-ancestors since it doesn't fit our template at all
|
|
52005
52065
|
if ((directive === null || directive === void 0 ? void 0 : directive.toLowerCase()) === 'frame-ancestors') {
|
|
52006
|
-
return
|
|
52066
|
+
return `Content Security Policy${reportOnlyText}: The display of ${blockedURI} in a frame was blocked because an ancestor violates your site's frame-ancestors policy.\nCurrent CSP: "${originalPolicy}".`;
|
|
52007
52067
|
}
|
|
52008
|
-
|
|
52009
|
-
|
|
52010
|
-
|
|
52011
|
-
|
|
52012
|
-
|
|
52013
|
-
|
|
52014
|
-
return
|
|
52068
|
+
const resourceType = getResourceType(blockedURI, directive);
|
|
52069
|
+
const article = getArticle(resourceType);
|
|
52070
|
+
const source = formatBlockedUri(blockedURI);
|
|
52071
|
+
const directiveValue = getDirective(originalPolicy, directive);
|
|
52072
|
+
const policyDisplay = directiveValue || directive;
|
|
52073
|
+
const resourceDescription = `${article} ${resourceType}${source ? ` from ${source}` : ''}`;
|
|
52074
|
+
return `Content Security Policy${reportOnlyText}: ${resourceDescription} was blocked by your site's \`${policyDisplay}\` policy.\nCurrent CSP: "${originalPolicy}".`;
|
|
52015
52075
|
}
|
|
52016
52076
|
catch (error) {
|
|
52017
|
-
return
|
|
52077
|
+
return `Content Security Policy: Error formatting violation message: ${error.message}`;
|
|
52018
52078
|
}
|
|
52019
52079
|
}
|
|
52020
52080
|
|
|
52021
|
-
|
|
52022
|
-
|
|
52081
|
+
const MAX_LENGTH = 1000;
|
|
52082
|
+
const PII_PATTERN = {
|
|
52023
52083
|
ip: /\b(?:\d{1,3}\.){3}\d{1,3}\b/g,
|
|
52024
52084
|
ssn: /\b\d{3}-\d{2}-\d{4}\b/g,
|
|
52025
52085
|
creditCard: /\b(?:\d[ -]?){12,18}\d\b/g,
|
|
52026
52086
|
httpsUrls: /https:\/\/[^\s]+/g,
|
|
52027
52087
|
email: /[\w._+-]+@[\w.-]+\.\w+/g
|
|
52028
52088
|
};
|
|
52029
|
-
|
|
52030
|
-
|
|
52031
|
-
|
|
52032
|
-
|
|
52033
|
-
|
|
52089
|
+
const PII_REPLACEMENT = '*'.repeat(10);
|
|
52090
|
+
const JSON_PII_KEYS = ['password', 'email', 'key', 'token', 'auth', 'authentication', 'phone', 'address', 'ssn'];
|
|
52091
|
+
const UNABLE_TO_DISPLAY_BODY = '[Unable to display body: detected PII could not be redacted]';
|
|
52092
|
+
const joinedKeys = JSON_PII_KEYS.join('|');
|
|
52093
|
+
const keyPattern = `"([^"]*(?:${joinedKeys})[^"]*)"`;
|
|
52034
52094
|
// only scrub strings, numbers, and booleans
|
|
52035
|
-
|
|
52095
|
+
const acceptedValues = '("([^"\\\\]*(?:\\\\.[^"\\\\]*)*")|(\\d+)|(true|false))';
|
|
52036
52096
|
/**
|
|
52037
52097
|
* Truncates a string to the max length
|
|
52038
52098
|
* @access private
|
|
52039
52099
|
* @param {String} string
|
|
52040
52100
|
* @returns {String}
|
|
52041
52101
|
*/
|
|
52042
|
-
function truncate(string, includeEllipsis) {
|
|
52043
|
-
if (includeEllipsis === void 0) { includeEllipsis = false; }
|
|
52102
|
+
function truncate(string, includeEllipsis = false) {
|
|
52044
52103
|
if (string.length <= MAX_LENGTH)
|
|
52045
52104
|
return string;
|
|
52046
52105
|
if (includeEllipsis) {
|
|
@@ -52057,7 +52116,7 @@ function truncate(string, includeEllipsis) {
|
|
|
52057
52116
|
* @returns {String}
|
|
52058
52117
|
*/
|
|
52059
52118
|
function generateLogKey(methodName, message, stackTrace) {
|
|
52060
|
-
return
|
|
52119
|
+
return `${methodName}|${message}|${stackTrace}`;
|
|
52061
52120
|
}
|
|
52062
52121
|
/**
|
|
52063
52122
|
* Checks if a string has 2 or more digits, a https URL, or an email address
|
|
@@ -52074,13 +52133,12 @@ function mightContainPII(string) {
|
|
|
52074
52133
|
* @param {String} string
|
|
52075
52134
|
* @returns {String}
|
|
52076
52135
|
*/
|
|
52077
|
-
function scrubPII(
|
|
52078
|
-
var string = _a.string, _ = _a._;
|
|
52136
|
+
function scrubPII({ string, _ }) {
|
|
52079
52137
|
if (!string || typeof string !== 'string')
|
|
52080
52138
|
return string;
|
|
52081
52139
|
if (!mightContainPII(string))
|
|
52082
52140
|
return string;
|
|
52083
|
-
return _.reduce(_.values(PII_PATTERN),
|
|
52141
|
+
return _.reduce(_.values(PII_PATTERN), (str, pattern) => str.replace(pattern, PII_REPLACEMENT), string);
|
|
52084
52142
|
}
|
|
52085
52143
|
/**
|
|
52086
52144
|
* Scrub PII from a stringified JSON object
|
|
@@ -52089,14 +52147,12 @@ function scrubPII(_a) {
|
|
|
52089
52147
|
* @returns {String}
|
|
52090
52148
|
*/
|
|
52091
52149
|
function scrubJsonPII(string) {
|
|
52092
|
-
|
|
52150
|
+
const fullScrubRegex = new RegExp(`${keyPattern}\\s*:\\s*[\\{\\[]`, 'i');
|
|
52093
52151
|
if (fullScrubRegex.test(string)) {
|
|
52094
52152
|
return UNABLE_TO_DISPLAY_BODY;
|
|
52095
52153
|
}
|
|
52096
|
-
|
|
52097
|
-
return string.replace(keyValueScrubRegex,
|
|
52098
|
-
return "\"".concat(key, "\":\"").concat(PII_REPLACEMENT, "\"");
|
|
52099
|
-
});
|
|
52154
|
+
const keyValueScrubRegex = new RegExp(`${keyPattern}\\s*:\\s*${acceptedValues}`, 'gi');
|
|
52155
|
+
return string.replace(keyValueScrubRegex, (match, key) => `"${key}":"${PII_REPLACEMENT}"`);
|
|
52100
52156
|
}
|
|
52101
52157
|
/**
|
|
52102
52158
|
* Checks if a string is a JSON object
|
|
@@ -52108,7 +52164,7 @@ function scrubJsonPII(string) {
|
|
|
52108
52164
|
function mightContainJson(string, contentType) {
|
|
52109
52165
|
if (!string || typeof string !== 'string')
|
|
52110
52166
|
return false;
|
|
52111
|
-
|
|
52167
|
+
const firstChar = string.charAt(0);
|
|
52112
52168
|
if (contentType && contentType.indexOf('application/json') !== -1) {
|
|
52113
52169
|
return true;
|
|
52114
52170
|
}
|
|
@@ -52121,20 +52177,19 @@ function mightContainJson(string, contentType) {
|
|
|
52121
52177
|
* @param {String} contentType
|
|
52122
52178
|
* @returns {String}
|
|
52123
52179
|
*/
|
|
52124
|
-
function maskSensitiveFields(
|
|
52125
|
-
var string = _a.string, contentType = _a.contentType, _ = _a._;
|
|
52180
|
+
function maskSensitiveFields({ string, contentType, _ }) {
|
|
52126
52181
|
if (!string || typeof string !== 'string')
|
|
52127
52182
|
return string;
|
|
52128
52183
|
if (mightContainJson(string, contentType)) {
|
|
52129
52184
|
string = scrubJsonPII(string);
|
|
52130
52185
|
}
|
|
52131
52186
|
if (mightContainPII(string)) {
|
|
52132
|
-
string = scrubPII({ string
|
|
52187
|
+
string = scrubPII({ string, _ });
|
|
52133
52188
|
}
|
|
52134
52189
|
return string;
|
|
52135
52190
|
}
|
|
52136
52191
|
|
|
52137
|
-
|
|
52192
|
+
const DEV_LOG_TYPE = 'devlog';
|
|
52138
52193
|
function createDevLogEnvelope(pluginAPI, globalPendo) {
|
|
52139
52194
|
return {
|
|
52140
52195
|
browser_time: pluginAPI.util.getNow(),
|
|
@@ -52145,12 +52200,12 @@ function createDevLogEnvelope(pluginAPI, globalPendo) {
|
|
|
52145
52200
|
};
|
|
52146
52201
|
}
|
|
52147
52202
|
|
|
52148
|
-
|
|
52149
|
-
|
|
52150
|
-
|
|
52151
|
-
|
|
52152
|
-
|
|
52153
|
-
|
|
52203
|
+
const TOKEN_MAX_SIZE = 100;
|
|
52204
|
+
const TOKEN_REFILL_RATE = 10;
|
|
52205
|
+
const TOKEN_REFRESH_INTERVAL = 1000;
|
|
52206
|
+
const MAX_UNCOMPRESSED_SIZE = 125000; // 125KB
|
|
52207
|
+
class DevlogBuffer {
|
|
52208
|
+
constructor(pendo, pluginAPI) {
|
|
52154
52209
|
this.pendo = pendo;
|
|
52155
52210
|
this.pluginAPI = pluginAPI;
|
|
52156
52211
|
this.events = [];
|
|
@@ -52161,36 +52216,36 @@ var DevlogBuffer = /** @class */ (function () {
|
|
|
52161
52216
|
this.lastRefillTime = this.pluginAPI.util.getNow();
|
|
52162
52217
|
this.nextRefillTime = this.lastRefillTime + TOKEN_REFRESH_INTERVAL;
|
|
52163
52218
|
}
|
|
52164
|
-
|
|
52219
|
+
isEmpty() {
|
|
52165
52220
|
return this.events.length === 0 && this.payloads.length === 0;
|
|
52166
|
-
}
|
|
52167
|
-
|
|
52168
|
-
|
|
52221
|
+
}
|
|
52222
|
+
refillTokens() {
|
|
52223
|
+
const now = this.pluginAPI.util.getNow();
|
|
52169
52224
|
if (now >= this.nextRefillTime) {
|
|
52170
|
-
|
|
52171
|
-
|
|
52172
|
-
|
|
52225
|
+
const timeSinceLastRefill = now - this.lastRefillTime;
|
|
52226
|
+
const secondsSinceLastRefill = Math.floor(timeSinceLastRefill / TOKEN_REFRESH_INTERVAL);
|
|
52227
|
+
const tokensToRefill = secondsSinceLastRefill * TOKEN_REFILL_RATE;
|
|
52173
52228
|
this.tokens = Math.min(this.tokens + tokensToRefill, TOKEN_MAX_SIZE);
|
|
52174
52229
|
this.lastRefillTime = now;
|
|
52175
52230
|
this.nextRefillTime = now + TOKEN_REFRESH_INTERVAL;
|
|
52176
52231
|
}
|
|
52177
|
-
}
|
|
52178
|
-
|
|
52232
|
+
}
|
|
52233
|
+
clear() {
|
|
52179
52234
|
this.events = [];
|
|
52180
52235
|
this.lastEvent = null;
|
|
52181
52236
|
this.uncompressedSize = 0;
|
|
52182
|
-
}
|
|
52183
|
-
|
|
52237
|
+
}
|
|
52238
|
+
hasTokenAvailable() {
|
|
52184
52239
|
this.refillTokens();
|
|
52185
52240
|
return this.tokens > 0;
|
|
52186
|
-
}
|
|
52187
|
-
|
|
52241
|
+
}
|
|
52242
|
+
estimateEventSize(event) {
|
|
52188
52243
|
return JSON.stringify(event).length;
|
|
52189
|
-
}
|
|
52190
|
-
|
|
52244
|
+
}
|
|
52245
|
+
push(event) {
|
|
52191
52246
|
if (!this.hasTokenAvailable())
|
|
52192
52247
|
return false;
|
|
52193
|
-
|
|
52248
|
+
const eventSize = this.estimateEventSize(event);
|
|
52194
52249
|
if (this.uncompressedSize + eventSize > MAX_UNCOMPRESSED_SIZE) {
|
|
52195
52250
|
this.compressCurrentChunk();
|
|
52196
52251
|
}
|
|
@@ -52199,55 +52254,54 @@ var DevlogBuffer = /** @class */ (function () {
|
|
|
52199
52254
|
this.events.push(event);
|
|
52200
52255
|
this.tokens = Math.max(this.tokens - 1, 0);
|
|
52201
52256
|
return true;
|
|
52202
|
-
}
|
|
52203
|
-
|
|
52257
|
+
}
|
|
52258
|
+
compressCurrentChunk() {
|
|
52204
52259
|
if (this.events.length === 0)
|
|
52205
52260
|
return;
|
|
52206
|
-
|
|
52261
|
+
const jzb = this.pendo.compress(this.events);
|
|
52207
52262
|
this.payloads.push(jzb);
|
|
52208
52263
|
this.clear();
|
|
52209
|
-
}
|
|
52210
|
-
|
|
52211
|
-
|
|
52264
|
+
}
|
|
52265
|
+
generateUrl() {
|
|
52266
|
+
const queryParams = {
|
|
52212
52267
|
v: this.pendo.VERSION,
|
|
52213
52268
|
ct: this.pluginAPI.util.getNow()
|
|
52214
52269
|
};
|
|
52215
52270
|
return this.pluginAPI.transmit.buildBaseDataUrl(DEV_LOG_TYPE, this.pendo.apiKey, queryParams);
|
|
52216
|
-
}
|
|
52217
|
-
|
|
52271
|
+
}
|
|
52272
|
+
pack() {
|
|
52218
52273
|
if (this.isEmpty())
|
|
52219
52274
|
return;
|
|
52220
|
-
|
|
52275
|
+
const url = this.generateUrl();
|
|
52221
52276
|
this.compressCurrentChunk();
|
|
52222
|
-
|
|
52223
|
-
jzb
|
|
52224
|
-
url
|
|
52225
|
-
})
|
|
52277
|
+
const payloads = this.pendo._.map(this.payloads, (jzb) => ({
|
|
52278
|
+
jzb,
|
|
52279
|
+
url
|
|
52280
|
+
}));
|
|
52226
52281
|
this.payloads = [];
|
|
52227
52282
|
return payloads;
|
|
52228
|
-
}
|
|
52229
|
-
|
|
52230
|
-
}());
|
|
52283
|
+
}
|
|
52284
|
+
}
|
|
52231
52285
|
|
|
52232
|
-
|
|
52233
|
-
|
|
52286
|
+
class DevlogTransport {
|
|
52287
|
+
constructor(globalPendo, pluginAPI) {
|
|
52234
52288
|
this.pendo = globalPendo;
|
|
52235
52289
|
this.pluginAPI = pluginAPI;
|
|
52236
52290
|
}
|
|
52237
|
-
|
|
52238
|
-
|
|
52291
|
+
buildGetUrl(baseUrl, jzb) {
|
|
52292
|
+
const params = {};
|
|
52239
52293
|
if (this.pluginAPI.agent.treatAsAdoptPartner()) {
|
|
52240
52294
|
this.pluginAPI.agent.addAccountIdParams(params, this.pendo.get_account_id(), this.pluginAPI.ConfigReader.get('oemAccountId'));
|
|
52241
52295
|
}
|
|
52242
|
-
|
|
52296
|
+
const jwtOptions = this.pluginAPI.agent.getJwtInfoCopy();
|
|
52243
52297
|
if (!this.pendo._.isEmpty(jwtOptions)) {
|
|
52244
52298
|
this.pendo._.extend(params, jwtOptions);
|
|
52245
52299
|
}
|
|
52246
52300
|
params.jzb = jzb;
|
|
52247
|
-
|
|
52248
|
-
return
|
|
52249
|
-
}
|
|
52250
|
-
|
|
52301
|
+
const queryString = this.pendo._.map(params, (value, key) => `${key}=${value}`).join('&');
|
|
52302
|
+
return `${baseUrl}${baseUrl.indexOf('?') !== -1 ? '&' : '?'}${queryString}`;
|
|
52303
|
+
}
|
|
52304
|
+
get(url, options) {
|
|
52251
52305
|
options.method = 'GET';
|
|
52252
52306
|
if (this.pluginAPI.transmit.fetchKeepalive.supported()) {
|
|
52253
52307
|
return this.pluginAPI.transmit.fetchKeepalive(url, options);
|
|
@@ -52255,90 +52309,86 @@ var DevlogTransport = /** @class */ (function () {
|
|
|
52255
52309
|
else {
|
|
52256
52310
|
return this.pendo.ajax.get(url);
|
|
52257
52311
|
}
|
|
52258
|
-
}
|
|
52259
|
-
|
|
52260
|
-
|
|
52261
|
-
var getUrl = this.buildGetUrl(url, jzb);
|
|
52312
|
+
}
|
|
52313
|
+
sendRequestWithGet({ url, jzb }) {
|
|
52314
|
+
const getUrl = this.buildGetUrl(url, jzb);
|
|
52262
52315
|
return this.get(getUrl, {
|
|
52263
52316
|
headers: {
|
|
52264
52317
|
'Content-Type': 'application/octet-stream'
|
|
52265
52318
|
}
|
|
52266
52319
|
});
|
|
52267
|
-
}
|
|
52268
|
-
|
|
52320
|
+
}
|
|
52321
|
+
post(url, options) {
|
|
52269
52322
|
options.method = 'POST';
|
|
52270
52323
|
if (options.keepalive && this.pluginAPI.transmit.fetchKeepalive.supported()) {
|
|
52271
52324
|
return this.pluginAPI.transmit.fetchKeepalive(url, options);
|
|
52272
52325
|
}
|
|
52273
52326
|
else if (options.keepalive && this.pluginAPI.transmit.sendBeacon.supported()) {
|
|
52274
|
-
|
|
52327
|
+
const result = this.pluginAPI.transmit.sendBeacon(url, new Blob([options.body]));
|
|
52275
52328
|
return result ? Promise$2.resolve() : Promise$2.reject(new Error('sendBeacon failed to send devlog data'));
|
|
52276
52329
|
}
|
|
52277
52330
|
else {
|
|
52278
52331
|
return this.pendo.ajax.post(url, options.body);
|
|
52279
52332
|
}
|
|
52280
|
-
}
|
|
52281
|
-
|
|
52282
|
-
|
|
52283
|
-
|
|
52284
|
-
var bodyPayload = {
|
|
52333
|
+
}
|
|
52334
|
+
sendRequestWithPost({ url, jzb }, isUnload) {
|
|
52335
|
+
const jwtOptions = this.pluginAPI.agent.getJwtInfoCopy();
|
|
52336
|
+
const bodyPayload = {
|
|
52285
52337
|
events: jzb,
|
|
52286
52338
|
browser_time: this.pluginAPI.util.getNow()
|
|
52287
52339
|
};
|
|
52288
52340
|
if (this.pluginAPI.agent.treatAsAdoptPartner()) {
|
|
52289
52341
|
this.pluginAPI.agent.addAccountIdParams(bodyPayload, this.pendo.get_account_id(), this.pluginAPI.ConfigReader.get('oemAccountId'));
|
|
52290
52342
|
}
|
|
52291
|
-
|
|
52343
|
+
const body = JSON.stringify(this.pendo._.extend(bodyPayload, jwtOptions));
|
|
52292
52344
|
return this.post(url, {
|
|
52293
|
-
body
|
|
52345
|
+
body,
|
|
52294
52346
|
headers: {
|
|
52295
52347
|
'Content-Type': 'application/json'
|
|
52296
52348
|
},
|
|
52297
52349
|
keepalive: isUnload
|
|
52298
52350
|
});
|
|
52299
|
-
}
|
|
52300
|
-
|
|
52301
|
-
|
|
52302
|
-
var compressedLength = jzb.length;
|
|
52351
|
+
}
|
|
52352
|
+
sendRequest({ url, jzb }, isUnload) {
|
|
52353
|
+
const compressedLength = jzb.length;
|
|
52303
52354
|
if (compressedLength <= this.pluginAPI.constants.ENCODED_EVENT_MAX_LENGTH && !this.pluginAPI.ConfigReader.get('sendEventsWithPostOnly')) {
|
|
52304
|
-
return this.sendRequestWithGet({ url
|
|
52355
|
+
return this.sendRequestWithGet({ url, jzb });
|
|
52305
52356
|
}
|
|
52306
|
-
return this.sendRequestWithPost({ url
|
|
52307
|
-
}
|
|
52308
|
-
|
|
52309
|
-
}());
|
|
52357
|
+
return this.sendRequestWithPost({ url, jzb }, isUnload);
|
|
52358
|
+
}
|
|
52359
|
+
}
|
|
52310
52360
|
|
|
52311
52361
|
function ConsoleCapture() {
|
|
52312
|
-
|
|
52313
|
-
|
|
52314
|
-
|
|
52315
|
-
|
|
52316
|
-
|
|
52317
|
-
|
|
52318
|
-
|
|
52319
|
-
|
|
52320
|
-
|
|
52321
|
-
|
|
52322
|
-
|
|
52323
|
-
|
|
52362
|
+
let pluginAPI;
|
|
52363
|
+
let _;
|
|
52364
|
+
let globalPendo;
|
|
52365
|
+
let buffer;
|
|
52366
|
+
let sendQueue;
|
|
52367
|
+
let sendInterval;
|
|
52368
|
+
let transport;
|
|
52369
|
+
let isPtmPaused;
|
|
52370
|
+
let isCapturingConsoleLogs = false;
|
|
52371
|
+
const CAPTURE_CONSOLE_CONFIG = 'captureConsoleLogs';
|
|
52372
|
+
const CONSOLE_METHODS = ['log', 'warn', 'error', 'info'];
|
|
52373
|
+
const DEV_LOG_SUB_TYPE = 'console';
|
|
52324
52374
|
// deduplicate logs
|
|
52325
|
-
|
|
52375
|
+
let lastLogKey = '';
|
|
52326
52376
|
return {
|
|
52327
52377
|
name: 'ConsoleCapture',
|
|
52328
|
-
initialize
|
|
52329
|
-
teardown
|
|
52330
|
-
addIntercepts
|
|
52331
|
-
createConsoleEvent
|
|
52332
|
-
captureStackTrace
|
|
52333
|
-
send
|
|
52334
|
-
setCaptureState
|
|
52335
|
-
recordingStarted
|
|
52336
|
-
recordingStopped
|
|
52337
|
-
onAppHidden
|
|
52338
|
-
onAppUnloaded
|
|
52339
|
-
onPtmPaused
|
|
52340
|
-
onPtmUnpaused
|
|
52341
|
-
securityPolicyViolationFn
|
|
52378
|
+
initialize,
|
|
52379
|
+
teardown,
|
|
52380
|
+
addIntercepts,
|
|
52381
|
+
createConsoleEvent,
|
|
52382
|
+
captureStackTrace,
|
|
52383
|
+
send,
|
|
52384
|
+
setCaptureState,
|
|
52385
|
+
recordingStarted,
|
|
52386
|
+
recordingStopped,
|
|
52387
|
+
onAppHidden,
|
|
52388
|
+
onAppUnloaded,
|
|
52389
|
+
onPtmPaused,
|
|
52390
|
+
onPtmUnpaused,
|
|
52391
|
+
securityPolicyViolationFn,
|
|
52342
52392
|
get isCapturingConsoleLogs() {
|
|
52343
52393
|
return isCapturingConsoleLogs;
|
|
52344
52394
|
},
|
|
@@ -52355,16 +52405,16 @@ function ConsoleCapture() {
|
|
|
52355
52405
|
function initialize(pendo, PluginAPI) {
|
|
52356
52406
|
_ = pendo._;
|
|
52357
52407
|
pluginAPI = PluginAPI;
|
|
52358
|
-
|
|
52408
|
+
const { ConfigReader } = pluginAPI;
|
|
52359
52409
|
ConfigReader.addOption(CAPTURE_CONSOLE_CONFIG, [ConfigReader.sources.PENDO_CONFIG_SRC], false);
|
|
52360
|
-
|
|
52410
|
+
const captureConsoleEnabled = ConfigReader.get(CAPTURE_CONSOLE_CONFIG);
|
|
52361
52411
|
if (!captureConsoleEnabled)
|
|
52362
52412
|
return;
|
|
52363
52413
|
globalPendo = pendo;
|
|
52364
52414
|
buffer = new DevlogBuffer(pendo, pluginAPI);
|
|
52365
52415
|
transport = new DevlogTransport(pendo, pluginAPI);
|
|
52366
52416
|
sendQueue = new pluginAPI.SendQueue(transport.sendRequest.bind(transport));
|
|
52367
|
-
sendInterval = setInterval(
|
|
52417
|
+
sendInterval = setInterval(() => {
|
|
52368
52418
|
if (!sendQueue.failed()) {
|
|
52369
52419
|
send();
|
|
52370
52420
|
}
|
|
@@ -52390,19 +52440,17 @@ function ConsoleCapture() {
|
|
|
52390
52440
|
function onPtmUnpaused() {
|
|
52391
52441
|
isPtmPaused = false;
|
|
52392
52442
|
if (!buffer.isEmpty()) {
|
|
52393
|
-
for (
|
|
52394
|
-
|
|
52395
|
-
pluginAPI.Events.eventCaptured.trigger(event_1);
|
|
52443
|
+
for (const event of buffer.events) {
|
|
52444
|
+
pluginAPI.Events.eventCaptured.trigger(event);
|
|
52396
52445
|
}
|
|
52397
52446
|
send();
|
|
52398
52447
|
}
|
|
52399
52448
|
}
|
|
52400
|
-
function setCaptureState(
|
|
52401
|
-
var _b = _a === void 0 ? {} : _a, _c = _b.shouldCapture, shouldCapture = _c === void 0 ? false : _c, _d = _b.reason, reason = _d === void 0 ? '' : _d;
|
|
52449
|
+
function setCaptureState({ shouldCapture = false, reason = '' } = {}) {
|
|
52402
52450
|
if (shouldCapture === isCapturingConsoleLogs)
|
|
52403
52451
|
return;
|
|
52404
52452
|
isCapturingConsoleLogs = shouldCapture;
|
|
52405
|
-
pluginAPI.log.info(
|
|
52453
|
+
pluginAPI.log.info(`[ConsoleCapture] Console log capture ${shouldCapture ? 'started' : 'stopped'}${reason ? `: ${reason}` : ''}`);
|
|
52406
52454
|
}
|
|
52407
52455
|
function recordingStarted() {
|
|
52408
52456
|
setCaptureState({ shouldCapture: true, reason: 'recording started' });
|
|
@@ -52422,12 +52470,12 @@ function ConsoleCapture() {
|
|
|
52422
52470
|
}
|
|
52423
52471
|
function addIntercepts() {
|
|
52424
52472
|
_.each(CONSOLE_METHODS, function (methodName) {
|
|
52425
|
-
|
|
52473
|
+
const originalMethod = console[methodName];
|
|
52426
52474
|
if (!originalMethod)
|
|
52427
52475
|
return;
|
|
52428
52476
|
console[methodName] = _.wrap(originalMethod, function (originalFn) {
|
|
52429
52477
|
// slice 1 to omit originalFn
|
|
52430
|
-
|
|
52478
|
+
const args = _.toArray(arguments).slice(1);
|
|
52431
52479
|
originalFn.apply(console, args);
|
|
52432
52480
|
createConsoleEvent(args, methodName);
|
|
52433
52481
|
});
|
|
@@ -52439,10 +52487,10 @@ function ConsoleCapture() {
|
|
|
52439
52487
|
function securityPolicyViolationFn(evt) {
|
|
52440
52488
|
if (!evt || typeof evt !== 'object')
|
|
52441
52489
|
return;
|
|
52442
|
-
|
|
52443
|
-
|
|
52444
|
-
|
|
52445
|
-
|
|
52490
|
+
const { blockedURI, violatedDirective, effectiveDirective, disposition, originalPolicy } = evt;
|
|
52491
|
+
const directive = violatedDirective || effectiveDirective;
|
|
52492
|
+
const isReportOnly = disposition === 'report';
|
|
52493
|
+
const message = createCspViolationMessage(blockedURI, directive, isReportOnly, originalPolicy);
|
|
52446
52494
|
if (isReportOnly) {
|
|
52447
52495
|
createConsoleEvent([message], 'warn', { skipStackTrace: true, skipScrubPII: true });
|
|
52448
52496
|
}
|
|
@@ -52450,13 +52498,12 @@ function ConsoleCapture() {
|
|
|
52450
52498
|
createConsoleEvent([message], 'error', { skipStackTrace: true, skipScrubPII: true });
|
|
52451
52499
|
}
|
|
52452
52500
|
}
|
|
52453
|
-
function createConsoleEvent(args, methodName,
|
|
52454
|
-
var _b = _a === void 0 ? {} : _a, _c = _b.skipStackTrace, skipStackTrace = _c === void 0 ? false : _c, _d = _b.skipScrubPII, skipScrubPII = _d === void 0 ? false : _d;
|
|
52501
|
+
function createConsoleEvent(args, methodName, { skipStackTrace = false, skipScrubPII = false } = {}) {
|
|
52455
52502
|
if (!isCapturingConsoleLogs || !args || args.length === 0 || !_.contains(CONSOLE_METHODS, methodName))
|
|
52456
52503
|
return;
|
|
52457
52504
|
// stringify args
|
|
52458
|
-
|
|
52459
|
-
|
|
52505
|
+
let message = _.compact(_.map(args, arg => {
|
|
52506
|
+
let stringifiedArg;
|
|
52460
52507
|
try {
|
|
52461
52508
|
stringifiedArg = stringify(arg);
|
|
52462
52509
|
}
|
|
@@ -52468,22 +52515,22 @@ function ConsoleCapture() {
|
|
|
52468
52515
|
if (!message)
|
|
52469
52516
|
return;
|
|
52470
52517
|
// capture stack trace
|
|
52471
|
-
|
|
52518
|
+
let stackTrace = '';
|
|
52472
52519
|
if (!skipStackTrace) {
|
|
52473
|
-
|
|
52520
|
+
const maxStackFrames = methodName === 'error' ? 4 : 1;
|
|
52474
52521
|
stackTrace = captureStackTrace(maxStackFrames);
|
|
52475
52522
|
}
|
|
52476
52523
|
// truncate message and stack trace
|
|
52477
52524
|
message = truncate(message);
|
|
52478
52525
|
stackTrace = truncate(stackTrace);
|
|
52479
52526
|
// de-duplicate log
|
|
52480
|
-
|
|
52527
|
+
const logKey = generateLogKey(methodName, message, stackTrace);
|
|
52481
52528
|
if (isExistingDuplicateLog(logKey)) {
|
|
52482
52529
|
buffer.lastEvent.devLogCount++;
|
|
52483
52530
|
return;
|
|
52484
52531
|
}
|
|
52485
|
-
|
|
52486
|
-
|
|
52532
|
+
const devLogEnvelope = createDevLogEnvelope(pluginAPI, globalPendo);
|
|
52533
|
+
const consoleEvent = Object.assign(Object.assign({}, devLogEnvelope), { subType: DEV_LOG_SUB_TYPE, devLogLevel: methodName === 'log' ? 'info' : methodName, devLogMessage: skipScrubPII ? message : scrubPII({ string: message, _ }), devLogTrace: stackTrace, devLogCount: 1 });
|
|
52487
52534
|
if (!buffer.hasTokenAvailable())
|
|
52488
52535
|
return consoleEvent;
|
|
52489
52536
|
if (!isPtmPaused) {
|
|
@@ -52495,8 +52542,8 @@ function ConsoleCapture() {
|
|
|
52495
52542
|
}
|
|
52496
52543
|
function captureStackTrace(maxStackFrames) {
|
|
52497
52544
|
try {
|
|
52498
|
-
|
|
52499
|
-
return _.map(stackFrames,
|
|
52545
|
+
const stackFrames = ErrorStackParser.parse(new Error(), maxStackFrames);
|
|
52546
|
+
return _.map(stackFrames, frame => frame.toString()).join('\n');
|
|
52500
52547
|
}
|
|
52501
52548
|
catch (error) {
|
|
52502
52549
|
return '';
|
|
@@ -52508,22 +52555,21 @@ function ConsoleCapture() {
|
|
|
52508
52555
|
function updateLastLog(logKey) {
|
|
52509
52556
|
lastLogKey = logKey;
|
|
52510
52557
|
}
|
|
52511
|
-
function send(
|
|
52512
|
-
var _b = _a === void 0 ? {} : _a, _c = _b.unload, unload = _c === void 0 ? false : _c, _d = _b.hidden, hidden = _d === void 0 ? false : _d;
|
|
52558
|
+
function send({ unload = false, hidden = false } = {}) {
|
|
52513
52559
|
if (!buffer || buffer.isEmpty())
|
|
52514
52560
|
return;
|
|
52515
52561
|
if (!globalPendo.isSendingEvents()) {
|
|
52516
52562
|
buffer.clear();
|
|
52517
52563
|
return;
|
|
52518
52564
|
}
|
|
52519
|
-
|
|
52565
|
+
const payloads = buffer.pack();
|
|
52520
52566
|
if (!payloads || payloads.length === 0)
|
|
52521
52567
|
return;
|
|
52522
52568
|
if (unload || hidden) {
|
|
52523
52569
|
sendQueue.drain(payloads, unload);
|
|
52524
52570
|
}
|
|
52525
52571
|
else {
|
|
52526
|
-
sendQueue.push
|
|
52572
|
+
sendQueue.push(...payloads);
|
|
52527
52573
|
}
|
|
52528
52574
|
}
|
|
52529
52575
|
function teardown() {
|
|
@@ -52547,7 +52593,7 @@ function ConsoleCapture() {
|
|
|
52547
52593
|
_.each(CONSOLE_METHODS, function (methodName) {
|
|
52548
52594
|
if (!console[methodName])
|
|
52549
52595
|
return _.noop;
|
|
52550
|
-
|
|
52596
|
+
const unwrap = console[methodName]._pendoUnwrap;
|
|
52551
52597
|
if (_.isFunction(unwrap)) {
|
|
52552
52598
|
unwrap();
|
|
52553
52599
|
}
|