@v-tilt/browser 1.0.10 → 1.0.11
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/array.js +1 -1
- package/dist/array.js.map +1 -1
- package/dist/array.no-external.js +1 -1
- package/dist/array.no-external.js.map +1 -1
- package/dist/constants.d.ts +1 -0
- package/dist/main.js +1 -1
- package/dist/main.js.map +1 -1
- package/dist/module.d.ts +2 -1
- package/dist/module.js +1 -1
- package/dist/module.js.map +1 -1
- package/dist/module.no-external.d.ts +2 -1
- package/dist/module.no-external.js +1 -1
- package/dist/module.no-external.js.map +1 -1
- package/dist/user-manager.d.ts +21 -0
- package/dist/utils/event-utils.d.ts +35 -17
- package/dist/utils/index.d.ts +21 -0
- package/dist/utils/request-utils.d.ts +17 -0
- package/dist/vtilt.d.ts +2 -1
- package/lib/constants.d.ts +1 -0
- package/lib/constants.js +2 -1
- package/lib/user-manager.d.ts +21 -0
- package/lib/user-manager.js +66 -0
- package/lib/utils/event-utils.d.ts +35 -17
- package/lib/utils/event-utils.js +245 -122
- package/lib/utils/index.d.ts +21 -0
- package/lib/utils/index.js +58 -0
- package/lib/utils/request-utils.d.ts +17 -0
- package/lib/utils/request-utils.js +78 -0
- package/lib/vtilt.d.ts +2 -1
- package/lib/vtilt.js +24 -2
- package/package.json +61 -61
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Request utilities
|
|
3
|
+
* Functions for parsing URLs, query parameters, and masking sensitive data
|
|
4
|
+
*/
|
|
5
|
+
/**
|
|
6
|
+
* Convert string URL to HTMLAnchorElement for parsing
|
|
7
|
+
* IE11 doesn't support `new URL`, so we use anchor element
|
|
8
|
+
*/
|
|
9
|
+
export declare function convertToURL(url: string): HTMLAnchorElement | null;
|
|
10
|
+
/**
|
|
11
|
+
* Get query parameter from URL
|
|
12
|
+
*/
|
|
13
|
+
export declare function getQueryParam(url: string, param: string): string;
|
|
14
|
+
/**
|
|
15
|
+
* Mask query parameters in URL
|
|
16
|
+
*/
|
|
17
|
+
export declare function maskQueryParams<T extends string | undefined>(url: T, maskedParams: string[] | undefined, mask: string): T extends string ? string : undefined;
|
package/dist/vtilt.d.ts
CHANGED
|
@@ -86,7 +86,8 @@ export declare class VTilt {
|
|
|
86
86
|
/**
|
|
87
87
|
* Capture an event
|
|
88
88
|
* Automatically adds common properties to all events
|
|
89
|
-
* ($current_url, $host, $pathname, $referrer, $referring_domain, $
|
|
89
|
+
* ($current_url, $host, $pathname, $referrer, $referring_domain, $browser, $os, $device, $timezone, etc.)
|
|
90
|
+
* Only properties in EVENT_TO_PERSON_PROPERTIES are copied to person properties
|
|
90
91
|
* Also adds title property for $pageview events only
|
|
91
92
|
*
|
|
92
93
|
* @param name - Event name
|
package/lib/constants.d.ts
CHANGED
|
@@ -7,5 +7,6 @@ export declare const DISTINCT_ID_KEY = "vt_distinct_id";
|
|
|
7
7
|
export declare const DEVICE_ID_KEY = "vt_device_id";
|
|
8
8
|
export declare const USER_PROPERTIES_KEY = "vt_user_properties";
|
|
9
9
|
export declare const USER_STATE_KEY = "vt_user_state";
|
|
10
|
+
export declare const INITIAL_PERSON_INFO = "$initial_person_info";
|
|
10
11
|
export declare const STORAGE_METHODS: StorageMethods;
|
|
11
12
|
export declare const TIMEZONES: Record<string, string>;
|
package/lib/constants.js
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
-
exports.TIMEZONES = exports.STORAGE_METHODS = exports.USER_STATE_KEY = exports.USER_PROPERTIES_KEY = exports.DEVICE_ID_KEY = exports.DISTINCT_ID_KEY = exports.ANONYMOUS_ID_KEY = exports.PRIMARY_WINDOW_EXISTS_KEY = exports.WINDOW_ID_KEY = exports.STORAGE_KEY = void 0;
|
|
3
|
+
exports.TIMEZONES = exports.STORAGE_METHODS = exports.INITIAL_PERSON_INFO = exports.USER_STATE_KEY = exports.USER_PROPERTIES_KEY = exports.DEVICE_ID_KEY = exports.DISTINCT_ID_KEY = exports.ANONYMOUS_ID_KEY = exports.PRIMARY_WINDOW_EXISTS_KEY = exports.WINDOW_ID_KEY = exports.STORAGE_KEY = void 0;
|
|
4
4
|
exports.STORAGE_KEY = "vt_session_id";
|
|
5
5
|
exports.WINDOW_ID_KEY = "vt_window_id";
|
|
6
6
|
exports.PRIMARY_WINDOW_EXISTS_KEY = "vt_primary_window_exists";
|
|
@@ -9,6 +9,7 @@ exports.DISTINCT_ID_KEY = "vt_distinct_id";
|
|
|
9
9
|
exports.DEVICE_ID_KEY = "vt_device_id";
|
|
10
10
|
exports.USER_PROPERTIES_KEY = "vt_user_properties";
|
|
11
11
|
exports.USER_STATE_KEY = "vt_user_state";
|
|
12
|
+
exports.INITIAL_PERSON_INFO = "$initial_person_info";
|
|
12
13
|
exports.STORAGE_METHODS = {
|
|
13
14
|
cookie: "cookie",
|
|
14
15
|
localStorage: "localStorage",
|
package/lib/user-manager.d.ts
CHANGED
|
@@ -159,4 +159,25 @@ export declare class UserManager {
|
|
|
159
159
|
* Remove cookie value
|
|
160
160
|
*/
|
|
161
161
|
private removeCookieValue;
|
|
162
|
+
/**
|
|
163
|
+
* Register a value once (only if not already set)
|
|
164
|
+
* Stores properties in localStorage only if they don't already exist
|
|
165
|
+
*/
|
|
166
|
+
private register_once;
|
|
167
|
+
/**
|
|
168
|
+
* Set initial person info
|
|
169
|
+
* Stores referrer and URL info on first visit for generating $initial_* properties
|
|
170
|
+
*/
|
|
171
|
+
set_initial_person_info(maskPersonalDataProperties?: boolean, customPersonalDataProperties?: string[]): void;
|
|
172
|
+
/**
|
|
173
|
+
* Get initial props
|
|
174
|
+
* Generates $initial_* properties from stored initial person info
|
|
175
|
+
* These are sent with events as $set_once to preserve first values
|
|
176
|
+
*/
|
|
177
|
+
get_initial_props(): Record<string, any>;
|
|
178
|
+
/**
|
|
179
|
+
* Update referrer info
|
|
180
|
+
* Stores current referrer information if not already stored
|
|
181
|
+
*/
|
|
182
|
+
update_referrer_info(): void;
|
|
162
183
|
}
|
package/lib/user-manager.js
CHANGED
|
@@ -3,6 +3,7 @@ Object.defineProperty(exports, "__esModule", { value: true });
|
|
|
3
3
|
exports.UserManager = void 0;
|
|
4
4
|
const constants_1 = require("./constants");
|
|
5
5
|
const utils_1 = require("./utils");
|
|
6
|
+
const event_utils_1 = require("./utils/event-utils");
|
|
6
7
|
class UserManager {
|
|
7
8
|
constructor(storageMethod = "localStorage", domain) {
|
|
8
9
|
this._cachedPersonProperties = null; // Cache for deduplication
|
|
@@ -570,5 +571,70 @@ class UserManager {
|
|
|
570
571
|
}
|
|
571
572
|
document.cookie = cookieValue;
|
|
572
573
|
}
|
|
574
|
+
/**
|
|
575
|
+
* Register a value once (only if not already set)
|
|
576
|
+
* Stores properties in localStorage only if they don't already exist
|
|
577
|
+
*/
|
|
578
|
+
register_once(props, defaultValues) {
|
|
579
|
+
const stored = this.getStoredUserProperties();
|
|
580
|
+
let changed = false;
|
|
581
|
+
for (const key in props) {
|
|
582
|
+
if (Object.prototype.hasOwnProperty.call(props, key)) {
|
|
583
|
+
if (!(key in stored)) {
|
|
584
|
+
stored[key] = props[key];
|
|
585
|
+
changed = true;
|
|
586
|
+
}
|
|
587
|
+
}
|
|
588
|
+
}
|
|
589
|
+
if (defaultValues) {
|
|
590
|
+
for (const key in defaultValues) {
|
|
591
|
+
if (Object.prototype.hasOwnProperty.call(defaultValues, key)) {
|
|
592
|
+
if (!(key in stored)) {
|
|
593
|
+
stored[key] = defaultValues[key];
|
|
594
|
+
changed = true;
|
|
595
|
+
}
|
|
596
|
+
}
|
|
597
|
+
}
|
|
598
|
+
}
|
|
599
|
+
if (changed) {
|
|
600
|
+
this.setStoredUserProperties(stored);
|
|
601
|
+
}
|
|
602
|
+
}
|
|
603
|
+
/**
|
|
604
|
+
* Set initial person info
|
|
605
|
+
* Stores referrer and URL info on first visit for generating $initial_* properties
|
|
606
|
+
*/
|
|
607
|
+
set_initial_person_info(maskPersonalDataProperties, customPersonalDataProperties) {
|
|
608
|
+
const stored = this.getStoredUserProperties();
|
|
609
|
+
// Check if already set (backwards compatibility check)
|
|
610
|
+
if (stored[constants_1.INITIAL_PERSON_INFO]) {
|
|
611
|
+
return;
|
|
612
|
+
}
|
|
613
|
+
const personInfo = (0, event_utils_1.getPersonInfo)(maskPersonalDataProperties, customPersonalDataProperties);
|
|
614
|
+
this.register_once({
|
|
615
|
+
[constants_1.INITIAL_PERSON_INFO]: personInfo,
|
|
616
|
+
}, undefined);
|
|
617
|
+
}
|
|
618
|
+
/**
|
|
619
|
+
* Get initial props
|
|
620
|
+
* Generates $initial_* properties from stored initial person info
|
|
621
|
+
* These are sent with events as $set_once to preserve first values
|
|
622
|
+
*/
|
|
623
|
+
get_initial_props() {
|
|
624
|
+
const stored = this.getStoredUserProperties();
|
|
625
|
+
const initialPersonInfo = stored[constants_1.INITIAL_PERSON_INFO];
|
|
626
|
+
if (!initialPersonInfo) {
|
|
627
|
+
return {};
|
|
628
|
+
}
|
|
629
|
+
return (0, event_utils_1.getInitialPersonPropsFromInfo)(initialPersonInfo);
|
|
630
|
+
}
|
|
631
|
+
/**
|
|
632
|
+
* Update referrer info
|
|
633
|
+
* Stores current referrer information if not already stored
|
|
634
|
+
*/
|
|
635
|
+
update_referrer_info() {
|
|
636
|
+
const referrerInfo = (0, event_utils_1.getReferrerInfo)();
|
|
637
|
+
this.register_once(referrerInfo, undefined);
|
|
638
|
+
}
|
|
573
639
|
}
|
|
574
640
|
exports.UserManager = UserManager;
|
|
@@ -1,34 +1,52 @@
|
|
|
1
1
|
/**
|
|
2
|
-
*
|
|
3
|
-
*
|
|
2
|
+
* Event utilities
|
|
3
|
+
* Functions for extracting event properties, campaign parameters, and person info
|
|
4
4
|
*/
|
|
5
|
-
export declare
|
|
5
|
+
export declare const PERSONAL_DATA_CAMPAIGN_PARAMS: string[];
|
|
6
|
+
export declare const CAMPAIGN_PARAMS: string[];
|
|
7
|
+
export declare const EVENT_TO_PERSON_PROPERTIES: string[];
|
|
8
|
+
export declare const MASKED = "<masked>";
|
|
9
|
+
export declare const COOKIE_CAMPAIGN_PARAMS: string[];
|
|
6
10
|
/**
|
|
7
|
-
* Get
|
|
8
|
-
*
|
|
11
|
+
* Get campaign parameters from URL
|
|
12
|
+
* Extracts UTM and other campaign tracking parameters from current page URL
|
|
13
|
+
* Masks personal data parameters if configured
|
|
9
14
|
*/
|
|
15
|
+
export declare function getCampaignParams(customTrackedParams?: string[], maskPersonalDataProperties?: boolean, customPersonalDataProperties?: string[] | undefined): Record<string, string>;
|
|
16
|
+
export declare function getSearchInfo(): Record<string, any>;
|
|
17
|
+
export declare function getBrowserLanguage(): string | undefined;
|
|
10
18
|
export declare function getBrowserLanguagePrefix(): string | undefined;
|
|
19
|
+
export declare function getReferrer(): string;
|
|
20
|
+
export declare function getReferringDomain(): string;
|
|
11
21
|
/**
|
|
12
|
-
* Get referrer
|
|
13
|
-
* Returns
|
|
22
|
+
* Get referrer information
|
|
23
|
+
* Returns current referrer and referring domain
|
|
14
24
|
*/
|
|
15
|
-
export declare function
|
|
25
|
+
export declare function getReferrerInfo(): Record<string, any>;
|
|
16
26
|
/**
|
|
17
|
-
* Get
|
|
18
|
-
*
|
|
27
|
+
* Get person info for initial storage
|
|
28
|
+
* Extracts referrer and URL info, masks personal data if configured
|
|
29
|
+
* Returns compact format (r: referrer, u: url) for storage efficiency
|
|
19
30
|
*/
|
|
20
|
-
export declare function
|
|
31
|
+
export declare function getPersonInfo(maskPersonalDataProperties?: boolean, customPersonalDataProperties?: string[]): {
|
|
32
|
+
r: string;
|
|
33
|
+
u: string | undefined;
|
|
34
|
+
};
|
|
21
35
|
/**
|
|
22
|
-
*
|
|
23
|
-
*
|
|
36
|
+
* Convert person info to person properties
|
|
37
|
+
* Extracts referrer, URL, campaign params, and search info from stored person info
|
|
24
38
|
*/
|
|
25
|
-
export declare function
|
|
39
|
+
export declare function getPersonPropsFromInfo(info: Record<string, any>): Record<string, any>;
|
|
26
40
|
/**
|
|
27
|
-
*
|
|
28
|
-
*
|
|
41
|
+
* Convert person info to initial person properties
|
|
42
|
+
* Generates $initial_* properties from person info (preserves first values)
|
|
29
43
|
*/
|
|
44
|
+
export declare function getInitialPersonPropsFromInfo(info: Record<string, any>): Record<string, any>;
|
|
45
|
+
export declare function getTimezone(): string | undefined;
|
|
30
46
|
export declare function getTimezoneOffset(): number | undefined;
|
|
31
47
|
/**
|
|
32
48
|
* Get event properties that should be added to all events
|
|
49
|
+
* Returns all event context properties (browser, device, URL, etc.) plus event metadata
|
|
50
|
+
* Note: Only properties in EVENT_TO_PERSON_PROPERTIES are copied to person properties
|
|
33
51
|
*/
|
|
34
|
-
export declare function getEventProperties(): Record<string, any>;
|
|
52
|
+
export declare function getEventProperties(maskPersonalDataProperties?: boolean, customPersonalDataProperties?: string[]): Record<string, any>;
|
package/lib/utils/event-utils.js
CHANGED
|
@@ -1,63 +1,248 @@
|
|
|
1
1
|
"use strict";
|
|
2
|
+
/**
|
|
3
|
+
* Event utilities
|
|
4
|
+
* Functions for extracting event properties, campaign parameters, and person info
|
|
5
|
+
*/
|
|
2
6
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
7
|
+
exports.COOKIE_CAMPAIGN_PARAMS = exports.MASKED = exports.EVENT_TO_PERSON_PROPERTIES = exports.CAMPAIGN_PARAMS = exports.PERSONAL_DATA_CAMPAIGN_PARAMS = void 0;
|
|
8
|
+
exports.getCampaignParams = getCampaignParams;
|
|
9
|
+
exports.getSearchInfo = getSearchInfo;
|
|
3
10
|
exports.getBrowserLanguage = getBrowserLanguage;
|
|
4
11
|
exports.getBrowserLanguagePrefix = getBrowserLanguagePrefix;
|
|
5
12
|
exports.getReferrer = getReferrer;
|
|
6
13
|
exports.getReferringDomain = getReferringDomain;
|
|
14
|
+
exports.getReferrerInfo = getReferrerInfo;
|
|
15
|
+
exports.getPersonInfo = getPersonInfo;
|
|
16
|
+
exports.getPersonPropsFromInfo = getPersonPropsFromInfo;
|
|
17
|
+
exports.getInitialPersonPropsFromInfo = getInitialPersonPropsFromInfo;
|
|
7
18
|
exports.getTimezone = getTimezone;
|
|
8
19
|
exports.getTimezoneOffset = getTimezoneOffset;
|
|
9
20
|
exports.getEventProperties = getEventProperties;
|
|
21
|
+
const request_utils_1 = require("./request-utils");
|
|
22
|
+
const index_1 = require("./index");
|
|
23
|
+
const index_2 = require("./index");
|
|
10
24
|
const globals_1 = require("./globals");
|
|
11
25
|
const user_agent_utils_1 = require("./user-agent-utils");
|
|
26
|
+
const URL_REGEX_PREFIX = 'https?://(.*)';
|
|
12
27
|
// Library version - should match package.json version
|
|
13
|
-
const LIB_VERSION =
|
|
28
|
+
const LIB_VERSION = '1.0.7'; // TODO: Auto-import from package.json
|
|
29
|
+
// Campaign parameters that could be considered personal data (e.g., GDPR)
|
|
30
|
+
// These can be masked in URLs and properties before being sent
|
|
31
|
+
exports.PERSONAL_DATA_CAMPAIGN_PARAMS = [
|
|
32
|
+
'gclid', // google ads
|
|
33
|
+
'gclsrc', // google ads 360
|
|
34
|
+
'dclid', // google display ads
|
|
35
|
+
'gbraid', // google ads, web to app
|
|
36
|
+
'wbraid', // google ads, app to web
|
|
37
|
+
'fbclid', // facebook
|
|
38
|
+
'msclkid', // microsoft
|
|
39
|
+
'twclid', // twitter
|
|
40
|
+
'li_fat_id', // linkedin
|
|
41
|
+
'igshid', // instagram
|
|
42
|
+
'ttclid', // tiktok
|
|
43
|
+
'rdt_cid', // reddit
|
|
44
|
+
'epik', // pinterest
|
|
45
|
+
'qclid', // quora
|
|
46
|
+
'sccid', // snapchat
|
|
47
|
+
'irclid', // impact
|
|
48
|
+
'_kx', // klaviyo
|
|
49
|
+
];
|
|
50
|
+
exports.CAMPAIGN_PARAMS = (0, index_2.extendArray)([
|
|
51
|
+
'utm_source',
|
|
52
|
+
'utm_medium',
|
|
53
|
+
'utm_campaign',
|
|
54
|
+
'utm_content',
|
|
55
|
+
'utm_term',
|
|
56
|
+
'gad_source', // google ads source
|
|
57
|
+
'mc_cid', // mailchimp campaign id
|
|
58
|
+
], exports.PERSONAL_DATA_CAMPAIGN_PARAMS);
|
|
59
|
+
// Properties that should be automatically copied from events to person properties
|
|
60
|
+
exports.EVENT_TO_PERSON_PROPERTIES = [
|
|
61
|
+
// Mobile app properties
|
|
62
|
+
'$app_build',
|
|
63
|
+
'$app_name',
|
|
64
|
+
'$app_namespace',
|
|
65
|
+
'$app_version',
|
|
66
|
+
// Web browser properties
|
|
67
|
+
'$browser',
|
|
68
|
+
'$browser_version',
|
|
69
|
+
'$device_type',
|
|
70
|
+
'$current_url',
|
|
71
|
+
'$pathname',
|
|
72
|
+
'$os',
|
|
73
|
+
'$os_name', // Special case: treated as alias of $os
|
|
74
|
+
'$os_version',
|
|
75
|
+
'$referring_domain',
|
|
76
|
+
'$referrer',
|
|
77
|
+
'$screen_height',
|
|
78
|
+
'$screen_width',
|
|
79
|
+
'$viewport_height',
|
|
80
|
+
'$viewport_width',
|
|
81
|
+
'$raw_user_agent',
|
|
82
|
+
];
|
|
83
|
+
exports.MASKED = '<masked>';
|
|
84
|
+
// Campaign params that can be read from cookies (currently not implemented)
|
|
85
|
+
exports.COOKIE_CAMPAIGN_PARAMS = [
|
|
86
|
+
'li_fat_id', // linkedin
|
|
87
|
+
];
|
|
14
88
|
/**
|
|
15
|
-
* Get
|
|
16
|
-
*
|
|
89
|
+
* Get campaign parameters from URL
|
|
90
|
+
* Extracts UTM and other campaign tracking parameters from current page URL
|
|
91
|
+
* Masks personal data parameters if configured
|
|
17
92
|
*/
|
|
93
|
+
function getCampaignParams(customTrackedParams, maskPersonalDataProperties, customPersonalDataProperties) {
|
|
94
|
+
if (!globals_1.document) {
|
|
95
|
+
return {};
|
|
96
|
+
}
|
|
97
|
+
const paramsToMask = maskPersonalDataProperties
|
|
98
|
+
? (0, index_2.extendArray)([], exports.PERSONAL_DATA_CAMPAIGN_PARAMS, customPersonalDataProperties || [])
|
|
99
|
+
: [];
|
|
100
|
+
// Initially get campaign params from the URL
|
|
101
|
+
const urlCampaignParams = _getCampaignParamsFromUrl((0, request_utils_1.maskQueryParams)(globals_1.document.URL, paramsToMask, exports.MASKED), customTrackedParams);
|
|
102
|
+
// But we can also get some of them from the cookie store
|
|
103
|
+
// For now, we'll skip cookie-based campaign params (would need cookie store implementation)
|
|
104
|
+
const cookieCampaignParams = {};
|
|
105
|
+
// Prefer the values found in the urlCampaignParams if possible
|
|
106
|
+
// `extend` will override the values if found in the second argument
|
|
107
|
+
return (0, index_2.extend)(cookieCampaignParams, urlCampaignParams);
|
|
108
|
+
}
|
|
109
|
+
function _getCampaignParamsFromUrl(url, customParams) {
|
|
110
|
+
const campaign_keywords = exports.CAMPAIGN_PARAMS.concat(customParams || []);
|
|
111
|
+
const params = {};
|
|
112
|
+
(0, index_2.each)(campaign_keywords, function (kwkey) {
|
|
113
|
+
const kw = (0, request_utils_1.getQueryParam)(url, kwkey);
|
|
114
|
+
params[kwkey] = kw ? kw : null;
|
|
115
|
+
});
|
|
116
|
+
return params;
|
|
117
|
+
}
|
|
118
|
+
function _getSearchEngine(referrer) {
|
|
119
|
+
if (!referrer) {
|
|
120
|
+
return null;
|
|
121
|
+
}
|
|
122
|
+
else {
|
|
123
|
+
if (referrer.search(URL_REGEX_PREFIX + 'google.([^/?]*)') === 0) {
|
|
124
|
+
return 'google';
|
|
125
|
+
}
|
|
126
|
+
else if (referrer.search(URL_REGEX_PREFIX + 'bing.com') === 0) {
|
|
127
|
+
return 'bing';
|
|
128
|
+
}
|
|
129
|
+
else if (referrer.search(URL_REGEX_PREFIX + 'yahoo.com') === 0) {
|
|
130
|
+
return 'yahoo';
|
|
131
|
+
}
|
|
132
|
+
else if (referrer.search(URL_REGEX_PREFIX + 'duckduckgo.com') === 0) {
|
|
133
|
+
return 'duckduckgo';
|
|
134
|
+
}
|
|
135
|
+
else {
|
|
136
|
+
return null;
|
|
137
|
+
}
|
|
138
|
+
}
|
|
139
|
+
}
|
|
140
|
+
function _getSearchInfoFromReferrer(referrer) {
|
|
141
|
+
const search = _getSearchEngine(referrer);
|
|
142
|
+
const param = search != 'yahoo' ? 'q' : 'p';
|
|
143
|
+
const ret = {};
|
|
144
|
+
if (!(0, index_1.isNull)(search)) {
|
|
145
|
+
ret['$search_engine'] = search;
|
|
146
|
+
const keyword = globals_1.document ? (0, request_utils_1.getQueryParam)(globals_1.document.referrer, param) : '';
|
|
147
|
+
if (keyword.length) {
|
|
148
|
+
ret['ph_keyword'] = keyword;
|
|
149
|
+
}
|
|
150
|
+
}
|
|
151
|
+
return ret;
|
|
152
|
+
}
|
|
153
|
+
function getSearchInfo() {
|
|
154
|
+
const referrer = globals_1.document === null || globals_1.document === void 0 ? void 0 : globals_1.document.referrer;
|
|
155
|
+
if (!referrer) {
|
|
156
|
+
return {};
|
|
157
|
+
}
|
|
158
|
+
return _getSearchInfoFromReferrer(referrer);
|
|
159
|
+
}
|
|
18
160
|
function getBrowserLanguage() {
|
|
19
|
-
if (typeof
|
|
161
|
+
if (typeof navigator === 'undefined') {
|
|
20
162
|
return undefined;
|
|
21
163
|
}
|
|
22
|
-
return (
|
|
23
|
-
|
|
164
|
+
return (navigator.language || // Any modern browser
|
|
165
|
+
navigator.userLanguage // IE11
|
|
24
166
|
);
|
|
25
167
|
}
|
|
26
|
-
/**
|
|
27
|
-
* Get browser language prefix
|
|
28
|
-
* Returns the language code without region (e.g., "en" from "en-US")
|
|
29
|
-
*/
|
|
30
168
|
function getBrowserLanguagePrefix() {
|
|
31
169
|
const lang = getBrowserLanguage();
|
|
32
|
-
return typeof lang ===
|
|
170
|
+
return typeof lang === 'string' ? lang.split('-')[0] : undefined;
|
|
33
171
|
}
|
|
34
|
-
/**
|
|
35
|
-
* Get referrer
|
|
36
|
-
* Returns document.referrer or '$direct' if no referrer
|
|
37
|
-
*/
|
|
38
172
|
function getReferrer() {
|
|
39
|
-
return (globals_1.document === null || globals_1.document === void 0 ? void 0 : globals_1.document.referrer) ||
|
|
173
|
+
return (globals_1.document === null || globals_1.document === void 0 ? void 0 : globals_1.document.referrer) || '$direct';
|
|
40
174
|
}
|
|
41
|
-
/**
|
|
42
|
-
* Get referring domain
|
|
43
|
-
* Returns the hostname of the referrer URL or '$direct' if no referrer
|
|
44
|
-
*/
|
|
45
175
|
function getReferringDomain() {
|
|
176
|
+
var _a;
|
|
46
177
|
if (!(globals_1.document === null || globals_1.document === void 0 ? void 0 : globals_1.document.referrer)) {
|
|
47
|
-
return
|
|
178
|
+
return '$direct';
|
|
48
179
|
}
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
180
|
+
return ((_a = (0, request_utils_1.convertToURL)(globals_1.document.referrer)) === null || _a === void 0 ? void 0 : _a.host) || '$direct';
|
|
181
|
+
}
|
|
182
|
+
/**
|
|
183
|
+
* Get referrer information
|
|
184
|
+
* Returns current referrer and referring domain
|
|
185
|
+
*/
|
|
186
|
+
function getReferrerInfo() {
|
|
187
|
+
return {
|
|
188
|
+
$referrer: getReferrer(),
|
|
189
|
+
$referring_domain: getReferringDomain(),
|
|
190
|
+
};
|
|
191
|
+
}
|
|
192
|
+
/**
|
|
193
|
+
* Get person info for initial storage
|
|
194
|
+
* Extracts referrer and URL info, masks personal data if configured
|
|
195
|
+
* Returns compact format (r: referrer, u: url) for storage efficiency
|
|
196
|
+
*/
|
|
197
|
+
function getPersonInfo(maskPersonalDataProperties, customPersonalDataProperties) {
|
|
198
|
+
const paramsToMask = maskPersonalDataProperties
|
|
199
|
+
? (0, index_2.extendArray)([], exports.PERSONAL_DATA_CAMPAIGN_PARAMS, customPersonalDataProperties || [])
|
|
200
|
+
: [];
|
|
201
|
+
const url = globals_1.location === null || globals_1.location === void 0 ? void 0 : globals_1.location.href.substring(0, 1000);
|
|
202
|
+
// Compact format for storage efficiency (stored in localStorage)
|
|
203
|
+
return {
|
|
204
|
+
r: getReferrer().substring(0, 1000),
|
|
205
|
+
u: url ? (0, request_utils_1.maskQueryParams)(url, paramsToMask, exports.MASKED) : undefined,
|
|
206
|
+
};
|
|
207
|
+
}
|
|
208
|
+
/**
|
|
209
|
+
* Convert person info to person properties
|
|
210
|
+
* Extracts referrer, URL, campaign params, and search info from stored person info
|
|
211
|
+
*/
|
|
212
|
+
function getPersonPropsFromInfo(info) {
|
|
213
|
+
var _a;
|
|
214
|
+
const { r: referrer, u: url } = info;
|
|
215
|
+
const referring_domain = referrer == null ? undefined : referrer == '$direct' ? '$direct' : (_a = (0, request_utils_1.convertToURL)(referrer)) === null || _a === void 0 ? void 0 : _a.host;
|
|
216
|
+
const props = {
|
|
217
|
+
$referrer: referrer,
|
|
218
|
+
$referring_domain: referring_domain,
|
|
219
|
+
};
|
|
220
|
+
if (url) {
|
|
221
|
+
props['$current_url'] = url;
|
|
222
|
+
const location = (0, request_utils_1.convertToURL)(url);
|
|
223
|
+
props['$host'] = location === null || location === void 0 ? void 0 : location.host;
|
|
224
|
+
props['$pathname'] = location === null || location === void 0 ? void 0 : location.pathname;
|
|
225
|
+
const campaignParams = _getCampaignParamsFromUrl(url);
|
|
226
|
+
(0, index_2.extend)(props, campaignParams);
|
|
52
227
|
}
|
|
53
|
-
|
|
54
|
-
|
|
228
|
+
if (referrer) {
|
|
229
|
+
const searchInfo = _getSearchInfoFromReferrer(referrer);
|
|
230
|
+
(0, index_2.extend)(props, searchInfo);
|
|
55
231
|
}
|
|
232
|
+
return props;
|
|
56
233
|
}
|
|
57
234
|
/**
|
|
58
|
-
*
|
|
59
|
-
*
|
|
235
|
+
* Convert person info to initial person properties
|
|
236
|
+
* Generates $initial_* properties from person info (preserves first values)
|
|
60
237
|
*/
|
|
238
|
+
function getInitialPersonPropsFromInfo(info) {
|
|
239
|
+
const personProps = getPersonPropsFromInfo(info);
|
|
240
|
+
const props = {};
|
|
241
|
+
(0, index_2.each)(personProps, function (val, key) {
|
|
242
|
+
props[`$initial_${(0, index_1.stripLeadingDollar)(String(key))}`] = val;
|
|
243
|
+
});
|
|
244
|
+
return props;
|
|
245
|
+
}
|
|
61
246
|
function getTimezone() {
|
|
62
247
|
try {
|
|
63
248
|
return Intl.DateTimeFormat().resolvedOptions().timeZone;
|
|
@@ -66,10 +251,6 @@ function getTimezone() {
|
|
|
66
251
|
return undefined;
|
|
67
252
|
}
|
|
68
253
|
}
|
|
69
|
-
/**
|
|
70
|
-
* Get timezone offset
|
|
71
|
-
* Returns the timezone offset in minutes
|
|
72
|
-
*/
|
|
73
254
|
function getTimezoneOffset() {
|
|
74
255
|
try {
|
|
75
256
|
return new Date().getTimezoneOffset();
|
|
@@ -78,100 +259,42 @@ function getTimezoneOffset() {
|
|
|
78
259
|
return undefined;
|
|
79
260
|
}
|
|
80
261
|
}
|
|
81
|
-
/**
|
|
82
|
-
* Generate insert ID for deduplication
|
|
83
|
-
*/
|
|
84
|
-
function generateInsertId() {
|
|
85
|
-
return (Math.random().toString(36).substring(2, 10) +
|
|
86
|
-
Math.random().toString(36).substring(2, 10));
|
|
87
|
-
}
|
|
88
262
|
/**
|
|
89
263
|
* Get event properties that should be added to all events
|
|
264
|
+
* Returns all event context properties (browser, device, URL, etc.) plus event metadata
|
|
265
|
+
* Note: Only properties in EVENT_TO_PERSON_PROPERTIES are copied to person properties
|
|
90
266
|
*/
|
|
91
|
-
function getEventProperties() {
|
|
92
|
-
const props = {};
|
|
267
|
+
function getEventProperties(maskPersonalDataProperties, customPersonalDataProperties) {
|
|
93
268
|
if (!globals_1.userAgent) {
|
|
94
|
-
return
|
|
269
|
+
return {};
|
|
95
270
|
}
|
|
96
|
-
|
|
271
|
+
const paramsToMask = maskPersonalDataProperties
|
|
272
|
+
? (0, index_2.extendArray)([], exports.PERSONAL_DATA_CAMPAIGN_PARAMS, customPersonalDataProperties || [])
|
|
273
|
+
: [];
|
|
97
274
|
const [os_name, os_version] = (0, user_agent_utils_1.detectOS)(globals_1.userAgent);
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
props.$timezone = timezone;
|
|
124
|
-
}
|
|
125
|
-
const timezoneOffset = getTimezoneOffset();
|
|
126
|
-
if (timezoneOffset !== undefined) {
|
|
127
|
-
props.$timezone_offset = timezoneOffset;
|
|
128
|
-
}
|
|
129
|
-
// URL properties (added to all events)
|
|
130
|
-
if (globals_1.location) {
|
|
131
|
-
props.$current_url = globals_1.location.href;
|
|
132
|
-
props.$host = globals_1.location.host;
|
|
133
|
-
props.$pathname = globals_1.location.pathname;
|
|
134
|
-
}
|
|
135
|
-
// User agent
|
|
136
|
-
if (globals_1.userAgent) {
|
|
137
|
-
props.$raw_user_agent =
|
|
138
|
-
globals_1.userAgent.length > 1000 ? globals_1.userAgent.substring(0, 997) + "..." : globals_1.userAgent;
|
|
139
|
-
}
|
|
140
|
-
// Browser language (added to all events)
|
|
141
|
-
const browserLanguage = getBrowserLanguage();
|
|
142
|
-
const browserLanguagePrefix = getBrowserLanguagePrefix();
|
|
143
|
-
if (browserLanguage) {
|
|
144
|
-
props.$browser_language = browserLanguage;
|
|
145
|
-
}
|
|
146
|
-
if (browserLanguagePrefix) {
|
|
147
|
-
props.$browser_language_prefix = browserLanguagePrefix;
|
|
148
|
-
}
|
|
149
|
-
// Screen/viewport properties
|
|
150
|
-
if (globals_1.window === null || globals_1.window === void 0 ? void 0 : globals_1.window.screen) {
|
|
151
|
-
if (globals_1.window.screen.height) {
|
|
152
|
-
props.$screen_height = globals_1.window.screen.height;
|
|
153
|
-
}
|
|
154
|
-
if (globals_1.window.screen.width) {
|
|
155
|
-
props.$screen_width = globals_1.window.screen.width;
|
|
156
|
-
}
|
|
157
|
-
}
|
|
158
|
-
if (globals_1.window) {
|
|
159
|
-
if (globals_1.window.innerHeight) {
|
|
160
|
-
props.$viewport_height = globals_1.window.innerHeight;
|
|
161
|
-
}
|
|
162
|
-
if (globals_1.window.innerWidth) {
|
|
163
|
-
props.$viewport_width = globals_1.window.innerWidth;
|
|
164
|
-
}
|
|
165
|
-
}
|
|
166
|
-
// Library info
|
|
167
|
-
props.$lib = "web";
|
|
168
|
-
props.$lib_version = LIB_VERSION;
|
|
169
|
-
// Insert ID for deduplication
|
|
170
|
-
props.$insert_id = generateInsertId();
|
|
171
|
-
// Timestamp (epoch time in seconds)
|
|
172
|
-
props.$time = Date.now() / 1000;
|
|
173
|
-
// Referrer properties (added to all events)
|
|
174
|
-
props.$referrer = getReferrer();
|
|
175
|
-
props.$referring_domain = getReferringDomain();
|
|
176
|
-
return props;
|
|
275
|
+
return (0, index_2.extend)((0, index_2.stripEmptyProperties)({
|
|
276
|
+
$os: os_name,
|
|
277
|
+
$os_version: os_version,
|
|
278
|
+
$browser: (0, user_agent_utils_1.detectBrowser)(globals_1.userAgent, navigator.vendor),
|
|
279
|
+
$device: (0, user_agent_utils_1.detectDevice)(globals_1.userAgent),
|
|
280
|
+
$device_type: (0, user_agent_utils_1.detectDeviceType)(globals_1.userAgent),
|
|
281
|
+
$timezone: getTimezone(),
|
|
282
|
+
$timezone_offset: getTimezoneOffset(),
|
|
283
|
+
}), {
|
|
284
|
+
$current_url: (0, request_utils_1.maskQueryParams)(globals_1.location === null || globals_1.location === void 0 ? void 0 : globals_1.location.href, paramsToMask, exports.MASKED),
|
|
285
|
+
$host: globals_1.location === null || globals_1.location === void 0 ? void 0 : globals_1.location.host,
|
|
286
|
+
$pathname: globals_1.location === null || globals_1.location === void 0 ? void 0 : globals_1.location.pathname,
|
|
287
|
+
$raw_user_agent: globals_1.userAgent.length > 1000 ? globals_1.userAgent.substring(0, 997) + '...' : globals_1.userAgent,
|
|
288
|
+
$browser_version: (0, user_agent_utils_1.detectBrowserVersion)(globals_1.userAgent, navigator.vendor),
|
|
289
|
+
$browser_language: getBrowserLanguage(),
|
|
290
|
+
$browser_language_prefix: getBrowserLanguagePrefix(),
|
|
291
|
+
$screen_height: globals_1.window === null || globals_1.window === void 0 ? void 0 : globals_1.window.screen.height,
|
|
292
|
+
$screen_width: globals_1.window === null || globals_1.window === void 0 ? void 0 : globals_1.window.screen.width,
|
|
293
|
+
$viewport_height: globals_1.window === null || globals_1.window === void 0 ? void 0 : globals_1.window.innerHeight,
|
|
294
|
+
$viewport_width: globals_1.window === null || globals_1.window === void 0 ? void 0 : globals_1.window.innerWidth,
|
|
295
|
+
$lib: 'web',
|
|
296
|
+
$lib_version: LIB_VERSION,
|
|
297
|
+
$insert_id: Math.random().toString(36).substring(2, 10) + Math.random().toString(36).substring(2, 10),
|
|
298
|
+
$time: Date.now() / 1000, // epoch time in seconds
|
|
299
|
+
});
|
|
177
300
|
}
|