diff --git a/README.md b/README.md index 9ee33490..49c0da54 100644 --- a/README.md +++ b/README.md @@ -207,13 +207,14 @@ initLmcCookieConsentManager( // when loaded as a module, these options are passe ## Configuration options -| Option | Type | Default value | Description | -|---------------|-------------|--------------------------------|-------------------------------------------------------------------------------------------------------------------------------------------| -| `defaultLang` | string | 'cs' | Default language. One of `cs`, `de`, `en`, `hu`, `pl`, `ru`, `sk`, `uk`. This language will be used when autodetect is disabled or when it fails. | -| `autodetectLang`| boolean | true | Autodetect language from the browser. If autodetect fails or if unsupported language is detected, fallback to `defaultLang`.
When disabled, force language to `defaultLang`. | -| `companyNames`| array | ['LMC'] | Array of strings with company names. Adjust only when the consent needs to be given to multiple companies. [See example][examples-configuration]. | -| `config` | Object | {} | Override default config of the underlying library. For all parameters see [original library](https://github.com/orestbida/cookieconsent#all-available-options). | -| `on*` callbacks| function | (cookie, cookieConsent) => {} | See below for configurable callbacks. | +| Option | Type | Default value | Description | +|-----------------|-------------|---------------------------------|-------------------------------------------------------------------------------------------------------------------------------------------| +| `defaultLang` | string | 'cs' | Default language. One of `cs`, `de`, `en`, `hu`, `pl`, `ru`, `sk`, `uk`. This language will be used when autodetect is disabled or when it fails. | +| `autodetectLang`| boolean | true | Autodetect language from the browser. If autodetect fails or if unsupported language is detected, fallback to `defaultLang`.
When disabled, force language to `defaultLang`. | +| `companyNames` | array | ['LMC'] | Array of strings with company names. Adjust only when the consent needs to be given to multiple companies. [See example][examples-configuration]. | +| `consentCollectorApiUrl`| ?string | 'https://ccm.lmc.cz/(...)' | URL of the API where user consent information is sent. Null to disable sending data to the API. | +| `config` | Object | {} | Override default config of the underlying library. For all parameters see [original library](https://github.com/orestbida/cookieconsent#all-available-options). | +| `on*` callbacks | function | (cookie, cookieConsent) => {} | See below for configurable callbacks. | ### Supported languages diff --git a/examples/callbacks.html b/examples/callbacks.html index 39ff0f28..3cfd6cd9 100644 --- a/examples/callbacks.html +++ b/examples/callbacks.html @@ -80,6 +80,7 @@

Callbacks

{ autodetectLang: false, // do not detect language from the browser defaultLang: 'en', // use 'en' language by default + consentCollectorApiUrl: 'https://ccm.lmc.cz/local-data-acceptation-data-entries?Spot=(public,demo)', // override default URL for demo purposes; do not set custom consentCollectorApiUrl unless you have been explicitly guided to do so! onAccept: (cookie, cookieConsent) => { // any type of consent detected markCallbackCalled('onAccept'); }, diff --git a/examples/configuration.html b/examples/configuration.html index 454e4bc4..0f2ce944 100644 --- a/examples/configuration.html +++ b/examples/configuration.html @@ -80,6 +80,7 @@

Use cookieConsent instance

autodetectLang: false, // do not detect language from the browser defaultLang: 'en', // use 'en' language by default companyNames: ['LMC', 'Some Other Company', 'ACME'], // define custom company names to be shown in the consent text + consentCollectorApiUrl: 'https://ccm.lmc.cz/local-data-acceptation-data-entries?Spot=(public,demo)', // override default URL for demo purposes; do not set custom consentCollectorApiUrl unless you have been explicitly guided to do so! config: { // override default config of the underlying library, see https://github.com/orestbida/cookieconsent#all-available-options delay: 500, // show cookie consent banner after 500ms page_scripts: false, // disable third-party script management, see https://github.com/lmc-eu/cookie-consent-manager#third-party-scripts-loaded-via-script diff --git a/examples/index.html b/examples/index.html index 155baab5..0568a4a7 100644 --- a/examples/index.html +++ b/examples/index.html @@ -103,6 +103,7 @@

Allowed consent categories

{ autodetectLang: false, // do not detect language from the browser defaultLang: 'en', // use 'en' language by default + consentCollectorApiUrl: 'https://ccm.lmc.cz/local-data-acceptation-data-entries?Spot=(public,demo)', // override default URL for demo purposes; do not set custom consentCollectorApiUrl unless you have been explicitly guided to do so! onAccept: (cookie, cookieConsent) => { // any type of consent (including "only necessary") detected document.getElementById('onaccept-content').innerHTML = JSON.stringify(cookie) diff --git a/examples/theming.html b/examples/theming.html index 70bec754..a3c18a70 100644 --- a/examples/theming.html +++ b/examples/theming.html @@ -73,6 +73,7 @@

TODO

{ autodetectLang: false, // do not detect language from the browser defaultLang: 'en', // use 'en' language by default + consentCollectorApiUrl: 'https://ccm.lmc.cz/local-data-acceptation-data-entries?Spot=(public,demo)', // override default URL for demo purposes; do not set custom consentCollectorApiUrl unless you have been explicitly guided to do so! } ); }); diff --git a/src/LmcCookieConsentManager.js b/src/LmcCookieConsentManager.js index d0647024..2b78e131 100644 --- a/src/LmcCookieConsentManager.js +++ b/src/LmcCookieConsentManager.js @@ -9,10 +9,12 @@ import { config as configPl } from './languages/pl'; import { config as configRu } from './languages/ru'; import { config as configSk } from './languages/sk'; import { config as configUk } from './languages/uk'; +import submitConsent from './consentCollector'; const defaultOptions = { defaultLang: 'cs', autodetectLang: true, + consentCollectorApiUrl: 'https://ccm.lmc.cz/local-data-acceptation-data-entries', onFirstAccept: (cookie, cookieConsent) => {}, onFirstAcceptOnlyNecessary: (cookie, cookieConsent) => {}, onFirstAcceptAll: (cookie, cookieConsent) => {}, @@ -28,6 +30,7 @@ const defaultOptions = { * @param {Object} [args] - Options for cookie consent manager * @param {string} [args.defaultLang] - Default language. Must be one of predefined languages. * @param {boolean} [args.autodetectLang] - Autodetect language from the browser + * @param {?string} [args.consentCollectorApiUrl] - URL of the API where user consent information should be sent. Null to disable. * @param {function} [args.onFirstAccept] - Callback to be executed right after any consent is just accepted * @param {function} [args.onFirstAcceptOnlyNecessary] - Callback to be executed right after only necessary cookies are accepted * @param {function} [args.onFirstAcceptAll] - Callback to be executed right after all cookies are accepted @@ -47,6 +50,7 @@ const LmcCookieConsentManager = (serviceName, args) => { const { defaultLang, autodetectLang, + consentCollectorApiUrl, onFirstAccept, onFirstAcceptOnlyNecessary, onFirstAcceptAll, @@ -114,6 +118,10 @@ const LmcCookieConsentManager = (serviceName, args) => { }); } + if (consentCollectorApiUrl !== null) { + submitConsent(consentCollectorApiUrl, cookieConsent, acceptedOnlyNecessary); + } + onFirstAccept(cookie, cookieConsent); acceptedOnlyNecessary ? onFirstAcceptOnlyNecessary(cookie, cookieConsent) diff --git a/src/consentCollector.js b/src/consentCollector.js new file mode 100644 index 00000000..a3778f8b --- /dev/null +++ b/src/consentCollector.js @@ -0,0 +1,61 @@ +/** + * Submit information about consent level given by the user. + * + * @param {string} consentCollectorApiUrl + * @param {Object} cookieConsent + * @param {boolean} acceptedOnlyNecessary + */ +export const submitConsent = (consentCollectorApiUrl, cookieConsent, acceptedOnlyNecessary) => { + const payload = buildPayload(cookieConsent, acceptedOnlyNecessary); + + postDataToApi(consentCollectorApiUrl, payload); +}; + +/** + * @param {Object} cookieConsent + * @param {boolean} acceptedOnlyNecessary + * @returns {Object} + */ +const buildPayload = (cookieConsent, acceptedOnlyNecessary) => { + const cookieData = cookieConsent.get('data'); + const acceptedCategories = cookieConsent.get('level'); + // TODO: read actual categories once following is implemented in vanilla-cookieconsent: + // https://github.com/orestbida/cookieconsent/discussions/90#discussioncomment-1466886 + const rejectedCategories = acceptedOnlyNecessary + ? ['ad', 'analytics', 'functionality', 'personalization'] + : []; + + return { + data: { + type: 'localDataAcceptationDataEntries', + attributes: { + acceptation_id: cookieData.uid, + accept_type: acceptedOnlyNecessary ? 'accept_necessary' : 'accept_all', + accepted_categories: acceptedCategories, + rejected_categories: rejectedCategories, + revision: cookieConsent.get('revision'), + source: cookieData.serviceName, + }, + }, + }; +}; + +/** + * @param {string} apiUrl + * @param {Object} payload + * @return {Promise} + */ +const postDataToApi = async (apiUrl, payload) => { + const response = await fetch(apiUrl, { + method: 'POST', + headers: { + 'Content-Type': 'application/vnd.api+json', + Accept: 'application/vnd.api+json', + }, + body: JSON.stringify(payload), + }); + + return response.json(); +}; + +export default submitConsent;