This guide provides general technical implementation advice. It does not constitute legal advice. Consult with a qualified privacy professional to ensure full compliance with applicable laws.

Website owners are responsible for their website’s compliance with privacy laws. This includes responsibility for collecting and retaining a log of their visitors’ valid tracking consents where required.

A Consent Management Platform (CMP) is a tool that helps website owners ensure compliance with privacy laws by managing visitor consent for cookie-based or cookieless tracking. It presents website visitors with a consent banner explaining data processing activities and allows them to accept or decline specific purposes, such as analytics or marketing.

Didomi consent manager integration with Matomo can be implemented using the Matomo tracking code or Matomo Tag Manager. The Matomo Tag Manager method is covered in a separate guide.

This guide focuses on three consent methods using the Matomo tracking code.

Each method is based on different regulatory requirements, so it is important to consider your organisation’s legal obligations and tracking needs when integrating the CMP:

  1. Consent-based Tracking: For websites targeting users in countries that require prior consent for use of cookies and similar technologies for analytics and marketing (for example, most or EU and EEA countries), enable cookieless or cookie-based Matomo tracking only after obtaining visitor consent.

  2. Opt-out Tracking for CNIL Exemption: For organisations relying on the CNIL consent exemption for website analytics, limited tracking is permitted, provided that conditions of exemption are strictly met and users are offered a clear opt-out mechanism. CNIL exemption is strict and if any conditions of the CNIL exemption are not met, consent is also required.

  3. Adaptive Tracking: For websites operating outside the EU/UK/EEA, in countries where prior consent is either not required or only required when the analytics processes personal data, you can enable cookie-based tracking with consent and fallback to cookieless tracking if consent is not given (unless the visitor opts out of all tracking).

Before you start

Didomi offers extensive configuration options for advanced consent management setups such as enabling IAB Transparency and Consent Framework (TCF v2.2), creating multiple vendors, purposes, and consent notices for different regions. The example provided in this guide covers a general purpose-based integration where consent for analytics tracking is shared with Matomo.

If your tracking setup involves advanced configurations, refer to the official Didomi documentation for framework-specific implementation details and API usage.

  1. Set up your Didomi account.
  2. Define a Vendor (for Matomo) and the applicable Purposes.
  3. For Matomo, select Analytics (Purpose ID: analytics_tracking). Read the Didomi documentation on managing vendors and purposes.
  4. Purposes must be assigned to the Opt-in or Opt-out purposes (according to the consent method used).
  5. Take note of the Vendor ID and Purpose ID.
    view didomi data manager
  6. Complete the necessary steps to configure your Consent Notice in line with the consent method used and the legal requirements that apply to your website.
    apply regulations for consent notice
  7. After publishing the notice, copy your Didomi SDK snippet and paste it as the first tag within the <head> section of the web pages you are tracking. This example uses the default Didomi domain to load the SDK.
    copy didomi sdk snippet
  8. The Consent choices opening link (shown as step 4 above) is included in the consent handling script below.

In regions with strict privacy and ePrivacy laws, such as the EU or UK, websites must obtain explicit consent before collecting analytics data. Consent-based tracking ensures that no tracking occurs until a website visitor actively provides consent.

This method can operate in either cookieless (JavaScript-based) or cookie-based mode, but tracking is only activated after the visitor gives consent. When consent is revoked or denied, any existing Matomo cookies are removed from the visitor’s browser and tracking stops.

Install and modify the Matomo tracking code

  1. If you do not have the tracking code installed yet, go to Matomo > Administration Settings Cog Icon > Websites > Tracking Code and select the website you want to track.
  2. Copy the tracking code shown in the code box and paste into a text editor.
  3. Insert the line _paq.push(['requireConsent']); before _paq.push(['trackPageView']).
  4. Paste the modified tracking code inside the <head> tag on all the website pages you are tracking.
  5. If you already have the Matomo tracking code on the page, replace it with the updated tracking code:
<!-- Matomo -->
<!-- SAMPLE CODE - DO NOT COPY THIS -->
<!-- COPY THE TRACKING CODE FROM YOUR MATOMO DASHBOARD -->
<script>
  var _paq = window._paq = window._paq || [];
  _paq.push(['requireConsent']);
  _paq.push(['trackPageView']);
  _paq.push(['enableLinkTracking']);
  (function() {
    var u="//matomo/";
    _paq.push(['setTrackerUrl', u+'matomo.php']);
    _paq.push(['setSiteId', '1']);
  })();
</script>
<script src="//matomo/matomo.js"></script>
<!-- End Matomo Code -->

The integration relies on the Didomi SDK to collect and store consent for your configured vendor and purposes, and communicate user consent to Matomo. This script listens for Analytics consent events and enables or disables Matomo tracking depending on the user’s choice..

<script>
// --- REPLACE YOUR_VENDOR_ID` with the Vendor ID created in Didomi---
var VENDOR_CANDIDATES  = ['YOUR_VENDOR_ID'];
var PURPOSE_CANDIDATES = ['analytics_tracking'];

function idsFrom(x){ return Array.isArray(x) ? x.map(v=>v.id) : Object.keys(x||{}); }

function vendorGranted() {
  try {
    var vRaw = Didomi.getVendors && Didomi.getVendors();
    var vendorIds = idsFrom(vRaw);
    var existing  = VENDOR_CANDIDATES.filter(id => vendorIds.includes(id));
    if (!existing.length) return true; // no Matomo vendor in notice → don’t block on vendor
    return existing.some(id => !!Didomi.getUserConsentStatusForVendor(id));
  } catch(e){ return true; }
}

function purposeGranted() {
  try {
    var pRaw = Didomi.getPurposes && Didomi.getPurposes();
    var purposeIds = idsFrom(pRaw);
    var existing   = PURPOSE_CANDIDATES.filter(id => purposeIds.includes(id));
    if (!existing.length) return true; // no analytics purpose in notice - do not block on purpose
    return existing.some(id => !!Didomi.getUserConsentStatusForPurpose(id));
  } catch(e){ return true; }
}

function isGranted(){
  var v = vendorGranted(), p = purposeGranted();
  console.log('[Didomi] vendorOK=%s purposeOK=%s', v, p);
  return v && p;
}

function onGrant(){
  console.log('[Glue] consent granted then enable Matomo');
  _paq.push(['rememberConsentGiven']);
  _paq.push(['setConsentGiven']);
}
function onWithdraw(){ console.log('[Glue] consent not granted then disable Matomo'); 
_paq.push(['forgetConsentGiven']); }
function apply(){ isGranted() ? onGrant() : onWithdraw(); }

// Reliable ready hooks (SDK must be before this block)
window.didomiOnReady = window.didomiOnReady || [];
window.didomiOnReady.push(function(){ console.log('[Hook] didomiOnReady'); apply(); });
document.addEventListener('didomi-consent-changed', function(){ console.log('[Event] didomi-consent-changed'); setTimeout(apply,0); });
document.addEventListener('didomi-ready', function(){ console.log('[Event] didomi-ready'); apply(); });
</script>

<!-- User can review and reset consent preferences -->
<button id="open-preferences">Open preferences</button>
<button id="reset-consent">Reset consent</button>
<script>
  document.getElementById('open-preferences').onclick = function () {
    if (window.Didomi?.preferences?.show) Didomi.preferences.show();
  };
  document.getElementById('reset-consent').onclick = function () {
    if (window.Didomi?.reset) { Didomi.reset(); location.reload(); }
  };
</script>

Validate the integration

Once you have installed the Matomo tracking code and added the consent handling script to your website, you can test the tracking behaviour for different regions to validate your privacy compliance setup.

  • To simulate different locations, use a VPN during testing.
  • Open your website and use the Consent Notice to decline tracking consent.
  • In your Matomo instance, select the Visitors > Real-time report, and check that no tracking requests are sent.
  • Next, grant consent and verify that tracking starts in your Matomo instance.
  • If using cookie-based tracking, open the browser’s developer tools (press F12 or right click > Inspect) and view the Application (or Storage) > Cookies tab to confirm cookies were set.
  • Revoke/reset consent and confirm that Matomo tracking stops and cookies are deleted from the browser.

This simple test confirms that the integration correctly respects regional privacy requirements and only activates tracking after consent is granted. If you are experiencing errors or issues with the integration test, read the Troubleshooting section below.

Method 2: Opt-out Tracking (CNIL Exemption)

The French supervisory authority, the Commission nationale de l’informatique et des libertés (CNIL) allows specific configuration of Matomo Analytics to be used without prior consent, provided that strict conditions are met. This is commonly referred to as CNIL consent exemption for audience measurement tools.

Organisations relying on the CNIL consent exemption can track website visitors by default provided that all exemption conditions are met:

  • The data is collected only for audience measurement their visitors are informed about and can object to tracking via an opt-out mechanism;
  • The cookies or other tracking tools used solely for audience analytics;
  • The tracking meets required time limits and produces specific aggregated data sets; and
  • The trackers are not used for identification, profiling, or cross-site tracking of visitors.

Note: To comply with this exemption, you must implement the necessary settings in Matomo to ensure data collection remains privacy-friendly and adheres to CNIL’s guidelines.

Refer to the CNIL consent exemption for Matomo Analytics Configuration Guide (English version) or (French version).

While CNIL’s exemption is specific to France, supervisory authorities in a small number of other EU countries have also exempted narrow scope of website analytics from consent (with opt-out right). The Opt-out tracking method can also be used in the context of those exemptions, if Matomo is configured in line with the specific requirements. Refer to the ePrivacy Directive overview, National Implementations, and Matomo’s Website Analytics Guide for details.

To configure tracking under the CNIL exemption (opt-out model), it’s important to assess whether your site qualifies for this setup. Consult with your data privacy officer or legal team before relying on the CNIL exemption.

If you fully comply with CNIL’s criteria for exempt audience measurement tools, there are different approaches you can take to integrate with your consent manager platform (CMP).

  1. Your website targets visitors in countries where CNIL or very similar exemption exists (e.g., France, Spain, Italy), or you have an establishment in such countries:
    • Configure your CMP to either load Matomo Analytics cookies and start tracking without prior consent. Didomi offers a CNIL (France) configuration for the GDPR regulation. Edit Consent Notice > Customization > Specific settings:
      enable CNIL config
    • The CMP banner must clearly inform users about the use of consent exempt website analytics tracking and include a visible and easily accessible opt-out mechanism (e.g. a link to your privacy policy with an opt-out checkbox).
  2. If your website serves a broader audience that targets visitors from countries that require prior consent for cookie based or cookieless website analytics (e.g. most of EU countries):
    • Consider splitting your banner configuration if the CMP supports region-specific geotargeting and consent rules.
  3. Follow the steps in this guide, How to include a web analytics opt-out feature on your site to add the embedded Matomo opt-out form to your website. The form includes all required JavaScript to allow users to opt-out of tracking.
  4. Alternatively, you can create a custom opt-out form using HTML and JavaScript, as explained in this developer guide.

Validate the integration

Once configured, test the tracking behaviour and validate your privacy compliance setup.

  • Perform test actions on your website and view the Visitors > Real-time report to verify tracking requests are sent to Matomo.
  • Select to opt-out of tracking.
  • Open the browser’s developer tools (press F12 or right click > Inspect) and view the Application or Storage > Cookies tab to verify that the mtm_consent_removed cookie is set.
  • Perform test actions on your website and view the Real-time report to ensure no tracking requests are sent to Matomo after opting out.
  • Change the settings to opt back in and resume tracking to ensure tracking requests are sent to Matomo.

This test confirms that the integration respects the user’s choice to opt out and behaves in accordance with CNIL’s exemption criteria.

⚠️ If you use Matomo features like Heatmaps, User ID, Ecommerce, Advertising Conversion, or Session Recording, or you want to access or export raw data you must switch to Method 1 (Consent-based Tracking), as these features fall outside the exemption.

Method 3: Adaptive Tracking

The Adaptive Tracking method can be used in regions where prior consent for analytics cookies or other trackers:

  • are not legally required (but you want to minimise the data you collect),
  • are not required for pseudonymised non-sensitive personal data or
  • are only required if certain personal data is processed.

You can minimise the data you collect by configuring the Matomo privacy settings.

This method allows tracking to begin immediately in cookieless mode, with the option to request consent for cookie-based tracking. When the website visitor provides consent, tracking switches to cookie-based mode. If consent is denied or later revoked, tracking continues in cookieless mode.

Install and modify the Matomo tracking code

  1. If you do not have the tracking code installed yet, go to Matomo > Administration Settings Cog Icon > Websites > Tracking Code and select the website you want to track.
  2. Copy the tracking code shown in the code box and paste into a text editor.
  3. Insert the line _paq.push(['requireCookieConsent']); before _paq.push(['trackPageView']).
  4. Paste the modified tracking code inside the <head> tag on all the website pages you are tracking.
  5. If you already have the Matomo tracking code on the page, replace it with the updated tracking code:
<!-- Matomo -->
<!-- SAMPLE CODE - DO NOT COPY THIS -->
<!-- COPY THE TRACKING CODE FROM YOUR MATOMO DASHBOARD -->
<script>
  var _paq = window._paq = window._paq || [];
  _paq.push(['requireCookieConsent']);
  _paq.push(['trackPageView']);
  _paq.push(['enableLinkTracking']);
  (function() {
    var u="//matomo/";
    _paq.push(['setTrackerUrl', u+'matomo.php']);
    _paq.push(['setSiteId', '1']);
  })();
</script>
<script src="//matomo/matomo.js"></script>
<!-- End Matomo Code -->

The integration relies on the Didomi SDK to collect and store consent for your configured vendor and purposes, and communicate user consent to Matomo. Cookieless tracking is active by default. This script listens for Analytics consent events and enables cookies or disables Matomo tracking depending on the user’s choice.

<script>
// --- REPLACE YOUR_VENDOR_ID` with the Vendor ID created in Didomi---
var VENDOR_CANDIDATES  = ['YOUR_VENDOR_ID'];
var PURPOSE_CANDIDATES = ['analytics_tracking'];

function idsFrom(x){ return Array.isArray(x) ? x.map(v=>v.id) : Object.keys(x||{}); }

function vendorGranted() {
  try {
    var vRaw = Didomi.getVendors && Didomi.getVendors();
    var vendorIds = idsFrom(vRaw);
    var existing  = VENDOR_CANDIDATES.filter(id => vendorIds.includes(id));
    if (!existing.length) return true; // no Matomo vendor in notice → don’t block on vendor
    return existing.some(id => !!Didomi.getUserConsentStatusForVendor(id));
  } catch(e){ return true; }
}

function purposeGranted() {
  try {
    var pRaw = Didomi.getPurposes && Didomi.getPurposes();
    var purposeIds = idsFrom(pRaw);
    var existing   = PURPOSE_CANDIDATES.filter(id => purposeIds.includes(id));
    if (!existing.length) return true; // no analytics purpose in notice - do not block on purpose
    return existing.some(id => !!Didomi.getUserConsentStatusForPurpose(id));
  } catch(e){ return true; }
}

function isGranted(){
  var v = vendorGranted(), p = purposeGranted();
  console.log('[Didomi] vendorOK=%s purposeOK=%s', v, p);
  return v && p;
}

function onGrant(){
  console.log('[Glue] consent granted then enable Matomo');
  _paq.push(['rememberCookieConsentGiven']);
  _paq.push(['setCookieConsentGiven']);
}
function onWithdraw(){ console.log('[Glue] consent not granted then disable Matomo'); 
_paq.push(['forgetCookieConsentGiven']);
_paq.push(['deleteCookies']); // Ensures Matomo tracking cookies are removed when consent is withdrawn
}
function apply(){ isGranted() ? onGrant() : onWithdraw(); }

// Reliable ready hooks (SDK must be before this block)
window.didomiOnReady = window.didomiOnReady || [];
window.didomiOnReady.push(function(){ console.log('[Hook] didomiOnReady'); apply(); });
document.addEventListener('didomi-consent-changed', function(){ console.log('[Event] didomi-consent-changed'); setTimeout(apply,0); });
document.addEventListener('didomi-ready', function(){ console.log('[Event] didomi-ready'); apply(); });
</script>

<!-- User can review and reset consent preferences -->
<button id="open-preferences">Open preferences</button>
<button id="reset-consent">Reset consent</button>
<script>
  document.getElementById('open-preferences').onclick = function () {
    if (window.Didomi?.preferences?.show) Didomi.preferences.show();
  };
  document.getElementById('reset-consent').onclick = function () {
    if (window.Didomi?.reset) { Didomi.reset(); location.reload(); }
  };
</script>

Validate the integration

Once you have installed the Matomo tracking code and added the consent handling script to your website, you can test the tracking behaviour for different regions to validate your privacy compliance setup.

  • To simulate different locations, use a VPN during testing.
  • Open your website and use the Consent Notice to decline tracking consent.
  • In your Matomo instance, select the Visitors > Real-time report, and check that no tracking requests are sent.
  • Next, grant consent and verify that tracking starts in your Matomo instance.
  • Open the browser’s developer tools (press F12 or right click > Inspect) and view the Application (or Storage) > Cookies tab to confirm cookies were set.
  • Revoke/reset consent and confirm that Matomo tracking stops and cookies are deleted from the browser.

This simple test confirms that the integration correctly respects regional privacy requirements and only uses cookies after consent is granted. If you are experiencing errors or issues with the integration test, read the Troubleshooting section below.

Troubleshooting

If you are having tracking issues or the consent is not being managed correctly, follow these steps to identify and resolve the problem:

1. Load order matters

Place the Didomi SDK snippet as close as possible to the top of the <head> tag. The SDK must load **before any vendor scripts **to ensure that Didomi is fully initialised before Matomo checks for consent. Refer to the `official Didomi instructions for loading the SDK.

2. Check the Matomo tracking code

Your Matomo tracking code must include the requireConsent or requireCookieConsent method before any other tracking commands. This ensures that Matomo does not track or set cookies until the user explicitly grants consent through the Didomi Consent Notice. Read more about Implementing tracking or cookie consent with the Matomo JavaScript Tracking Client.

3. Confirm correct Vendor and Purpose ID

The Didomi Consent Notice must include the exact vendor ID and purpose ID that your script checks for. For example, if your Matomo vendor ID is matomo-AbCdE and your analytics purpose ID is analytics_tracking, those same values must be used in your script.

If the IDs in the consent handling script do not match what is configured in the Didomi Console, Didomi will always block Matomo tracking. If you make any changes to your Consent Notice, republish, so the latest version is live.

Note: The Didomi SDK snippet references your Didomi Public API Key and the Consent Notice ID. Ensure these are the correct values included in the SDK.

4. Review security policy

If you are loading the SDK from the default Didomi domain, the following domains must be whitelisted in your site’s Content Security Policy:

https://sdk.privacy-center.org/
https://api.privacy-center.org/

If either is missing, the SDK will fail to load or communicate with Didomi’s servers and failed network requests or console messages might be displayed such as loader.js failed to load. When testing, disable strict tracking protection or ad-blockers as some browsers may block sdk.privacy-center.org by default.

Disclaimer: The use of any third-party tools (plugins, extensions, platforms, APIs, widgets, etc.) is at your own risk. Matomo does not own, control, maintain or support any third-party tools that integrate with our product. We recommend checking your privacy setup is correctly configured across your environment when using any third-party tools.

Previous FAQ: How to integrate CookieScript CMP with Matomo