@mparticle/web-sdk 2.50.1 → 2.52.0
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/README.md +1 -1
- package/dist/mparticle.common.js +38 -19
- package/dist/mparticle.esm.js +38 -19
- package/dist/mparticle.js +232 -45
- package/package.json +9 -5
- package/src/cookieSyncManager.ts +16 -2
- package/src/helpers.js +15 -0
- package/src/identity.interfaces.ts +5 -2
- package/src/identity.js +3 -1
- package/src/integrationCapture.ts +6 -0
- package/src/mparticle-instance-manager.ts +2 -2
- package/src/roktManager.ts +97 -7
- package/src/sessionManager.ts +45 -40
- package/src/store.ts +1 -0
- package/src/stub/mparticle.stub.js +1 -0
- package/src/utils.ts +13 -3
package/dist/mparticle.js
CHANGED
|
@@ -203,7 +203,7 @@ var mParticle = (function () {
|
|
|
203
203
|
Base64: Base64$1
|
|
204
204
|
};
|
|
205
205
|
|
|
206
|
-
var version = "2.
|
|
206
|
+
var version = "2.52.0";
|
|
207
207
|
|
|
208
208
|
var Constants = {
|
|
209
209
|
sdkVersion: version,
|
|
@@ -667,12 +667,17 @@ var mParticle = (function () {
|
|
|
667
667
|
var replaceAmpWithAmpersand = function replaceAmpWithAmpersand(value) {
|
|
668
668
|
return value.replace(/&/g, '&');
|
|
669
669
|
};
|
|
670
|
-
var createCookieSyncUrl = function createCookieSyncUrl(mpid, pixelUrl, redirectUrl) {
|
|
670
|
+
var createCookieSyncUrl = function createCookieSyncUrl(mpid, pixelUrl, redirectUrl, domain) {
|
|
671
671
|
var modifiedPixelUrl = replaceAmpWithAmpersand(pixelUrl);
|
|
672
672
|
var modifiedDirectUrl = redirectUrl ? replaceAmpWithAmpersand(redirectUrl) : null;
|
|
673
673
|
var url = replaceMPID(modifiedPixelUrl, mpid);
|
|
674
674
|
var redirect = modifiedDirectUrl ? replaceMPID(modifiedDirectUrl, mpid) : '';
|
|
675
|
-
|
|
675
|
+
var fullUrl = url + encodeURIComponent(redirect);
|
|
676
|
+
if (domain) {
|
|
677
|
+
var separator = fullUrl.includes('?') ? '&' : '?';
|
|
678
|
+
fullUrl += "".concat(separator, "domain=").concat(domain);
|
|
679
|
+
}
|
|
680
|
+
return fullUrl;
|
|
676
681
|
};
|
|
677
682
|
// FIXME: REFACTOR for V3
|
|
678
683
|
// only used in store.js to sanitize server-side formatting of
|
|
@@ -3182,6 +3187,16 @@ var mParticle = (function () {
|
|
|
3182
3187
|
if ((options = arguments[i]) != null) {
|
|
3183
3188
|
// Extend the base object
|
|
3184
3189
|
for (name in options) {
|
|
3190
|
+
// Prevent prototype pollution
|
|
3191
|
+
// https://github.com/advisories/GHSA-jf85-cpcp-j695
|
|
3192
|
+
if (name === '__proto__' || name === 'constructor' || name === 'prototype') {
|
|
3193
|
+
continue;
|
|
3194
|
+
}
|
|
3195
|
+
|
|
3196
|
+
// Only copy own properties
|
|
3197
|
+
if (!Object.prototype.hasOwnProperty.call(options, name)) {
|
|
3198
|
+
continue;
|
|
3199
|
+
}
|
|
3185
3200
|
src = target[name];
|
|
3186
3201
|
copy = options[name];
|
|
3187
3202
|
|
|
@@ -3464,6 +3479,15 @@ var mParticle = (function () {
|
|
|
3464
3479
|
var Messages$7 = Constants.Messages;
|
|
3465
3480
|
var InformationMessages = Messages$7.InformationMessages;
|
|
3466
3481
|
var DAYS_IN_MILLISECONDS = 1000 * 60 * 60 * 24;
|
|
3482
|
+
// Partner module IDs for cookie sync configurations
|
|
3483
|
+
var PARTNER_MODULE_IDS = {
|
|
3484
|
+
AdobeEventForwarder: 11,
|
|
3485
|
+
DoubleclickDFP: 41,
|
|
3486
|
+
AppNexus: 50,
|
|
3487
|
+
Lotame: 58,
|
|
3488
|
+
TradeDesk: 103,
|
|
3489
|
+
VerizonMedia: 155
|
|
3490
|
+
};
|
|
3467
3491
|
function CookieSyncManager(mpInstance) {
|
|
3468
3492
|
var self = this;
|
|
3469
3493
|
// Public
|
|
@@ -3512,8 +3536,12 @@ var mParticle = (function () {
|
|
|
3512
3536
|
if (!isLastSyncDateExpired(frequencyCap, lastSyncDateForModule)) {
|
|
3513
3537
|
return;
|
|
3514
3538
|
}
|
|
3515
|
-
//
|
|
3516
|
-
|
|
3539
|
+
// The Trade Desk requires a URL parameter for GDPR enabled users.
|
|
3540
|
+
// It is optional but to simplify the code, we add it for all Trade
|
|
3541
|
+
// // Desk cookie syncs.
|
|
3542
|
+
var domain = moduleId === PARTNER_MODULE_IDS.TradeDesk ? window.location.hostname : undefined;
|
|
3543
|
+
// Add domain parameter for Trade Desk
|
|
3544
|
+
var fullUrl = createCookieSyncUrl(mpid, pixelUrl, redirectUrl, domain);
|
|
3517
3545
|
self.performCookieSync(fullUrl, moduleId.toString(), mpid, cookieSyncDates);
|
|
3518
3546
|
});
|
|
3519
3547
|
};
|
|
@@ -3700,17 +3728,20 @@ var mParticle = (function () {
|
|
|
3700
3728
|
var self = this;
|
|
3701
3729
|
this.initialize = function () {
|
|
3702
3730
|
if (mpInstance._Store.sessionId) {
|
|
3703
|
-
var
|
|
3704
|
-
|
|
3731
|
+
var _a = mpInstance._Store,
|
|
3732
|
+
dateLastEventSent = _a.dateLastEventSent,
|
|
3733
|
+
SDKConfig = _a.SDKConfig;
|
|
3734
|
+
var sessionTimeout = SDKConfig.sessionTimeout;
|
|
3735
|
+
if (hasSessionTimedOut(dateLastEventSent === null || dateLastEventSent === void 0 ? void 0 : dateLastEventSent.getTime(), sessionTimeout)) {
|
|
3705
3736
|
self.endSession();
|
|
3706
3737
|
self.startNewSession();
|
|
3707
3738
|
} else {
|
|
3708
3739
|
// https://go.mparticle.com/work/SQDSDKS-6045
|
|
3709
3740
|
// https://go.mparticle.com/work/SQDSDKS-6323
|
|
3710
3741
|
var currentUser = mpInstance.Identity.getCurrentUser();
|
|
3711
|
-
var sdkIdentityRequest =
|
|
3742
|
+
var sdkIdentityRequest = SDKConfig.identifyRequest;
|
|
3712
3743
|
if (hasIdentityRequestChanged(currentUser, sdkIdentityRequest)) {
|
|
3713
|
-
mpInstance.Identity.identify(
|
|
3744
|
+
mpInstance.Identity.identify(sdkIdentityRequest, SDKConfig.identityCallback);
|
|
3714
3745
|
mpInstance._Store.identifyCalled = true;
|
|
3715
3746
|
mpInstance._Store.SDKConfig.identityCallback = null;
|
|
3716
3747
|
}
|
|
@@ -3754,14 +3785,10 @@ var mParticle = (function () {
|
|
|
3754
3785
|
}
|
|
3755
3786
|
};
|
|
3756
3787
|
this.endSession = function (override) {
|
|
3757
|
-
var _a, _b, _c, _d
|
|
3788
|
+
var _a, _b, _c, _d;
|
|
3758
3789
|
mpInstance.Logger.verbose(Messages$6.InformationMessages.StartingEndSession);
|
|
3759
3790
|
if (override) {
|
|
3760
|
-
|
|
3761
|
-
messageType: Types.MessageType.SessionEnd
|
|
3762
|
-
});
|
|
3763
|
-
mpInstance._Store.nullifySession();
|
|
3764
|
-
(_a = mpInstance._timeOnSiteTimer) === null || _a === void 0 ? void 0 : _a.resetTimer();
|
|
3791
|
+
performSessionEnd();
|
|
3765
3792
|
return;
|
|
3766
3793
|
}
|
|
3767
3794
|
if (!mpInstance._Helpers.canLog()) {
|
|
@@ -3770,36 +3797,28 @@ var mParticle = (function () {
|
|
|
3770
3797
|
// - the devToken is undefined
|
|
3771
3798
|
// - webviewBridgeEnabled is set to false
|
|
3772
3799
|
mpInstance.Logger.verbose(Messages$6.InformationMessages.AbandonEndSession);
|
|
3773
|
-
(
|
|
3800
|
+
(_a = mpInstance._timeOnSiteTimer) === null || _a === void 0 ? void 0 : _a.resetTimer();
|
|
3774
3801
|
return;
|
|
3775
3802
|
}
|
|
3776
|
-
var sessionTimeoutInMilliseconds;
|
|
3777
|
-
var timeSinceLastEventSent;
|
|
3778
3803
|
var cookies = mpInstance._Persistence.getPersistence();
|
|
3779
3804
|
if (!cookies || cookies.gs && !cookies.gs.sid) {
|
|
3780
3805
|
mpInstance.Logger.verbose(Messages$6.InformationMessages.NoSessionToEnd);
|
|
3781
|
-
(
|
|
3806
|
+
(_b = mpInstance._timeOnSiteTimer) === null || _b === void 0 ? void 0 : _b.resetTimer();
|
|
3782
3807
|
return;
|
|
3783
3808
|
}
|
|
3784
3809
|
// sessionId is not equal to cookies.sid if cookies.sid is changed in another tab
|
|
3785
3810
|
if (cookies.gs.sid && mpInstance._Store.sessionId !== cookies.gs.sid) {
|
|
3786
3811
|
mpInstance._Store.sessionId = cookies.gs.sid;
|
|
3787
3812
|
}
|
|
3788
|
-
if ((
|
|
3789
|
-
|
|
3790
|
-
|
|
3791
|
-
|
|
3792
|
-
if (timeSinceLastEventSent < sessionTimeoutInMilliseconds) {
|
|
3793
|
-
self.setSessionTimer();
|
|
3813
|
+
if ((_c = cookies === null || cookies === void 0 ? void 0 : cookies.gs) === null || _c === void 0 ? void 0 : _c.les) {
|
|
3814
|
+
var sessionTimeout = mpInstance._Store.SDKConfig.sessionTimeout;
|
|
3815
|
+
if (hasSessionTimedOut(cookies.gs.les, sessionTimeout)) {
|
|
3816
|
+
performSessionEnd();
|
|
3794
3817
|
} else {
|
|
3795
|
-
|
|
3796
|
-
|
|
3797
|
-
});
|
|
3798
|
-
mpInstance._Store.sessionStartDate = null;
|
|
3799
|
-
mpInstance._Store.nullifySession();
|
|
3818
|
+
self.setSessionTimer();
|
|
3819
|
+
(_d = mpInstance._timeOnSiteTimer) === null || _d === void 0 ? void 0 : _d.resetTimer();
|
|
3800
3820
|
}
|
|
3801
3821
|
}
|
|
3802
|
-
(_e = mpInstance._timeOnSiteTimer) === null || _e === void 0 ? void 0 : _e.resetTimer();
|
|
3803
3822
|
};
|
|
3804
3823
|
this.setSessionTimer = function () {
|
|
3805
3824
|
var sessionTimeoutInMilliseconds = mpInstance._Store.SDKConfig.sessionTimeout * 60000;
|
|
@@ -3832,6 +3851,34 @@ var mParticle = (function () {
|
|
|
3832
3851
|
}
|
|
3833
3852
|
}
|
|
3834
3853
|
};
|
|
3854
|
+
/**
|
|
3855
|
+
* Checks if the session has expired based on the last event timestamp
|
|
3856
|
+
* @param lastEventTimestamp - Unix timestamp in milliseconds of the last event
|
|
3857
|
+
* @param sessionTimeout - Session timeout in minutes
|
|
3858
|
+
* @returns true if the session has expired, false otherwise
|
|
3859
|
+
*/
|
|
3860
|
+
function hasSessionTimedOut(lastEventTimestamp, sessionTimeout) {
|
|
3861
|
+
if (!lastEventTimestamp || !sessionTimeout || sessionTimeout <= 0) {
|
|
3862
|
+
return false;
|
|
3863
|
+
}
|
|
3864
|
+
var sessionTimeoutInMilliseconds = sessionTimeout * 60000;
|
|
3865
|
+
var timeSinceLastEvent = Date.now() - lastEventTimestamp;
|
|
3866
|
+
return timeSinceLastEvent >= sessionTimeoutInMilliseconds;
|
|
3867
|
+
}
|
|
3868
|
+
/**
|
|
3869
|
+
* Performs session end operations:
|
|
3870
|
+
* - Logs a SessionEnd event
|
|
3871
|
+
* - Nullifies the session ID and related data
|
|
3872
|
+
* - Resets the time-on-site timer
|
|
3873
|
+
*/
|
|
3874
|
+
function performSessionEnd() {
|
|
3875
|
+
var _a;
|
|
3876
|
+
mpInstance._Events.logEvent({
|
|
3877
|
+
messageType: Types.MessageType.SessionEnd
|
|
3878
|
+
});
|
|
3879
|
+
mpInstance._Store.nullifySession();
|
|
3880
|
+
(_a = mpInstance._timeOnSiteTimer) === null || _a === void 0 ? void 0 : _a.resetTimer();
|
|
3881
|
+
}
|
|
3835
3882
|
}
|
|
3836
3883
|
|
|
3837
3884
|
var Messages$5 = Constants.Messages;
|
|
@@ -4692,6 +4739,7 @@ var mParticle = (function () {
|
|
|
4692
4739
|
this.nullifySession = function () {
|
|
4693
4740
|
_this.sessionId = null;
|
|
4694
4741
|
_this.dateLastEventSent = null;
|
|
4742
|
+
_this.sessionStartDate = null;
|
|
4695
4743
|
_this.sessionAttributes = {};
|
|
4696
4744
|
_this.localSessionAttributes = {};
|
|
4697
4745
|
mpInstance._Persistence.update();
|
|
@@ -7352,7 +7400,8 @@ var mParticle = (function () {
|
|
|
7352
7400
|
DestinationMpid: aliasRequest.destinationMpid,
|
|
7353
7401
|
SourceMpid: aliasRequest.sourceMpid,
|
|
7354
7402
|
StartUnixtimeMs: aliasRequest.startTime,
|
|
7355
|
-
EndUnixtimeMs: aliasRequest.endTime
|
|
7403
|
+
EndUnixtimeMs: aliasRequest.endTime,
|
|
7404
|
+
Scope: aliasRequest.scope
|
|
7356
7405
|
};
|
|
7357
7406
|
},
|
|
7358
7407
|
convertToNative: function convertToNative(identityApiData) {
|
|
@@ -7652,7 +7701,7 @@ var mParticle = (function () {
|
|
|
7652
7701
|
after applying this adjustment it will be impossible to create an aliasRequest passes the aliasUsers()
|
|
7653
7702
|
validation that the startTime must be less than the endTime
|
|
7654
7703
|
*/
|
|
7655
|
-
createAliasRequest: function createAliasRequest(sourceUser, destinationUser) {
|
|
7704
|
+
createAliasRequest: function createAliasRequest(sourceUser, destinationUser, scope) {
|
|
7656
7705
|
try {
|
|
7657
7706
|
if (!destinationUser || !sourceUser) {
|
|
7658
7707
|
mpInstance.Logger.error("'destinationUser' and 'sourceUser' must both be present");
|
|
@@ -7679,7 +7728,8 @@ var mParticle = (function () {
|
|
|
7679
7728
|
destinationMpid: destinationUser.getMPID(),
|
|
7680
7729
|
sourceMpid: sourceUser.getMPID(),
|
|
7681
7730
|
startTime: startTime,
|
|
7682
|
-
endTime: endTime
|
|
7731
|
+
endTime: endTime,
|
|
7732
|
+
scope: scope || 'device'
|
|
7683
7733
|
};
|
|
7684
7734
|
} catch (e) {
|
|
7685
7735
|
mpInstance.Logger.error('There was a problem with creating an alias request: ' + e);
|
|
@@ -9399,6 +9449,12 @@ var mParticle = (function () {
|
|
|
9399
9449
|
ScCid: {
|
|
9400
9450
|
mappedKey: 'SnapchatConversions.ClickId',
|
|
9401
9451
|
output: IntegrationOutputs.CUSTOM_FLAGS
|
|
9452
|
+
},
|
|
9453
|
+
// Snapchat
|
|
9454
|
+
// https://developers.snap.com/api/marketing-api/Conversions-API/UsingTheAPI#sending-click-id
|
|
9455
|
+
_scid: {
|
|
9456
|
+
mappedKey: 'SnapchatConversions.Cookie1',
|
|
9457
|
+
output: IntegrationOutputs.CUSTOM_FLAGS
|
|
9402
9458
|
}
|
|
9403
9459
|
};
|
|
9404
9460
|
var integrationMappingRokt = {
|
|
@@ -9774,17 +9830,73 @@ var mParticle = (function () {
|
|
|
9774
9830
|
});
|
|
9775
9831
|
});
|
|
9776
9832
|
};
|
|
9777
|
-
|
|
9833
|
+
/**
|
|
9834
|
+
* Hashes attributes and returns both original and hashed versions
|
|
9835
|
+
* with Rokt-compatible key names (like emailsha256, mobilesha256)
|
|
9836
|
+
*
|
|
9837
|
+
*
|
|
9838
|
+
* @param {IRoktPartnerAttributes} attributes - Attributes to hash
|
|
9839
|
+
* @returns {Promise<IRoktPartnerAttributes>} Object with both original and hashed attributes
|
|
9840
|
+
*
|
|
9841
|
+
*/
|
|
9778
9842
|
RoktManager.prototype.hashAttributes = function (attributes) {
|
|
9779
|
-
|
|
9780
|
-
|
|
9781
|
-
|
|
9782
|
-
|
|
9783
|
-
|
|
9784
|
-
|
|
9785
|
-
|
|
9786
|
-
|
|
9843
|
+
return __awaiter(this, void 0, void 0, function () {
|
|
9844
|
+
var keys, hashPromises, results, hashedAttributes, _i, results_1, _a, key, attributeValue, hashedValue, error_3, errorMessage;
|
|
9845
|
+
var _this = this;
|
|
9846
|
+
return __generator(this, function (_b) {
|
|
9847
|
+
switch (_b.label) {
|
|
9848
|
+
case 0:
|
|
9849
|
+
_b.trys.push([0, 2,, 3]);
|
|
9850
|
+
if (!attributes || _typeof$1(attributes) !== 'object') {
|
|
9851
|
+
return [2 /*return*/, {}];
|
|
9852
|
+
}
|
|
9853
|
+
keys = Object.keys(attributes);
|
|
9854
|
+
if (keys.length === 0) {
|
|
9855
|
+
return [2 /*return*/, {}];
|
|
9856
|
+
}
|
|
9857
|
+
hashPromises = keys.map(function (key) {
|
|
9858
|
+
return __awaiter(_this, void 0, void 0, function () {
|
|
9859
|
+
var attributeValue, hashedValue;
|
|
9860
|
+
return __generator(this, function (_a) {
|
|
9861
|
+
switch (_a.label) {
|
|
9862
|
+
case 0:
|
|
9863
|
+
attributeValue = attributes[key];
|
|
9864
|
+
return [4 /*yield*/, this.hashSha256(attributeValue)];
|
|
9865
|
+
case 1:
|
|
9866
|
+
hashedValue = _a.sent();
|
|
9867
|
+
return [2 /*return*/, {
|
|
9868
|
+
key: key,
|
|
9869
|
+
attributeValue: attributeValue,
|
|
9870
|
+
hashedValue: hashedValue
|
|
9871
|
+
}];
|
|
9872
|
+
}
|
|
9873
|
+
});
|
|
9874
|
+
});
|
|
9875
|
+
});
|
|
9876
|
+
return [4 /*yield*/, Promise.all(hashPromises)];
|
|
9877
|
+
case 1:
|
|
9878
|
+
results = _b.sent();
|
|
9879
|
+
hashedAttributes = {};
|
|
9880
|
+
for (_i = 0, results_1 = results; _i < results_1.length; _i++) {
|
|
9881
|
+
_a = results_1[_i], key = _a.key, attributeValue = _a.attributeValue, hashedValue = _a.hashedValue;
|
|
9882
|
+
hashedAttributes[key] = attributeValue;
|
|
9883
|
+
if (hashedValue) {
|
|
9884
|
+
hashedAttributes["".concat(key, "sha256")] = hashedValue;
|
|
9885
|
+
}
|
|
9886
|
+
}
|
|
9887
|
+
return [2 /*return*/, hashedAttributes];
|
|
9888
|
+
case 2:
|
|
9889
|
+
error_3 = _b.sent();
|
|
9890
|
+
errorMessage = error_3 instanceof Error ? error_3.message : String(error_3);
|
|
9891
|
+
this.logger.error("Failed to hashAttributes, returning an empty object: ".concat(errorMessage));
|
|
9892
|
+
return [2 /*return*/, {}];
|
|
9893
|
+
case 3:
|
|
9894
|
+
return [2 /*return*/];
|
|
9895
|
+
}
|
|
9896
|
+
});
|
|
9897
|
+
});
|
|
9787
9898
|
};
|
|
9899
|
+
|
|
9788
9900
|
RoktManager.prototype.setExtensionData = function (extensionData) {
|
|
9789
9901
|
if (!this.isReady()) {
|
|
9790
9902
|
this.deferredCall('setExtensionData', extensionData);
|
|
@@ -9807,6 +9919,42 @@ var mParticle = (function () {
|
|
|
9807
9919
|
return Promise.reject(error instanceof Error ? error : new Error('Error using extension: ' + name));
|
|
9808
9920
|
}
|
|
9809
9921
|
};
|
|
9922
|
+
/**
|
|
9923
|
+
* Hashes an attribute using SHA-256
|
|
9924
|
+
*
|
|
9925
|
+
* @param {string | number | boolean | undefined | null} attribute - The value to hash
|
|
9926
|
+
* @returns {Promise<string | undefined | null>} SHA-256 hashed value or undefined/null
|
|
9927
|
+
*
|
|
9928
|
+
*/
|
|
9929
|
+
RoktManager.prototype.hashSha256 = function (attribute) {
|
|
9930
|
+
return __awaiter(this, void 0, void 0, function () {
|
|
9931
|
+
var normalizedValue, error_4, errorMessage;
|
|
9932
|
+
return __generator(this, function (_a) {
|
|
9933
|
+
switch (_a.label) {
|
|
9934
|
+
case 0:
|
|
9935
|
+
if (attribute === null || attribute === undefined) {
|
|
9936
|
+
this.logger.warning("hashSha256 received null/undefined as input");
|
|
9937
|
+
return [2 /*return*/, attribute];
|
|
9938
|
+
}
|
|
9939
|
+
_a.label = 1;
|
|
9940
|
+
case 1:
|
|
9941
|
+
_a.trys.push([1, 3,, 4]);
|
|
9942
|
+
normalizedValue = String(attribute).trim().toLocaleLowerCase();
|
|
9943
|
+
return [4 /*yield*/, this.sha256Hex(normalizedValue)];
|
|
9944
|
+
case 2:
|
|
9945
|
+
return [2 /*return*/, _a.sent()];
|
|
9946
|
+
case 3:
|
|
9947
|
+
error_4 = _a.sent();
|
|
9948
|
+
errorMessage = error_4 instanceof Error ? error_4.message : String(error_4);
|
|
9949
|
+
this.logger.error("Failed to hashSha256, returning undefined: ".concat(errorMessage));
|
|
9950
|
+
return [2 /*return*/, undefined];
|
|
9951
|
+
case 4:
|
|
9952
|
+
return [2 /*return*/];
|
|
9953
|
+
}
|
|
9954
|
+
});
|
|
9955
|
+
});
|
|
9956
|
+
};
|
|
9957
|
+
|
|
9810
9958
|
RoktManager.prototype.getLocalSessionAttributes = function () {
|
|
9811
9959
|
return this.store.getLocalSessionAttributes();
|
|
9812
9960
|
};
|
|
@@ -9902,6 +10050,45 @@ var mParticle = (function () {
|
|
|
9902
10050
|
}
|
|
9903
10051
|
this.messageQueue["delete"](messageId);
|
|
9904
10052
|
};
|
|
10053
|
+
/**
|
|
10054
|
+
* Hashes a string input using SHA-256 and returns the hex digest
|
|
10055
|
+
* Uses the Web Crypto API for secure hashing
|
|
10056
|
+
*
|
|
10057
|
+
* @param {string} input - The string to hash
|
|
10058
|
+
* @returns {Promise<string>} The SHA-256 hash as a hexadecimal string
|
|
10059
|
+
*/
|
|
10060
|
+
RoktManager.prototype.sha256Hex = function (input) {
|
|
10061
|
+
return __awaiter(this, void 0, void 0, function () {
|
|
10062
|
+
var encoder, encodedInput, digest;
|
|
10063
|
+
return __generator(this, function (_a) {
|
|
10064
|
+
switch (_a.label) {
|
|
10065
|
+
case 0:
|
|
10066
|
+
encoder = new TextEncoder();
|
|
10067
|
+
encodedInput = encoder.encode(input);
|
|
10068
|
+
return [4 /*yield*/, crypto.subtle.digest('SHA-256', encodedInput)];
|
|
10069
|
+
case 1:
|
|
10070
|
+
digest = _a.sent();
|
|
10071
|
+
return [2 /*return*/, this.arrayBufferToHex(digest)];
|
|
10072
|
+
}
|
|
10073
|
+
});
|
|
10074
|
+
});
|
|
10075
|
+
};
|
|
10076
|
+
/**
|
|
10077
|
+
* Converts an ArrayBuffer to a hexadecimal string representation
|
|
10078
|
+
* Each byte is converted to a 2-character hex string with leading zeros
|
|
10079
|
+
*
|
|
10080
|
+
* @param {ArrayBuffer} buffer - The buffer to convert
|
|
10081
|
+
* @returns {string} The hexadecimal string representation
|
|
10082
|
+
*/
|
|
10083
|
+
RoktManager.prototype.arrayBufferToHex = function (buffer) {
|
|
10084
|
+
var bytes = new Uint8Array(buffer);
|
|
10085
|
+
var hexString = '';
|
|
10086
|
+
for (var i = 0; i < bytes.length; i++) {
|
|
10087
|
+
var hexByte = bytes[i].toString(16).padStart(2, '0');
|
|
10088
|
+
hexString += hexByte;
|
|
10089
|
+
}
|
|
10090
|
+
return hexString;
|
|
10091
|
+
};
|
|
9905
10092
|
/**
|
|
9906
10093
|
* Checks if an identity value has changed by comparing current and new values
|
|
9907
10094
|
*
|
|
@@ -11451,8 +11638,8 @@ var mParticle = (function () {
|
|
|
11451
11638
|
aliasUsers: function aliasUsers(aliasRequest, callback) {
|
|
11452
11639
|
self.getInstance().Identity.aliasUsers(aliasRequest, callback);
|
|
11453
11640
|
},
|
|
11454
|
-
createAliasRequest: function createAliasRequest(sourceUser, destinationUser) {
|
|
11455
|
-
return self.getInstance().Identity.createAliasRequest(sourceUser, destinationUser);
|
|
11641
|
+
createAliasRequest: function createAliasRequest(sourceUser, destinationUser, scope) {
|
|
11642
|
+
return self.getInstance().Identity.createAliasRequest(sourceUser, destinationUser, scope);
|
|
11456
11643
|
},
|
|
11457
11644
|
getCurrentUser: function getCurrentUser() {
|
|
11458
11645
|
return self.getInstance().Identity.getCurrentUser();
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@mparticle/web-sdk",
|
|
3
|
-
"version": "2.
|
|
3
|
+
"version": "2.52.0",
|
|
4
4
|
"description": "mParticle core SDK for web applications",
|
|
5
5
|
"license": "Apache-2.0",
|
|
6
6
|
"keywords": [
|
|
@@ -15,7 +15,9 @@
|
|
|
15
15
|
"src/"
|
|
16
16
|
],
|
|
17
17
|
"publishConfig": {
|
|
18
|
-
"access": "public"
|
|
18
|
+
"access": "public",
|
|
19
|
+
"provenance": true,
|
|
20
|
+
"registry": "https://registry.npmjs.org"
|
|
19
21
|
},
|
|
20
22
|
"main": "dist/mparticle.common.js",
|
|
21
23
|
"module": "dist/mparticle.esm.js",
|
|
@@ -97,9 +99,11 @@
|
|
|
97
99
|
"@rollup/plugin-json": "^5.0.2",
|
|
98
100
|
"@rollup/plugin-node-resolve": "15.2.1",
|
|
99
101
|
"@rollup/plugin-typescript": "^11.1.0",
|
|
100
|
-
"@semantic-release/changelog": "^
|
|
101
|
-
"@semantic-release/exec": "^
|
|
102
|
-
"@semantic-release/git": "^
|
|
102
|
+
"@semantic-release/changelog": "^6.0.3",
|
|
103
|
+
"@semantic-release/exec": "^6.0.3",
|
|
104
|
+
"@semantic-release/git": "^10.0.1",
|
|
105
|
+
"@semantic-release/npm": "^13.1.2",
|
|
106
|
+
"semantic-release": "^24.2.0",
|
|
103
107
|
"@types/chai": "^4.2.3",
|
|
104
108
|
"@types/jest": "^29.5.1",
|
|
105
109
|
"@types/jest-expect-message": "^1.1.0",
|
package/src/cookieSyncManager.ts
CHANGED
|
@@ -13,6 +13,16 @@ const { InformationMessages } = Messages;
|
|
|
13
13
|
|
|
14
14
|
export const DAYS_IN_MILLISECONDS = 1000 * 60 * 60 * 24;
|
|
15
15
|
|
|
16
|
+
// Partner module IDs for cookie sync configurations
|
|
17
|
+
export const PARTNER_MODULE_IDS = {
|
|
18
|
+
AdobeEventForwarder: 11,
|
|
19
|
+
DoubleclickDFP: 41,
|
|
20
|
+
AppNexus: 50,
|
|
21
|
+
Lotame: 58,
|
|
22
|
+
TradeDesk: 103,
|
|
23
|
+
VerizonMedia: 155,
|
|
24
|
+
} as const;
|
|
25
|
+
|
|
16
26
|
export type CookieSyncDates = Dictionary<number>;
|
|
17
27
|
|
|
18
28
|
export interface IPixelConfiguration {
|
|
@@ -111,8 +121,12 @@ export default function CookieSyncManager(
|
|
|
111
121
|
return;
|
|
112
122
|
}
|
|
113
123
|
|
|
114
|
-
//
|
|
115
|
-
|
|
124
|
+
// The Trade Desk requires a URL parameter for GDPR enabled users.
|
|
125
|
+
// It is optional but to simplify the code, we add it for all Trade
|
|
126
|
+
// // Desk cookie syncs.
|
|
127
|
+
const domain = moduleId === PARTNER_MODULE_IDS.TradeDesk ? window.location.hostname : undefined;
|
|
128
|
+
// Add domain parameter for Trade Desk
|
|
129
|
+
const fullUrl = createCookieSyncUrl(mpid, pixelUrl, redirectUrl, domain);
|
|
116
130
|
|
|
117
131
|
self.performCookieSync(
|
|
118
132
|
fullUrl,
|
package/src/helpers.js
CHANGED
|
@@ -193,6 +193,21 @@ export default function Helpers(mpInstance) {
|
|
|
193
193
|
if ((options = arguments[i]) != null) {
|
|
194
194
|
// Extend the base object
|
|
195
195
|
for (name in options) {
|
|
196
|
+
// Prevent prototype pollution
|
|
197
|
+
// https://github.com/advisories/GHSA-jf85-cpcp-j695
|
|
198
|
+
if (
|
|
199
|
+
name === '__proto__' ||
|
|
200
|
+
name === 'constructor' ||
|
|
201
|
+
name === 'prototype'
|
|
202
|
+
) {
|
|
203
|
+
continue;
|
|
204
|
+
}
|
|
205
|
+
|
|
206
|
+
// Only copy own properties
|
|
207
|
+
if (!Object.prototype.hasOwnProperty.call(options, name)) {
|
|
208
|
+
continue;
|
|
209
|
+
}
|
|
210
|
+
|
|
196
211
|
src = target[name];
|
|
197
212
|
copy = options[name];
|
|
198
213
|
|
|
@@ -107,12 +107,14 @@ export interface IIdentityRequest {
|
|
|
107
107
|
): IdentityPreProcessResult;
|
|
108
108
|
}
|
|
109
109
|
|
|
110
|
+
export type AliasRequestScope = 'device' | 'mpid';
|
|
111
|
+
|
|
110
112
|
export interface IAliasRequest {
|
|
111
113
|
destinationMpid: MPID;
|
|
112
114
|
sourceMpid: MPID;
|
|
113
115
|
startTime: number;
|
|
114
116
|
endTime: number;
|
|
115
|
-
scope?:
|
|
117
|
+
scope?: AliasRequestScope;
|
|
116
118
|
}
|
|
117
119
|
|
|
118
120
|
export interface IAliasCallback {
|
|
@@ -151,7 +153,8 @@ export interface SDKIdentityApi {
|
|
|
151
153
|
): void;
|
|
152
154
|
createAliasRequest?(
|
|
153
155
|
sourceUser: IMParticleUser,
|
|
154
|
-
destinationUser: IMParticleUser
|
|
156
|
+
destinationUser: IMParticleUser,
|
|
157
|
+
scope?: AliasRequestScope
|
|
155
158
|
): IAliasRequest;
|
|
156
159
|
}
|
|
157
160
|
|
package/src/identity.js
CHANGED
|
@@ -195,6 +195,7 @@ export default function Identity(mpInstance) {
|
|
|
195
195
|
SourceMpid: aliasRequest.sourceMpid,
|
|
196
196
|
StartUnixtimeMs: aliasRequest.startTime,
|
|
197
197
|
EndUnixtimeMs: aliasRequest.endTime,
|
|
198
|
+
Scope: aliasRequest.scope,
|
|
198
199
|
};
|
|
199
200
|
},
|
|
200
201
|
|
|
@@ -744,7 +745,7 @@ export default function Identity(mpInstance) {
|
|
|
744
745
|
after applying this adjustment it will be impossible to create an aliasRequest passes the aliasUsers()
|
|
745
746
|
validation that the startTime must be less than the endTime
|
|
746
747
|
*/
|
|
747
|
-
createAliasRequest: function(sourceUser, destinationUser) {
|
|
748
|
+
createAliasRequest: function(sourceUser, destinationUser, scope) {
|
|
748
749
|
try {
|
|
749
750
|
if (!destinationUser || !sourceUser) {
|
|
750
751
|
mpInstance.Logger.error(
|
|
@@ -788,6 +789,7 @@ export default function Identity(mpInstance) {
|
|
|
788
789
|
sourceMpid: sourceUser.getMPID(),
|
|
789
790
|
startTime: startTime,
|
|
790
791
|
endTime: endTime,
|
|
792
|
+
scope: scope || 'device',
|
|
791
793
|
};
|
|
792
794
|
} catch (e) {
|
|
793
795
|
mpInstance.Logger.error(
|
|
@@ -120,6 +120,12 @@ const integrationMappingExternal: IntegrationIdMapping = {
|
|
|
120
120
|
mappedKey: 'SnapchatConversions.ClickId',
|
|
121
121
|
output: IntegrationOutputs.CUSTOM_FLAGS,
|
|
122
122
|
},
|
|
123
|
+
// Snapchat
|
|
124
|
+
// https://developers.snap.com/api/marketing-api/Conversions-API/UsingTheAPI#sending-click-id
|
|
125
|
+
_scid: {
|
|
126
|
+
mappedKey: 'SnapchatConversions.Cookie1',
|
|
127
|
+
output: IntegrationOutputs.CUSTOM_FLAGS,
|
|
128
|
+
},
|
|
123
129
|
};
|
|
124
130
|
|
|
125
131
|
const integrationMappingRokt: IntegrationIdMapping = {
|
|
@@ -368,10 +368,10 @@ function mParticleInstanceManager(this: IMParticleInstanceManager) {
|
|
|
368
368
|
aliasUsers: function(aliasRequest, callback) {
|
|
369
369
|
self.getInstance().Identity.aliasUsers(aliasRequest, callback);
|
|
370
370
|
},
|
|
371
|
-
createAliasRequest: function(sourceUser, destinationUser) {
|
|
371
|
+
createAliasRequest: function(sourceUser, destinationUser, scope) {
|
|
372
372
|
return self
|
|
373
373
|
.getInstance()
|
|
374
|
-
.Identity.createAliasRequest(sourceUser, destinationUser);
|
|
374
|
+
.Identity.createAliasRequest(sourceUser, destinationUser, scope);
|
|
375
375
|
},
|
|
376
376
|
getCurrentUser: function() {
|
|
377
377
|
return self.getInstance().Identity.getCurrentUser();
|