react-consent-management-banner
Version:
Beautiful and Highly Customizable GDPR/ePrivacy React Consent and Cookie Management Library for React and Next.js
270 lines (269 loc) • 16.4 kB
JavaScript
;
var __assign = (this && this.__assign) || function () {
__assign = Object.assign || function(t) {
for (var s, i = 1, n = arguments.length; i < n; i++) {
s = arguments[i];
for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p))
t[p] = s[p];
}
return t;
};
return __assign.apply(this, arguments);
};
var __importDefault = (this && this.__importDefault) || function (mod) {
return (mod && mod.__esModule) ? mod : { "default": mod };
};
Object.defineProperty(exports, "__esModule", { value: true });
exports.CookieConsent = CookieConsent;
var react_1 = __importDefault(require("react"));
var Banner = function (_a) {
var _b, _c, _d, _e, _f, _g, _h;
var mergedConfig = _a.mergedConfig, handleSavePreferences = _a.handleSavePreferences, setShowPreferences = _a.setShowPreferences;
var _j = mergedConfig.banner, position = _j.position, title = _j.title, links = _j.links, button = _j.button, className = _j.className;
return (react_1.default.createElement("div", { className: "cookie-banner-wrapper ".concat(position) },
react_1.default.createElement("div", { className: "cookie-banner".concat(className ? " ".concat(className) : "") },
react_1.default.createElement("p", null,
title,
react_1.default.createElement("a", { href: (_b = links.cookiePolicy) === null || _b === void 0 ? void 0 : _b.url, target: "_blank", rel: "noreferrer" }, (_c = links.cookiePolicy) === null || _c === void 0 ? void 0 : _c.title)),
react_1.default.createElement("div", { className: "cookie-buttons" },
react_1.default.createElement("button", { onClick: function () { return handleSavePreferences("all"); } }, button.acceptAlText),
react_1.default.createElement("button", { onClick: function () { return handleSavePreferences("essential"); } }, button.rejectNonEssentialText),
react_1.default.createElement("button", { onClick: function () { return setShowPreferences(true); }, className: "btn-outline" }, button.preferencesText)),
react_1.default.createElement("div", null,
react_1.default.createElement("a", { href: (_d = links.privacyPolicy) === null || _d === void 0 ? void 0 : _d.url, target: "_blank", rel: "noreferrer" }, (_e = links.privacyPolicy) === null || _e === void 0 ? void 0 : _e.title),
react_1.default.createElement("span", null, "-"),
react_1.default.createElement("a", { href: (_f = links.terms) === null || _f === void 0 ? void 0 : _f.url, target: "_blank", rel: "noreferrer" }, (_g = links.terms) === null || _g === void 0 ? void 0 : _g.title), (_h = links.moreLinks) === null || _h === void 0 ? void 0 :
_h.map(function (ml, i) {
return (react_1.default.createElement(react_1.default.Fragment, null,
react_1.default.createElement("span", null, "-"),
react_1.default.createElement("a", { key: i, href: ml === null || ml === void 0 ? void 0 : ml.url, target: "_blank", rel: "noreferrer" }, ml === null || ml === void 0 ? void 0 : ml.title)));
})))));
};
var CookieModal = function (_a) {
var _b;
var mergedConfig = _a.mergedConfig, togglePreference = _a.togglePreference, handleSavePreferences = _a.handleSavePreferences, handleClose = _a.handleClose, preferences = _a.preferences;
var _c = mergedConfig.preferences, button = _c.button, title = _c.title, para = _c.para;
return (react_1.default.createElement("div", { className: "cookie-modal" },
react_1.default.createElement("div", { className: "cookie-modal-content" },
react_1.default.createElement("span", { className: "cookie-modal__close", onClick: handleClose }, "\u00D7"),
react_1.default.createElement("h3", null, title),
para && react_1.default.createElement("p", null, para),
react_1.default.createElement("ul", null, (_b = mergedConfig.preferences.options) === null || _b === void 0 ? void 0 : _b.map(function (opt) { return (react_1.default.createElement("li", { key: opt.key },
react_1.default.createElement("label", null,
react_1.default.createElement("input", { type: "checkbox", disabled: opt.alwaysEnabled, checked: preferences[opt.key], onChange: function () { return togglePreference(opt.key); } }),
opt.label),
react_1.default.createElement("p", null, opt.description))); })),
react_1.default.createElement("div", { className: "cookie-modal__btn" },
react_1.default.createElement("button", { className: "btn-outline", onClick: handleClose }, button === null || button === void 0 ? void 0 : button.goBackText),
react_1.default.createElement("button", { onClick: handleSavePreferences }, button === null || button === void 0 ? void 0 : button.savePreferencesText)))));
};
var defaultConfig = {
banner: {
title: "We use cookies on our site to enhance your user experience, provide personalized content, and analyze our traffic.",
position: "bottom",
className: undefined,
button: {
acceptAlText: "Accept All",
rejectNonEssentialText: "Reject Non-Essentials",
preferencesText: "Preferences",
},
links: {
cookiePolicy: { title: "Cookie Policy", url: "/cookie-policy" },
privacyPolicy: { title: "Privacy Policy", url: "/privacy-policy" },
terms: { title: "Terms & Conditions", url: "/terms-and-conditions" },
moreLinks: [],
},
},
preferences: {
title: "Customize your cookie preferences",
para: "We respect your right to privacy. You can choose not to allow some types of cookies. Your cookie preferences will apply across our website.",
button: { savePreferencesText: "Save Preferences", goBackText: "Go Back" },
className: undefined,
options: [
{
key: "necessary_storage",
label: "Necessary",
alwaysEnabled: true,
description: "These cookies are necessary for the website to function properly and cannot be switched off. They help with things like logging in and setting your privacy preferences.",
},
{
key: "security_storage",
label: "Security",
alwaysEnabled: true,
description: "These cookies are security for the website to function properly and cannot be switched off.",
},
{
key: "functionality_storage",
label: "Functionality",
alwaysEnabled: true,
description: "These cookies allow the website to remember choices you make, such as your language or region, and provide enhanced, more personalized features. They may also enable services like video playback or live chats",
},
{
key: "ad_storage",
label: "Advertisement Storage",
description: "These cookies are used to deliver advertisements that are more relevant to you. They may also limit how often you see an ad and help measure the effectiveness of advertising campaigns.",
},
{
key: "ad_personalization",
label: "Advertisement Personalization",
description: "These cookies allow the website to deliver personalized ads based on your interests, browsing behavior, or previous interactions. They help tailor advertising content to make it more relevant to you.",
},
{
key: "ad_user_data",
label: "Advertisement User Data",
description: "These cookies enable the collection of user data for advertising purposes, such as demographics or engagement metrics. This data supports ad measurement, targeting, and optimization.",
},
{
key: "analytics_storage",
label: "Analytics",
description: "These cookies help us understand how visitors interact with the website by collecting and reporting information anonymously. They enable us to improve site performance and user experience.",
},
{
key: "personalization_storage",
label: "Personalization",
description: "These cookies enable the website to tailor content and recommendations based on your behavior and preferences, providing a more customized browsing experience.",
},
],
},
cookieFloatingButton: {
position: "bottom-right",
Component: function (props) { return (react_1.default.createElement("svg", __assign({ xmlns: "http://www.w3.org/2000/svg", fill: "none", stroke: "currentColor", viewBox: "0 0 512 512" }, props),
react_1.default.createElement("path", { d: "M257.5 27.6c-.8-5.4-4.9-9.8-10.3-10.6c-22.1-3.1-44.6 .9-64.4 11.4l-74 39.5C89.1 78.4 73.2 94.9 63.4 115L26.7 190.6c-9.8 20.1-13 42.9-9.1 64.9l14.5 82.8c3.9 22.1 14.6 42.3 30.7 57.9l60.3 58.4c16.1 15.6 36.6 25.6 58.7 28.7l83 11.7c22.1 3.1 44.6-.9 64.4-11.4l74-39.5c19.7-10.5 35.6-27 45.4-47.2l36.7-75.5c9.8-20.1 13-42.9 9.1-64.9c-.9-5.3-5.3-9.3-10.6-10.1c-51.5-8.2-92.8-47.1-104.5-97.4c-1.8-7.6-8-13.4-15.7-14.6c-54.6-8.7-97.7-52-106.2-106.8zM208 144a32 32 0 1 1 0 64 32 32 0 1 1 0-64zM144 336a32 32 0 1 1 64 0 32 32 0 1 1 -64 0zm224-64a32 32 0 1 1 0 64 32 32 0 1 1 0-64z" }))); },
show: true,
},
backgroundColor: "#fff",
linkColor: "#6ac3ff",
buttonBackgroundColor: "#0073e6",
textColor: "#000",
onPreferencesChange: function () { },
getConsentGiven: function () { },
getConsentPreferences: function () { },
};
function CookieConsent(_a) {
var _b;
var GA_TRACKING_ID = _a.GA_TRACKING_ID, _c = _a.config, config = _c === void 0 ? defaultConfig : _c;
var _d = react_1.default.useState(false), showBanner = _d[0], setShowBanner = _d[1];
var _e = react_1.default.useState(false), showPreferences = _e[0], setShowPreferences = _e[1];
var _f = react_1.default.useState({}), preferences = _f[0], setPreferences = _f[1];
var _g = react_1.default.useState(false), consentGiven = _g[0], setConsentGiven = _g[1];
var mergedConfig = __assign(__assign({}, defaultConfig), config);
var setTheme = react_1.default.useCallback(function () {
var root = document.documentElement;
root.style.setProperty("--cookie-consent-background-color", mergedConfig.backgroundColor);
root.style.setProperty("--cookie-consent-link-color", mergedConfig.linkColor);
root.style.setProperty("--cookie-consent-button-background-color", mergedConfig.buttonBackgroundColor);
root.style.setProperty("--cookie-consent-text-color", mergedConfig.textColor);
}, [
mergedConfig.backgroundColor,
mergedConfig.linkColor,
mergedConfig.buttonBackgroundColor,
mergedConfig.textColor,
]);
var getGtagAds = function (props) {
if (props.isDefault) {
return config.preferences.options.reduce(function (com, curr) {
var _a;
return __assign(__assign({}, com), (_a = {}, _a[curr.key] = curr.alwaysEnabled ? "granted" : "denied", _a));
}, {});
}
props = props;
return config.preferences.options.reduce(function (com, curr) {
var _a;
return __assign(__assign({}, com), (_a = {}, _a[curr.key] = props[curr.key] ? "granted" : "denied", _a));
}, {});
};
var updateScript = function (config, isDefault) {
if (isDefault === void 0) { isDefault = false; }
if (!window.gtag) {
window.dataLayer = window.dataLayer || [];
window.gtag = function () {
window.dataLayer.push(arguments);
};
console.info("Selected ".concat(isDefault ? "default" : "custom", " preferences:"), config);
window.gtag("consent", "default", config);
var script = document.createElement("script");
script.src = "https://www.googletagmanager.com/gtag/js?id=".concat(GA_TRACKING_ID);
script.async = true;
document.head.appendChild(script);
script.onload = function () {
window.gtag("js", new Date());
window.gtag("config", GA_TRACKING_ID);
};
}
else {
console.info("Selected ".concat(isDefault ? "default" : "custom", " preferences:"), config);
window.gtag("consent", isDefault ? "default" : "update", config);
}
};
react_1.default.useEffect(function () {
setTheme();
if (!GA_TRACKING_ID) {
console.error("GA_TRACKING_ID is required for Google Analytics.");
return;
}
var saved = localStorage.getItem("cookiePreferences");
if (!saved) {
handleSavePreferences("essential", true);
setShowBanner(true);
}
else {
var preference = JSON.parse(saved);
setPreferences(preference);
setConsentGiven(true);
}
}, [setTheme, mergedConfig.preferences.options]);
var handleSavePreferences = function (prefType, isDefault) {
var _a, _b;
if (isDefault === void 0) { isDefault = false; }
var prefToSave = {};
if (prefType == "all") {
mergedConfig.preferences.options.forEach(function (opt) {
prefToSave[opt.key] = true;
});
}
else if (prefType == "essential") {
(_a = mergedConfig.preferences.options) === null || _a === void 0 ? void 0 : _a.forEach(function (opt) {
prefToSave[opt.key] = !!opt.alwaysEnabled;
});
}
else {
prefToSave = __assign({}, preferences);
(_b = mergedConfig.preferences.options) === null || _b === void 0 ? void 0 : _b.filter(function (opt) { return opt === null || opt === void 0 ? void 0 : opt.alwaysEnabled; }).forEach(function (opt) {
prefToSave[opt.key] = !!opt.alwaysEnabled;
});
}
if (isDefault) {
var pref = getGtagAds({ isDefault: true });
updateScript(pref, true);
setPreferences(prefToSave);
config.onPreferencesChange(prefToSave, false);
}
else {
var pref = getGtagAds(prefToSave);
updateScript(pref);
localStorage.setItem("cookiePreferences", JSON.stringify(prefToSave));
setShowPreferences(false);
setShowBanner(false);
setConsentGiven(true);
setPreferences(prefToSave);
config.onPreferencesChange(prefToSave, true);
}
};
var togglePreference = function (key) {
setPreferences(function (prev) {
var _a;
return (__assign(__assign({}, prev), (_a = {}, _a[key] = !prev[key], _a)));
});
};
config.getConsentGiven = react_1.default.useCallback(function () {
return consentGiven;
}, [consentGiven]);
config.getConsentPreferences = react_1.default.useCallback(function () {
return preferences;
}, [preferences]);
return (react_1.default.createElement(react_1.default.Fragment, null,
!showPreferences && showBanner && (react_1.default.createElement(Banner, { mergedConfig: mergedConfig, handleSavePreferences: handleSavePreferences, setShowPreferences: setShowPreferences })),
showPreferences && (react_1.default.createElement(CookieModal, { mergedConfig: mergedConfig, togglePreference: togglePreference, handleSavePreferences: handleSavePreferences, handleClose: function () { return setShowPreferences(false); }, preferences: preferences })),
((_b = mergedConfig.cookieFloatingButton) === null || _b === void 0 ? void 0 : _b.show) && consentGiven && (react_1.default.createElement("button", { className: "cookie-settings-button ".concat(mergedConfig.cookieFloatingButton.position), onClick: function () { return setShowPreferences(true); } },
react_1.default.createElement(mergedConfig.cookieFloatingButton.Component, null)))));
}