media/js/firefox/landing/get/marketing-opt-out.es6.js (121 lines of code) (raw):
/*
* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at https://mozilla.org/MPL/2.0/.
*/
import {
hasConsentCookie,
getConsentCookie,
setConsentCookie,
consentRequired,
dntEnabled,
gpcEnabled
} from '../../../base/consent/utils.es6';
const MarketingOptOut = {};
/**
* Processes attribution changes depending on checkbox state.
* @param {Boolean} checked - checkbox target value.
*/
MarketingOptOut.processAttributionRequest = (checked) => {
let previousPreferenceCookie;
/**
* Preserve previous preference cookie consent state if one exists
*/
if (hasConsentCookie()) {
const cookie = getConsentCookie();
previousPreferenceCookie = cookie.preference;
}
/**
* If checked, consent to analytics and initiate attribution.
*/
if (checked) {
setConsentCookie({
analytics: true,
preference:
previousPreferenceCookie !== undefined &&
previousPreferenceCookie !== null
? previousPreferenceCookie
: true
});
window.Mozilla.StubAttribution.init(() => {
/**
* Rebind event listeners only after attribution
* request has been successful.
*/
MarketingOptOut.bindEvents();
});
} else {
/**
* Else set a cookie that rejects analytics.
* Remove all existing attribution data.
*/
setConsentCookie({
analytics: false,
preference:
previousPreferenceCookie !== undefined &&
previousPreferenceCookie !== null
? previousPreferenceCookie
: true
});
window.Mozilla.StubAttribution.removeAttributionData();
MarketingOptOut.bindEvents();
}
};
/**
* Handles checkbox change event. Because checkbox state must be
* synced between all checkboxes on the page, we must temporarily
* unbind event listeners to avoid triggering multiple change
* events at once.
* @param {Object} e - change event object.
*/
MarketingOptOut.handleChangeEvent = (e) => {
MarketingOptOut.unbindEvents();
MarketingOptOut.setCheckboxState(e.target.checked);
MarketingOptOut.processAttributionRequest(e.target.checked);
};
/**
* Unbinds checkbox change event listeners and disables
* inputs when unbound.
*/
MarketingOptOut.unbindEvents = () => {
const checkboxes = document.querySelectorAll(
'.marketing-opt-out-checkbox-input'
);
for (let i = 0; i < checkboxes.length; i++) {
checkboxes[i].removeEventListener(
'change',
MarketingOptOut.handleChangeEvent,
false
);
checkboxes[i].disabled = true;
}
};
/**
* Binds checkbox change event listeners and removes
* disabled states on inputs when bound.
*/
MarketingOptOut.bindEvents = () => {
const checkboxes = document.querySelectorAll(
'.marketing-opt-out-checkbox-input'
);
for (let i = 0; i < checkboxes.length; i++) {
checkboxes[i].addEventListener(
'change',
MarketingOptOut.handleChangeEvent,
false
);
checkboxes[i].disabled = false;
}
};
/**
* Sets the checked state of all checkbox inputs.
* @param {Boolean} checked state
*/
MarketingOptOut.setCheckboxState = (checked) => {
const checkboxes = document.querySelectorAll(
'.marketing-opt-out-checkbox-input'
);
for (let i = 0; i < checkboxes.length; i++) {
checkboxes[i].checked = checked;
}
};
/**
* Determines if marketing opt-out checkboxes should
* be displayed.
* @returns {Boolean}
*/
MarketingOptOut.shouldShowCheckbox = () => {
let show = false;
/**
* Has the visitor set a browser-level privacy flag?
*/
if (dntEnabled() || gpcEnabled()) {
show = false;
} else if (window.Mozilla.StubAttribution.hasCookie()) {
/**
* Does the visitor have an existing attribution cookie?
*/
show = true;
} else if (hasConsentCookie()) {
/**
* Does the visitor have an existing analytics consent cookie?
*/
const cookie = getConsentCookie();
show = cookie.analytics ? true : false;
} else {
/**
* Is the visitor in EU/EAA?
*/
show = consentRequired() ? false : true;
}
return show;
};
/**
* Displays checkboxes via CSS by removing the `hidden`
* class on their corresponding `<label>` parent elements.
* Also sets `checked=true` to enforce opt-out state.
*/
MarketingOptOut.showCheckbox = () => {
const labels = document.querySelectorAll(
'.marketing-opt-out-checkbox-label'
);
for (let i = 0; i < labels.length; i++) {
labels[i].classList.remove('hidden');
labels[i].querySelector('.marketing-opt-out-checkbox-input').checked =
true;
}
};
/**
* Determines if marketing opt-out logic should run,
* based on existing attribution requirements.
* @returns {Boolean}
*/
MarketingOptOut.meetsRequirements = () => {
return (
typeof window.Mozilla.StubAttribution !== 'undefined' &&
window.Mozilla.StubAttribution.meetsRequirements()
);
};
/**
* Initializes marketing opt-out flow
* @returns {Boolean}.
*/
MarketingOptOut.init = () => {
if (!MarketingOptOut.meetsRequirements()) {
return false;
}
if (MarketingOptOut.shouldShowCheckbox()) {
MarketingOptOut.showCheckbox();
MarketingOptOut.bindEvents();
return true;
}
return false;
};
export default MarketingOptOut;