@newrelic/browser-agent 1.301.0-rc.0 → 1.301.0-rc.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/cjs/common/config/init-types.js +1 -1
- package/dist/cjs/common/config/init.js +7 -1
- package/dist/cjs/common/config/runtime.js +1 -1
- package/dist/cjs/common/constants/agent-constants.js +11 -2
- package/dist/cjs/common/constants/env.cdn.js +1 -1
- package/dist/cjs/common/constants/env.npm.js +1 -1
- package/dist/cjs/common/drain/drain.js +1 -1
- package/dist/cjs/common/harvest/harvester.js +30 -39
- package/dist/cjs/common/util/mfe.js +45 -0
- package/dist/cjs/features/generic_events/aggregate/index.js +9 -8
- package/dist/cjs/features/generic_events/constants.js +3 -1
- package/dist/cjs/features/jserrors/aggregate/index.js +18 -17
- package/dist/cjs/features/logging/aggregate/index.js +19 -15
- package/dist/cjs/features/logging/shared/utils.js +3 -3
- package/dist/cjs/features/page_view_event/aggregate/index.js +3 -33
- package/dist/cjs/features/session_replay/aggregate/index.js +13 -13
- package/dist/cjs/features/session_replay/shared/recorder.js +3 -2
- package/dist/cjs/features/session_trace/aggregate/index.js +0 -2
- package/dist/cjs/features/soft_navigations/aggregate/index.js +1 -2
- package/dist/cjs/features/utils/aggregate-base.js +45 -47
- package/dist/cjs/loaders/api/addPageAction.js +2 -2
- package/dist/cjs/loaders/api/log.js +2 -2
- package/dist/cjs/loaders/api/noticeError.js +2 -2
- package/dist/cjs/loaders/api/register-api-types.js +5 -5
- package/dist/cjs/loaders/api/register.js +80 -97
- package/dist/esm/common/config/init-types.js +1 -1
- package/dist/esm/common/config/init.js +7 -1
- package/dist/esm/common/config/runtime.js +1 -1
- package/dist/esm/common/constants/agent-constants.js +9 -1
- package/dist/esm/common/constants/env.cdn.js +1 -1
- package/dist/esm/common/constants/env.npm.js +1 -1
- package/dist/esm/common/drain/drain.js +1 -1
- package/dist/esm/common/harvest/harvester.js +30 -39
- package/dist/esm/common/util/mfe.js +38 -0
- package/dist/esm/features/generic_events/aggregate/index.js +9 -8
- package/dist/esm/features/generic_events/constants.js +3 -1
- package/dist/esm/features/jserrors/aggregate/index.js +18 -17
- package/dist/esm/features/logging/aggregate/index.js +19 -15
- package/dist/esm/features/logging/shared/utils.js +3 -3
- package/dist/esm/features/page_view_event/aggregate/index.js +3 -33
- package/dist/esm/features/session_replay/aggregate/index.js +13 -13
- package/dist/esm/features/session_replay/shared/recorder.js +3 -2
- package/dist/esm/features/session_trace/aggregate/index.js +0 -2
- package/dist/esm/features/soft_navigations/aggregate/index.js +1 -2
- package/dist/esm/features/utils/aggregate-base.js +46 -48
- package/dist/esm/loaders/api/addPageAction.js +2 -2
- package/dist/esm/loaders/api/log.js +2 -2
- package/dist/esm/loaders/api/noticeError.js +2 -2
- package/dist/esm/loaders/api/register-api-types.js +5 -5
- package/dist/esm/loaders/api/register.js +80 -97
- package/dist/tsconfig.tsbuildinfo +1 -1
- package/dist/types/common/config/init-types.d.ts +4 -1
- package/dist/types/common/config/init-types.d.ts.map +1 -1
- package/dist/types/common/config/init.d.ts.map +1 -1
- package/dist/types/common/constants/agent-constants.d.ts +7 -4
- package/dist/types/common/constants/agent-constants.d.ts.map +1 -1
- package/dist/types/common/harvest/harvester.d.ts +2 -2
- package/dist/types/common/harvest/harvester.d.ts.map +1 -1
- package/dist/types/common/util/mfe.d.ts +20 -0
- package/dist/types/common/util/mfe.d.ts.map +1 -0
- package/dist/types/features/generic_events/aggregate/index.d.ts +2 -2
- package/dist/types/features/generic_events/aggregate/index.d.ts.map +1 -1
- package/dist/types/features/generic_events/constants.d.ts +1 -0
- package/dist/types/features/jserrors/aggregate/index.d.ts +3 -3
- package/dist/types/features/jserrors/aggregate/index.d.ts.map +1 -1
- package/dist/types/features/logging/aggregate/index.d.ts +3 -3
- package/dist/types/features/logging/aggregate/index.d.ts.map +1 -1
- package/dist/types/features/logging/shared/utils.d.ts +2 -2
- package/dist/types/features/logging/shared/utils.d.ts.map +1 -1
- package/dist/types/features/page_view_event/aggregate/index.d.ts +2 -4
- package/dist/types/features/page_view_event/aggregate/index.d.ts.map +1 -1
- package/dist/types/features/session_replay/aggregate/index.d.ts +13 -4
- package/dist/types/features/session_replay/aggregate/index.d.ts.map +1 -1
- package/dist/types/features/session_replay/shared/recorder.d.ts +1 -0
- package/dist/types/features/session_replay/shared/recorder.d.ts.map +1 -1
- package/dist/types/features/session_trace/aggregate/index.d.ts.map +1 -1
- package/dist/types/features/soft_navigations/aggregate/index.d.ts.map +1 -1
- package/dist/types/features/utils/aggregate-base.d.ts +13 -5
- package/dist/types/features/utils/aggregate-base.d.ts.map +1 -1
- package/dist/types/loaders/api/addPageAction.d.ts +1 -1
- package/dist/types/loaders/api/addPageAction.d.ts.map +1 -1
- package/dist/types/loaders/api/log.d.ts +1 -1
- package/dist/types/loaders/api/log.d.ts.map +1 -1
- package/dist/types/loaders/api/noticeError.d.ts +1 -1
- package/dist/types/loaders/api/noticeError.d.ts.map +1 -1
- package/dist/types/loaders/api/register-api-types.d.ts +4 -4
- package/dist/types/loaders/api/register-api-types.d.ts.map +1 -1
- package/dist/types/loaders/api/register.d.ts +8 -1
- package/dist/types/loaders/api/register.d.ts.map +1 -1
- package/package.json +1 -1
- package/src/common/config/init-types.js +1 -1
- package/src/common/config/init.js +3 -1
- package/src/common/config/runtime.js +1 -1
- package/src/common/constants/agent-constants.js +10 -0
- package/src/common/drain/drain.js +1 -1
- package/src/common/harvest/harvester.js +27 -32
- package/src/common/util/mfe.js +35 -0
- package/src/features/generic_events/aggregate/index.js +9 -8
- package/src/features/generic_events/constants.js +3 -1
- package/src/features/jserrors/aggregate/index.js +17 -17
- package/src/features/logging/aggregate/index.js +20 -13
- package/src/features/logging/shared/utils.js +3 -3
- package/src/features/page_view_event/aggregate/index.js +3 -28
- package/src/features/session_replay/aggregate/index.js +12 -10
- package/src/features/session_replay/shared/recorder.js +3 -2
- package/src/features/session_trace/aggregate/index.js +0 -2
- package/src/features/soft_navigations/aggregate/index.js +1 -2
- package/src/features/utils/aggregate-base.js +47 -42
- package/src/loaders/api/addPageAction.js +2 -2
- package/src/loaders/api/log.js +2 -2
- package/src/loaders/api/noticeError.js +2 -2
- package/src/loaders/api/register-api-types.js +5 -5
- package/src/loaders/api/register.js +62 -89
- package/dist/cjs/common/util/target.js +0 -34
- package/dist/cjs/features/utils/entity-manager.js +0 -46
- package/dist/cjs/features/utils/event-store-manager.js +0 -174
- package/dist/cjs/loaders/api/register-api.js +0 -165
- package/dist/esm/common/util/target.js +0 -27
- package/dist/esm/features/utils/entity-manager.js +0 -39
- package/dist/esm/features/utils/event-store-manager.js +0 -166
- package/dist/esm/loaders/api/register-api.js +0 -159
- package/dist/types/common/util/target.d.ts +0 -18
- package/dist/types/common/util/target.d.ts.map +0 -1
- package/dist/types/features/utils/entity-manager.d.ts +0 -11
- package/dist/types/features/utils/entity-manager.d.ts.map +0 -1
- package/dist/types/features/utils/event-store-manager.d.ts +0 -85
- package/dist/types/features/utils/event-store-manager.d.ts.map +0 -1
- package/dist/types/loaders/api/register-api.d.ts +0 -14
- package/dist/types/loaders/api/register-api.d.ts.map +0 -1
- package/src/common/util/target.js +0 -27
- package/src/features/utils/entity-manager.js +0 -45
- package/src/features/utils/event-store-manager.js +0 -165
- package/src/loaders/api/register-api.js +0 -152
|
@@ -14,6 +14,16 @@ export class AggregateBase extends FeatureBase {
|
|
|
14
14
|
isRetrying: boolean;
|
|
15
15
|
harvestOpts: {};
|
|
16
16
|
events: any;
|
|
17
|
+
/** @type {Boolean} indicates if the feature supports registered entities and the harvest requirements therein. Also read by getter "harvestEndpointVersion". Controlled by feature flag in pre-release phase. */
|
|
18
|
+
get supportsRegisteredEntities(): boolean;
|
|
19
|
+
/**
|
|
20
|
+
* the endpoint version the feature uses during harvests
|
|
21
|
+
* @type {number}
|
|
22
|
+
* @returns {boolean}
|
|
23
|
+
*/
|
|
24
|
+
get harvestEndpointVersion(): number;
|
|
25
|
+
waitForDrain(): void;
|
|
26
|
+
drained: boolean | undefined;
|
|
17
27
|
/**
|
|
18
28
|
* Evaluates whether a harvest should be made early by estimating the size of the current payload. Currently, this only happens if the event storage is EventBuffer, since that triggers this method directly.
|
|
19
29
|
* If conditions are met, a new harvest will be triggered immediately.
|
|
@@ -30,26 +40,24 @@ export class AggregateBase extends FeatureBase {
|
|
|
30
40
|
* Stages the feature to be drained
|
|
31
41
|
*/
|
|
32
42
|
drain(): void;
|
|
33
|
-
drained: boolean | undefined;
|
|
34
43
|
preHarvestChecks(opts: any): boolean;
|
|
35
44
|
/**
|
|
36
45
|
* Return harvest payload. A "serializer" function can be defined on a derived class to format the payload.
|
|
37
46
|
* @param {Boolean} shouldRetryOnFail - harvester flag to backup payload for retry later if harvest request fails; this should be moved to harvester logic
|
|
38
47
|
* @param {object|undefined} opts - opts passed from the harvester to help form the payload
|
|
39
|
-
* @param {string} opts.
|
|
48
|
+
* @param {string} opts.target - the target app metadata
|
|
40
49
|
* @returns {Array} Final payload tagged with their targeting browser app. The value of `payload` can be undefined if there are no pending events for an app. This should be a minimum length of 1.
|
|
41
50
|
*/
|
|
42
51
|
makeHarvestPayload(shouldRetryOnFail?: boolean, opts?: object | undefined): any[];
|
|
43
52
|
/**
|
|
44
53
|
* Cleanup task after a harvest.
|
|
45
54
|
* @param {object} result - the cbResult object from the harvester's send method
|
|
46
|
-
* @param {object=} result.targetApp - the target app object that was used to point the harvest to the correct app
|
|
47
|
-
* @param {string=} result.targetApp.entityGuid - the entity guid of the target app
|
|
48
55
|
* @param {boolean=} result.sent - whether the harvest was sent successfully
|
|
49
56
|
* @param {boolean=} result.retry - whether the harvest should be retried
|
|
50
57
|
*/
|
|
51
58
|
postHarvestCleanup(result?: {
|
|
52
|
-
|
|
59
|
+
sent?: boolean | undefined;
|
|
60
|
+
retry?: boolean | undefined;
|
|
53
61
|
}): void;
|
|
54
62
|
/**
|
|
55
63
|
* Checks for additional `jsAttributes` items to support backward compatibility with implementations of the agent where
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"aggregate-base.d.ts","sourceRoot":"","sources":["../../../../src/features/utils/aggregate-base.js"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"aggregate-base.d.ts","sourceRoot":"","sources":["../../../../src/features/utils/aggregate-base.js"],"names":[],"mappings":"AAmBA;IACE;;;;OAIG;IACH,sBAHW,MAAM,eACN,MAAM,EAoBhB;IAhBC,iBAAwB;IAIxB,uOAAuO;IACvO,qCAAwC;IACxC,gLAAgL;IAChL,yBAA2B;IAC3B,sFAAsF;IACtF,oBAAuB;IAEvB,gBAAqB;IAqBjB,YAAsE;IAW5E,iNAAiN;IACjN,0CAEC;IAED;;;;OAIG;IACH,8BAHU,MAAM,CAKf;IAED,qBAOC;IAFG,6BAAmB;IAIvB;;;;OAIG;IACH,2BAOC;IAED;;;;OAIG;IACH,yBAHW,MAAM,EAAE,gBAwBlB;IAED;;OAEG;IACH,cAEC;IAED,qCAEC;IAED;;;;;;OAMG;IACH,uDAJW,MAAM,GAAC,SAAS,SAsB1B;IAED;;;;;OAKG;IACH,4BAHG;QAAyB,IAAI,GAArB,OAAO,YAAC;QACS,KAAK,GAAtB,OAAO,YAAC;KAClB,QAKA;IAED;;;OAGG;IACH,6CAsBC;IAED;;;OAGG;IACH,2CAKC;IAHC,gBAA6C;IAK/C;;;;OAIG;IACH,uCAHW,GAAC,UACD,GAAC,QAIX;;CACF;4BApO2B,gBAAgB"}
|
|
@@ -1,3 +1,3 @@
|
|
|
1
1
|
export function setupAddPageActionAPI(agent: any): void;
|
|
2
|
-
export function addPageAction(name: any, attributes: any, agentRef: any,
|
|
2
|
+
export function addPageAction(name: any, attributes: any, agentRef: any, target: any, timestamp?: number): void;
|
|
3
3
|
//# sourceMappingURL=addPageAction.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"addPageAction.d.ts","sourceRoot":"","sources":["../../../../src/loaders/api/addPageAction.js"],"names":[],"mappings":"AAUA,wDAEC;AAED,
|
|
1
|
+
{"version":3,"file":"addPageAction.d.ts","sourceRoot":"","sources":["../../../../src/loaders/api/addPageAction.js"],"names":[],"mappings":"AAUA,wDAEC;AAED,gHAEC"}
|
|
@@ -2,5 +2,5 @@ export function setupLogAPI(agent: any): void;
|
|
|
2
2
|
export function log(message: any, { customAttributes, level }: {
|
|
3
3
|
customAttributes?: {} | undefined;
|
|
4
4
|
level?: string | undefined;
|
|
5
|
-
} | undefined, agentRef: any,
|
|
5
|
+
} | undefined, agentRef: any, target: any, timestamp?: number): void;
|
|
6
6
|
//# sourceMappingURL=log.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"log.d.ts","sourceRoot":"","sources":["../../../../src/loaders/api/log.js"],"names":[],"mappings":"AAWA,8CAEC;AAED
|
|
1
|
+
{"version":3,"file":"log.d.ts","sourceRoot":"","sources":["../../../../src/loaders/api/log.js"],"names":[],"mappings":"AAWA,8CAEC;AAED;;;qEAEC"}
|
|
@@ -1,3 +1,3 @@
|
|
|
1
1
|
export function setupNoticeErrorAPI(agent: any): void;
|
|
2
|
-
export function noticeError(err: any, customAttributes: any, agentRef: any,
|
|
2
|
+
export function noticeError(err: any, customAttributes: any, agentRef: any, target: any, timestamp?: number): void;
|
|
3
3
|
//# sourceMappingURL=noticeError.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"noticeError.d.ts","sourceRoot":"","sources":["../../../../src/loaders/api/noticeError.js"],"names":[],"mappings":"AAUA,sDAEC;AAED,
|
|
1
|
+
{"version":3,"file":"noticeError.d.ts","sourceRoot":"","sources":["../../../../src/loaders/api/noticeError.js"],"names":[],"mappings":"AAUA,sDAEC;AAED,mHAIC"}
|
|
@@ -35,8 +35,8 @@ export type RegisterAPIConstructor = {
|
|
|
35
35
|
* - The options for the registered entity.
|
|
36
36
|
*/
|
|
37
37
|
opts: {
|
|
38
|
-
|
|
39
|
-
|
|
38
|
+
id: string;
|
|
39
|
+
name: string;
|
|
40
40
|
};
|
|
41
41
|
};
|
|
42
42
|
export type RegisterAPIMetadata = {
|
|
@@ -49,8 +49,8 @@ export type RegisterAPIMetadata = {
|
|
|
49
49
|
*/
|
|
50
50
|
target: {
|
|
51
51
|
licenseKey: string;
|
|
52
|
-
|
|
53
|
-
|
|
52
|
+
id: string;
|
|
53
|
+
name: string;
|
|
54
54
|
};
|
|
55
55
|
};
|
|
56
56
|
//# sourceMappingURL=register-api-types.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"register-api-types.d.ts","sourceRoot":"","sources":["../../../../src/loaders/api/register-api-types.js"],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;cAac,mBAAmB;;;;;;UAM9B;QAAwB,
|
|
1
|
+
{"version":3,"file":"register-api-types.d.ts","sourceRoot":"","sources":["../../../../src/loaders/api/register-api-types.js"],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;cAac,mBAAmB;;;;;;UAM9B;QAAwB,EAAE,EAAf,MAAM;QACO,IAAI,EAAjB,MAAM;KACnB;;;;;;sBAIa,MAAM;;;;YAEjB;QAA0B,UAAU,EAAzB,MAAM;QACS,EAAE,EAAjB,MAAM;QACS,IAAI,EAAnB,MAAM;KACnB"}
|
|
@@ -13,8 +13,15 @@ export function setupRegisterAPI(agent: any): void;
|
|
|
13
13
|
* @param {Object} agentRef the reference to the base agent instance
|
|
14
14
|
* @param {Object} handlers the shared handlers to be used by both the base agent's API and the external target's API
|
|
15
15
|
* @param {Object} target the target information to be used by the external target's API to send data to the correct location
|
|
16
|
+
* @param {string} [target.licenseKey] the license key of the target to report data to
|
|
17
|
+
* @param {string} target.id the entity ID of the target to report data to
|
|
18
|
+
* @param {string} target.name the entity name of the target to report data to
|
|
16
19
|
* @returns {RegisterAPI} the api object to be returned from the register api method
|
|
17
20
|
*/
|
|
18
|
-
export function buildRegisterApi(agentRef: Object, target:
|
|
21
|
+
export function buildRegisterApi(agentRef: Object, target: {
|
|
22
|
+
licenseKey?: string | undefined;
|
|
23
|
+
id: string;
|
|
24
|
+
name: string;
|
|
25
|
+
}): RegisterAPI;
|
|
19
26
|
export type RegisterAPI = import("./register-api-types").RegisterAPI;
|
|
20
27
|
//# sourceMappingURL=register.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"register.d.ts","sourceRoot":"","sources":["../../../../src/loaders/api/register.js"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"register.d.ts","sourceRoot":"","sources":["../../../../src/loaders/api/register.js"],"names":[],"mappings":"AAiBA;;GAEG;AAEH;;;;GAIG;AACH,mDAIC;AAED;;;;;;;;;;GAUG;AACH,2CARW,MAAM,UAGd;IAAwB,UAAU;IACX,EAAE,EAAjB,MAAM;IACS,IAAI,EAAnB,MAAM;CACd,GAAU,WAAW,CAmGvB;0BA1HY,OAAO,sBAAsB,EAAE,WAAW"}
|
package/package.json
CHANGED
|
@@ -35,7 +35,7 @@
|
|
|
35
35
|
* @property {Object} [metrics]
|
|
36
36
|
* @property {boolean} [metrics.enabled] - Turn on/off the metrics feature (on by default).
|
|
37
37
|
* @property {boolean} [metrics.autoStart] - If true, the agent will automatically start the metrics feature. Otherwise, it will be in a deferred state until the `start` API method is called.
|
|
38
|
-
* @property {
|
|
38
|
+
* @property {{regex: RegExp | string, replacement: string}[]} [obfuscate] - Array of regexp and corresponding replacement patterns for obfuscating data.
|
|
39
39
|
* @property {Object} [page_action]
|
|
40
40
|
* @property {boolean} [page_action.enabled] - Must be true to allow PageAction events to be captured.
|
|
41
41
|
* @property {Object} [page_view_event]
|
|
@@ -21,6 +21,7 @@ const InitModelFn = () => {
|
|
|
21
21
|
const hiddenState = {
|
|
22
22
|
feature_flags: [],
|
|
23
23
|
experimental: {
|
|
24
|
+
allow_registered_children: false,
|
|
24
25
|
resources: false
|
|
25
26
|
},
|
|
26
27
|
mask_selector: '*',
|
|
@@ -48,7 +49,8 @@ const InitModelFn = () => {
|
|
|
48
49
|
return {
|
|
49
50
|
ajax: { deny_list: undefined, block_internal: true, enabled: true, autoStart: true },
|
|
50
51
|
api: {
|
|
51
|
-
allow_registered_children
|
|
52
|
+
get allow_registered_children () { return hiddenState.feature_flags.includes(FEATURE_FLAGS.REGISTER) || hiddenState.experimental.allow_registered_children },
|
|
53
|
+
set allow_registered_children (val) { hiddenState.experimental.allow_registered_children = val },
|
|
52
54
|
duplicate_registered_data: false
|
|
53
55
|
},
|
|
54
56
|
distributed_tracing: {
|
|
@@ -25,7 +25,6 @@ const RuntimeModel = {
|
|
|
25
25
|
customTransaction: undefined,
|
|
26
26
|
denyList: undefined,
|
|
27
27
|
disabled: false,
|
|
28
|
-
entityManager: undefined,
|
|
29
28
|
harvester: undefined,
|
|
30
29
|
isolatedBacklog: false,
|
|
31
30
|
isRecording: false, // true when actively recording, false when paused or stopped
|
|
@@ -37,6 +36,7 @@ const RuntimeModel = {
|
|
|
37
36
|
releaseIds: {},
|
|
38
37
|
session: undefined,
|
|
39
38
|
timeKeeper: undefined,
|
|
39
|
+
registeredEntities: [],
|
|
40
40
|
/** a proxy is set in agent-session to track jsAttributes changes for harvesting mechanics */
|
|
41
41
|
jsAttributesMetadata: { bytes: 0 },
|
|
42
42
|
get harvestCount () { return ++_harvestCount }
|
|
@@ -2,7 +2,17 @@
|
|
|
2
2
|
* Copyright 2020-2025 New Relic, Inc. All rights reserved.
|
|
3
3
|
* SPDX-License-Identifier: Apache-2.0
|
|
4
4
|
*/
|
|
5
|
+
import { FEATURE_NAMES } from '../../loaders/features/features'
|
|
6
|
+
|
|
5
7
|
export const IDEAL_PAYLOAD_SIZE = 16000
|
|
6
8
|
export const MAX_PAYLOAD_SIZE = 1000000
|
|
7
9
|
export const DEFAULT_KEY = 'NR_CONTAINER_AGENT'
|
|
8
10
|
export const SESSION_ERROR = 'SESSION_ERROR'
|
|
11
|
+
|
|
12
|
+
export const SUPPORTS_REGISTERED_ENTITIES = {
|
|
13
|
+
[FEATURE_NAMES.logging]: true,
|
|
14
|
+
// flip other features here when they are supported by DEM consumers
|
|
15
|
+
[FEATURE_NAMES.genericEvents]: false,
|
|
16
|
+
[FEATURE_NAMES.jserrors]: false,
|
|
17
|
+
[FEATURE_NAMES.ajax]: false
|
|
18
|
+
}
|
|
@@ -123,7 +123,7 @@ function drainGroup (agentIdentifier, group, activateGroup = true) {
|
|
|
123
123
|
|
|
124
124
|
if (!baseEE.isolatedBacklog) delete handlers[group]
|
|
125
125
|
baseEE.backlog[group] = null
|
|
126
|
-
baseEE.emit('drain-' + group, []) //
|
|
126
|
+
baseEE.emit('drain-' + group, []) // Informs the feature that it has drained its backlog of events, this kicks off an immediate harvest to capture any load-driven events that were buffered.
|
|
127
127
|
}
|
|
128
128
|
|
|
129
129
|
/**
|
|
@@ -55,34 +55,30 @@ export class Harvester {
|
|
|
55
55
|
* @returns {boolean} True if 1+ network call was made. Note that this does not mean or guarantee that it was successful (or that all were in the case of more than 1).
|
|
56
56
|
*/
|
|
57
57
|
triggerHarvestFor (aggregateInst, localOpts = {}) {
|
|
58
|
-
|
|
58
|
+
const output = { ranSend: false, payload: undefined, endpointVersion: aggregateInst.harvestEndpointVersion || 1 }
|
|
59
|
+
if (aggregateInst.blocked) return output
|
|
59
60
|
|
|
60
61
|
const submitMethod = getSubmitMethod(localOpts)
|
|
61
|
-
if (!submitMethod) return
|
|
62
|
+
if (!submitMethod) return output
|
|
62
63
|
|
|
63
64
|
const shouldRetryOnFail = !localOpts.isFinalHarvest && submitMethod === xhrMethod // always retry all features harvests except for final
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
localOpts,
|
|
78
|
-
submitMethod,
|
|
79
|
-
cbFinished,
|
|
80
|
-
raw: aggregateInst.harvestOpts.raw,
|
|
81
|
-
featureName: aggregateInst.featureName
|
|
82
|
-
})
|
|
83
|
-
ranSend = true
|
|
65
|
+
output.payload = !localOpts.directSend ? aggregateInst.makeHarvestPayload(shouldRetryOnFail, localOpts) : localOpts.directSend?.payload // features like PVE can define the payload directly, bypassing the makeHarvestPayload logic
|
|
66
|
+
|
|
67
|
+
if (!output.payload) return output
|
|
68
|
+
|
|
69
|
+
send(this.agentRef, {
|
|
70
|
+
endpoint: FEATURE_TO_ENDPOINT[aggregateInst.featureName],
|
|
71
|
+
payload: output.payload,
|
|
72
|
+
localOpts,
|
|
73
|
+
submitMethod,
|
|
74
|
+
cbFinished,
|
|
75
|
+
raw: aggregateInst.harvestOpts.raw,
|
|
76
|
+
featureName: aggregateInst.featureName,
|
|
77
|
+
endpointVersion: output.endpointVersion
|
|
84
78
|
})
|
|
85
|
-
|
|
79
|
+
output.ranSend = true
|
|
80
|
+
|
|
81
|
+
return output
|
|
86
82
|
|
|
87
83
|
/**
|
|
88
84
|
* This is executed immediately after harvest sends the data via XHR, or if there's nothing to send. Note that this excludes on unloading / sendBeacon.
|
|
@@ -112,13 +108,13 @@ const warnings = {}
|
|
|
112
108
|
* @param {NetworkSendSpec} param0 Specification for sending data
|
|
113
109
|
* @returns {boolean} True if a network call was made. Note that this does not mean or guarantee that it was successful.
|
|
114
110
|
*/
|
|
115
|
-
export function send (agentRef, { endpoint,
|
|
111
|
+
export function send (agentRef, { endpoint, payload, localOpts = {}, submitMethod, cbFinished, raw, featureName, endpointVersion = 1 }) {
|
|
116
112
|
if (!agentRef.info.errorBeacon) return false
|
|
117
113
|
|
|
118
114
|
let { body, qs } = cleanPayload(payload)
|
|
119
115
|
|
|
120
116
|
if (Object.keys(body).length === 0 && !localOpts.sendEmptyBody) { // if there's no body to send, just run onfinish stuff and return
|
|
121
|
-
if (cbFinished) cbFinished({ sent: false
|
|
117
|
+
if (cbFinished) cbFinished({ sent: false })
|
|
122
118
|
return false
|
|
123
119
|
}
|
|
124
120
|
|
|
@@ -126,8 +122,8 @@ export function send (agentRef, { endpoint, targetApp, payload, localOpts = {},
|
|
|
126
122
|
const perceivedBeacon = agentRef.init.proxy.beacon || agentRef.info.errorBeacon
|
|
127
123
|
const url = raw
|
|
128
124
|
? `${protocol}://${perceivedBeacon}/${endpoint}`
|
|
129
|
-
: `${protocol}://${perceivedBeacon}${endpoint !== RUM ? '/' + endpoint : ''}
|
|
130
|
-
const baseParams = !raw ? baseQueryString(agentRef, qs, endpoint
|
|
125
|
+
: `${protocol}://${perceivedBeacon}${endpoint !== RUM ? '/' + endpoint : ''}/${endpointVersion}/${agentRef.info.licenseKey}`
|
|
126
|
+
const baseParams = !raw ? baseQueryString(agentRef, qs, endpoint) : ''
|
|
131
127
|
let payloadParams = obj(qs, agentRef.runtime.maxBytes)
|
|
132
128
|
if (baseParams === '' && payloadParams.startsWith('&')) {
|
|
133
129
|
payloadParams = payloadParams.substring(1)
|
|
@@ -159,7 +155,7 @@ export function send (agentRef, { endpoint, targetApp, payload, localOpts = {},
|
|
|
159
155
|
result.addEventListener('loadend', function () {
|
|
160
156
|
// `this` here in block refers to the XHR object in this scope, do not change the anon function to an arrow function
|
|
161
157
|
// status 0 refers to a local error, such as CORS or network failure, or a blocked request by the browser (e.g. adblocker)
|
|
162
|
-
const cbResult = { sent: this.status !== 0, status: this.status, retry: shouldRetry(this.status), fullUrl, xhr: this
|
|
158
|
+
const cbResult = { sent: this.status !== 0, status: this.status, retry: shouldRetry(this.status), fullUrl, xhr: this }
|
|
163
159
|
if (localOpts.needResponse) cbResult.responseText = this.responseText
|
|
164
160
|
cbFinished(cbResult)
|
|
165
161
|
|
|
@@ -169,7 +165,7 @@ export function send (agentRef, { endpoint, targetApp, payload, localOpts = {},
|
|
|
169
165
|
} else if (submitMethod === fetchMethod) {
|
|
170
166
|
result.then(async function (response) {
|
|
171
167
|
const status = response.status
|
|
172
|
-
const cbResult = { sent: true, status, retry: shouldRetry(status), fullUrl, fetchResponse: response
|
|
168
|
+
const cbResult = { sent: true, status, retry: shouldRetry(status), fullUrl, fetchResponse: response }
|
|
173
169
|
if (localOpts.needResponse) cbResult.responseText = await response.text()
|
|
174
170
|
cbFinished(cbResult)
|
|
175
171
|
/** temporary audit of consistency of harvest metadata flags */
|
|
@@ -207,7 +203,6 @@ export function send (agentRef, { endpoint, targetApp, payload, localOpts = {},
|
|
|
207
203
|
data: {
|
|
208
204
|
endpoint,
|
|
209
205
|
headers,
|
|
210
|
-
targetApp,
|
|
211
206
|
payload,
|
|
212
207
|
submitMethod: getSubmitMethodName(),
|
|
213
208
|
raw,
|
|
@@ -264,14 +259,14 @@ function cleanPayload (payload = {}) {
|
|
|
264
259
|
}
|
|
265
260
|
|
|
266
261
|
// The stuff that gets sent every time.
|
|
267
|
-
function baseQueryString (agentRef, qs, endpoint
|
|
262
|
+
function baseQueryString (agentRef, qs, endpoint) {
|
|
268
263
|
const ref = agentRef.runtime.obfuscator.obfuscateString(cleanURL('' + globalScope.location))
|
|
269
264
|
const session = agentRef.runtime.session
|
|
270
265
|
const hr = !!session?.state.sessionReplaySentFirstChunk && session?.state.sessionReplayMode === 1 && endpoint !== JSERRORS
|
|
271
266
|
const ht = !!session?.state.traceHarvestStarted && session?.state.sessionTraceMode === 1 && ![LOGS, BLOBS].includes(endpoint)
|
|
272
267
|
|
|
273
268
|
const qps = [
|
|
274
|
-
'a=' + applicationID,
|
|
269
|
+
'a=' + agentRef.info.applicationID,
|
|
275
270
|
param('sa', (agentRef.info.sa ? '' + agentRef.info.sa : '')),
|
|
276
271
|
param('v', VERSION),
|
|
277
272
|
transactionNameParam(),
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Copyright 2020-2025 New Relic, Inc. All rights reserved.
|
|
3
|
+
* SPDX-License-Identifier: Apache-2.0
|
|
4
|
+
*/
|
|
5
|
+
|
|
6
|
+
/**
|
|
7
|
+
* @param {Object} [target] - the target to be validated
|
|
8
|
+
* @returns {boolean}
|
|
9
|
+
*/
|
|
10
|
+
export function isValidMFETarget (target = {}) {
|
|
11
|
+
return !!(target.id && target.name)
|
|
12
|
+
}
|
|
13
|
+
|
|
14
|
+
/**
|
|
15
|
+
* When given a valid target, returns an object with the MFE payload attributes. Returns an empty object otherwise.
|
|
16
|
+
* @param {Object} [target] the registered target
|
|
17
|
+
* @param {AggregateInstance} [aggregateInstance] the aggregate instance calling the method
|
|
18
|
+
* @returns {{'mfe.id': *, 'mfe.name': String}|{}} returns an empty object if args are not supplied or the aggregate instance is not supporting version 2
|
|
19
|
+
*/
|
|
20
|
+
export function getVersion2Attributes (target, aggregateInstance) {
|
|
21
|
+
if (aggregateInstance?.harvestEndpointVersion !== 2) return {}
|
|
22
|
+
const containerAgentEntityGuid = aggregateInstance.agentRef.runtime.appMetadata.agents[0].entityGuid
|
|
23
|
+
if (!isValidMFETarget(target)) {
|
|
24
|
+
return {
|
|
25
|
+
'entity.guid': containerAgentEntityGuid,
|
|
26
|
+
appId: aggregateInstance.agentRef.info.applicationID
|
|
27
|
+
}
|
|
28
|
+
}
|
|
29
|
+
return {
|
|
30
|
+
'mfe.id': target.id, // these field names may change as the schema is finalized
|
|
31
|
+
'mfe.name': target.name, // these field names may change as the schema is finalized
|
|
32
|
+
eventSource: 'MicroFrontendBrowserAgent', // these field names may change as the schema is finalized
|
|
33
|
+
'parent.id': containerAgentEntityGuid
|
|
34
|
+
}
|
|
35
|
+
}
|
|
@@ -14,6 +14,7 @@ import { applyFnToProps } from '../../../common/util/traverse'
|
|
|
14
14
|
import { UserActionsAggregator } from './user-actions/user-actions-aggregator'
|
|
15
15
|
import { isIFrameWindow } from '../../../common/dom/iframe'
|
|
16
16
|
import { isPureObject } from '../../../common/util/type-check'
|
|
17
|
+
import { getVersion2Attributes } from '../../../common/util/mfe'
|
|
17
18
|
|
|
18
19
|
export class Aggregate extends AggregateBase {
|
|
19
20
|
static featureName = FEATURE_NAME
|
|
@@ -42,8 +43,7 @@ export class Aggregate extends AggregateBase {
|
|
|
42
43
|
}, this.featureName, this.ee)
|
|
43
44
|
|
|
44
45
|
if (agentRef.init.page_action.enabled) {
|
|
45
|
-
registerHandler('api-addPageAction', (timestamp, name, attributes,
|
|
46
|
-
if (!this.agentRef.runtime.entityManager.get(targetEntityGuid)) return warn(56, this.featureName)
|
|
46
|
+
registerHandler('api-addPageAction', (timestamp, name, attributes, target) => {
|
|
47
47
|
this.addEvent({
|
|
48
48
|
...attributes,
|
|
49
49
|
eventType: 'PageAction',
|
|
@@ -55,7 +55,7 @@ export class Aggregate extends AggregateBase {
|
|
|
55
55
|
browserWidth: window.document.documentElement?.clientWidth,
|
|
56
56
|
browserHeight: window.document.documentElement?.clientHeight
|
|
57
57
|
})
|
|
58
|
-
},
|
|
58
|
+
}, target)
|
|
59
59
|
}, this.featureName, this.ee)
|
|
60
60
|
}
|
|
61
61
|
|
|
@@ -242,7 +242,6 @@ export class Aggregate extends AggregateBase {
|
|
|
242
242
|
this.addEvent(event)
|
|
243
243
|
}, this.featureName, this.ee)
|
|
244
244
|
|
|
245
|
-
agentRef.runtime.harvester.triggerHarvestFor(this)
|
|
246
245
|
this.drain()
|
|
247
246
|
})
|
|
248
247
|
}
|
|
@@ -258,10 +257,10 @@ export class Aggregate extends AggregateBase {
|
|
|
258
257
|
* * sessionTraceId: set by the `ptid=` query param
|
|
259
258
|
* * userAgent*: set by the userAgent header
|
|
260
259
|
* @param {object=} obj the event object for storing in the event buffer
|
|
261
|
-
* @param {string=}
|
|
260
|
+
* @param {string=} target the target metadata for the event to scope buffering and harvesting. Defaults to container agent config if undefined
|
|
262
261
|
* @returns void
|
|
263
262
|
*/
|
|
264
|
-
addEvent (obj = {},
|
|
263
|
+
addEvent (obj = {}, target) {
|
|
265
264
|
if (!obj || !Object.keys(obj).length) return
|
|
266
265
|
if (!obj.eventType) {
|
|
267
266
|
warn(44)
|
|
@@ -278,7 +277,9 @@ export class Aggregate extends AggregateBase {
|
|
|
278
277
|
timestamp: Math.floor(this.agentRef.runtime.timeKeeper.correctRelativeTimestamp(now())),
|
|
279
278
|
/** all generic events require pageUrl(s) */
|
|
280
279
|
pageUrl: cleanURL('' + initialLocation),
|
|
281
|
-
currentUrl: cleanURL('' + location)
|
|
280
|
+
currentUrl: cleanURL('' + location),
|
|
281
|
+
/** Specific attributes only supplied if harvesting to endpoint version 2 */
|
|
282
|
+
...(getVersion2Attributes(target, this))
|
|
282
283
|
}
|
|
283
284
|
|
|
284
285
|
const eventAttributes = {
|
|
@@ -290,7 +291,7 @@ export class Aggregate extends AggregateBase {
|
|
|
290
291
|
...obj
|
|
291
292
|
}
|
|
292
293
|
|
|
293
|
-
this.events.add(eventAttributes
|
|
294
|
+
this.events.add(eventAttributes)
|
|
294
295
|
}
|
|
295
296
|
|
|
296
297
|
serializer (eventBuffer) {
|
|
@@ -17,5 +17,7 @@ export const FRUSTRATION_TIMEOUT_MS = 2000
|
|
|
17
17
|
export const RESERVED_EVENT_TYPES = ['PageAction', 'UserAction', 'BrowserPerformance']
|
|
18
18
|
|
|
19
19
|
export const FEATURE_FLAGS = {
|
|
20
|
-
RESOURCES: 'experimental.resources'
|
|
20
|
+
RESOURCES: 'experimental.resources',
|
|
21
|
+
REGISTER: 'register'
|
|
22
|
+
// register.jserrors and register.generic_events are also used, but not referenced directly so no need to represent here
|
|
21
23
|
}
|
|
@@ -19,8 +19,7 @@ import { AggregateBase } from '../../utils/aggregate-base'
|
|
|
19
19
|
import { now } from '../../../common/timing/now'
|
|
20
20
|
import { applyFnToProps } from '../../../common/util/traverse'
|
|
21
21
|
import { evaluateInternalError } from './internal-errors'
|
|
22
|
-
import {
|
|
23
|
-
import { warn } from '../../../common/util/console'
|
|
22
|
+
import { getVersion2Attributes } from '../../../common/util/mfe'
|
|
24
23
|
import { buildCauseString } from './cause-string'
|
|
25
24
|
|
|
26
25
|
/**
|
|
@@ -32,6 +31,8 @@ export class Aggregate extends AggregateBase {
|
|
|
32
31
|
constructor (agentRef) {
|
|
33
32
|
super(agentRef, FEATURE_NAME)
|
|
34
33
|
|
|
34
|
+
/** set up agg-level behaviors specific to this feature */
|
|
35
|
+
this.harvestOpts.aggregatorTypes = ['err', 'ierr', 'xhr'] // the types in EventAggregator this feature cares about
|
|
35
36
|
this.stackReported = {}
|
|
36
37
|
this.observedAt = {}
|
|
37
38
|
this.pageviewReported = {}
|
|
@@ -46,8 +47,6 @@ export class Aggregate extends AggregateBase {
|
|
|
46
47
|
register('softNavFlush', (interactionId, wasFinished, softNavAttrs, interactionEndTime) =>
|
|
47
48
|
this.onSoftNavNotification(interactionId, wasFinished, softNavAttrs, interactionEndTime), this.featureName, this.ee) // when an ixn is done or cancelled
|
|
48
49
|
|
|
49
|
-
this.harvestOpts.aggregatorTypes = ['err', 'ierr', 'xhr'] // the types in EventAggregator this feature cares about
|
|
50
|
-
|
|
51
50
|
// 0 == off, 1 == on
|
|
52
51
|
this.waitForFlags(['err']).then(([errFlag]) => {
|
|
53
52
|
if (errFlag) {
|
|
@@ -113,10 +112,8 @@ export class Aggregate extends AggregateBase {
|
|
|
113
112
|
* @param {object=} target the target to buffer and harvest to, if undefined the default configuration target is used
|
|
114
113
|
* @returns
|
|
115
114
|
*/
|
|
116
|
-
storeError (err, time, internal, customAttributes, hasReplay, swallowReason,
|
|
115
|
+
storeError (err, time, internal, customAttributes, hasReplay, swallowReason, target) {
|
|
117
116
|
if (!err) return
|
|
118
|
-
const target = this.agentRef.runtime.entityManager.get(targetEntityGuid)
|
|
119
|
-
if (!target) return warn(56, this.featureName)
|
|
120
117
|
// are we in an interaction
|
|
121
118
|
time = time || now()
|
|
122
119
|
let filterOutput
|
|
@@ -155,7 +152,7 @@ export class Aggregate extends AggregateBase {
|
|
|
155
152
|
if (filterOutput?.group) params.errorGroup = filterOutput.group
|
|
156
153
|
|
|
157
154
|
// Should only decorate "hasReplay" for the container agent, so check if the target matches the config
|
|
158
|
-
if (hasReplay &&
|
|
155
|
+
if (hasReplay && !target) params.hasReplay = hasReplay
|
|
159
156
|
/**
|
|
160
157
|
* The bucketHash is different from the params.stackHash because the params.stackHash is based on the canonicalized
|
|
161
158
|
* stack trace and is used downstream in NR1 to attempt to group the same errors across different browsers. However,
|
|
@@ -191,7 +188,7 @@ export class Aggregate extends AggregateBase {
|
|
|
191
188
|
|
|
192
189
|
// Trace sends the error in its payload, and both trace & replay simply listens for any error to occur.
|
|
193
190
|
const jsErrorEvent = [type, bucketHash, params, newMetrics, customAttributes]
|
|
194
|
-
if (this.shouldAllowMainAgentToCapture(
|
|
191
|
+
if (this.shouldAllowMainAgentToCapture(target)) handle('trace-jserror', jsErrorEvent, undefined, FEATURE_NAMES.sessionTrace, this.ee)
|
|
195
192
|
// still send EE events for other features such as above, but stop this one from aggregating internal data
|
|
196
193
|
if (this.blocked) return
|
|
197
194
|
|
|
@@ -200,7 +197,7 @@ export class Aggregate extends AggregateBase {
|
|
|
200
197
|
params._interactionNodeId = err.__newrelic[this.agentIdentifier].interactionNodeId
|
|
201
198
|
}
|
|
202
199
|
|
|
203
|
-
if (this.shouldAllowMainAgentToCapture(
|
|
200
|
+
if (this.shouldAllowMainAgentToCapture(target)) {
|
|
204
201
|
const softNavInUse = Boolean(this.agentRef.features?.[FEATURE_NAMES.softNav])
|
|
205
202
|
// Note: the following are subject to potential race cond wherein if the other feature aren't fully initialized, it'll be treated as there being no associated interaction.
|
|
206
203
|
// They each will also tack on their respective properties to the params object as part of the decision flow.
|
|
@@ -221,12 +218,15 @@ export class Aggregate extends AggregateBase {
|
|
|
221
218
|
}
|
|
222
219
|
|
|
223
220
|
// always add directly if scoped to a sub-entity, the other pathways above will be deterministic if the main agent should procede
|
|
224
|
-
if (
|
|
221
|
+
if (target) this.#storeJserrorForHarvest([...jsErrorEvent, target], false, params._softNavAttributes)
|
|
225
222
|
}
|
|
226
223
|
|
|
227
224
|
#storeJserrorForHarvest (errorInfoArr, softNavOccurredFinished, softNavCustomAttrs = {}) {
|
|
228
|
-
let [type, bucketHash, params, newMetrics, localAttrs,
|
|
229
|
-
const allCustomAttrs = {
|
|
225
|
+
let [type, bucketHash, params, newMetrics, localAttrs, target] = errorInfoArr
|
|
226
|
+
const allCustomAttrs = {
|
|
227
|
+
/** MFE specific attributes if in "multiple" mode (ie consumer version 2) */
|
|
228
|
+
...getVersion2Attributes(target, this)
|
|
229
|
+
}
|
|
230
230
|
|
|
231
231
|
if (softNavOccurredFinished) {
|
|
232
232
|
Object.entries(softNavCustomAttrs).forEach(([k, v]) => setCustom(k, v)) // when an ixn finishes, it'll include stuff in jsAttributes + attrs specific to the ixn
|
|
@@ -243,7 +243,7 @@ export class Aggregate extends AggregateBase {
|
|
|
243
243
|
const jsAttributesHash = stringHashCode(stringify(allCustomAttrs))
|
|
244
244
|
const aggregateHash = bucketHash + ':' + jsAttributesHash
|
|
245
245
|
|
|
246
|
-
this.events.add([type, aggregateHash, params, newMetrics, allCustomAttrs]
|
|
246
|
+
this.events.add([type, aggregateHash, params, newMetrics, allCustomAttrs])
|
|
247
247
|
|
|
248
248
|
function setCustom (key, val) {
|
|
249
249
|
allCustomAttrs[key] = (val && typeof val === 'object' ? stringify(val) : val)
|
|
@@ -253,11 +253,11 @@ export class Aggregate extends AggregateBase {
|
|
|
253
253
|
/**
|
|
254
254
|
* If the event lacks an entityGuid (the default behavior), the main agent should capture the data. If the data is assigned to a sub-entity target
|
|
255
255
|
* the main agent should not capture events unless it is configured to do so.
|
|
256
|
-
* @param {string}
|
|
256
|
+
* @param {string} target - the context object for the event
|
|
257
257
|
* @returns {boolean} - whether the main agent should capture the event to its internal target
|
|
258
258
|
*/
|
|
259
|
-
shouldAllowMainAgentToCapture (
|
|
260
|
-
return (!
|
|
259
|
+
shouldAllowMainAgentToCapture (target) {
|
|
260
|
+
return (!target || this.agentRef.init.api.duplicate_registered_data)
|
|
261
261
|
}
|
|
262
262
|
|
|
263
263
|
// TO-DO: Remove this function when old spa is taken out. #storeJserrorForHarvest handles the work with the softnav feature.
|