Skip to content

Commit

Permalink
Merge pull request #971 from matomo-org/PG-4039-google-consent-tag
Browse files Browse the repository at this point in the history
Adds Google consent mode tag, #PG-4039
  • Loading branch information
AltamashShaikh authored Jan 14, 2025
2 parents b71e23d + 9bf942a commit c2345e7
Show file tree
Hide file tree
Showing 13 changed files with 291 additions and 16 deletions.
2 changes: 1 addition & 1 deletion Template/Tag/AxeptioTag.php
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@ public function getDescription()

public function getCategory()
{
return Piwik::translate('TagManager_ConsentManagementPlatform');
return Piwik::translate('TagManager_ConsentManagement');
}

public function getIcon()
Expand Down
2 changes: 1 addition & 1 deletion Template/Tag/CookieYesTag.php
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@ public function getDescription()

public function getCategory()
{
return Piwik::translate('TagManager_ConsentManagementPlatform');
return Piwik::translate('TagManager_ConsentManagement');
}

public function getIcon()
Expand Down
2 changes: 1 addition & 1 deletion Template/Tag/CookiebotTag.php
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@ public function getHelp()

public function getCategory()
{
return Piwik::translate('TagManager_ConsentManagementPlatform');
return Piwik::translate('TagManager_ConsentManagement');
}

public function getIcon()
Expand Down
100 changes: 100 additions & 0 deletions Template/Tag/GoogleConsentModeV2Tag.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,100 @@
<?php

/**
* Matomo - free/libre analytics platform
*
* @link https://matomo.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*/

namespace Piwik\Plugins\TagManager\Template\Tag;

use Piwik\Piwik;
use Piwik\Settings\FieldConfig;
use Piwik\Url;
use Piwik\Validators\NotEmpty;

class GoogleConsentModeV2Tag extends BaseTag
{
public function getName()
{
// By default, the name will be automatically fetched from the TagManager_CustomHtmlTagName translation key.
// you can either adjust/create/remove this translation key, or return a different value here directly.
return parent::getName();
}

public function getDescription()
{
// By default, the description will be automatically fetched from the TagManager_CustomHtmlTagDescription
// translation key. you can either adjust/create/remove this translation key, or return a different value
// here directly.
return parent::getDescription();
}

public function getHelp()
{
// By default, the help will be automatically fetched from the TagManager_CustomHtmlTagHelp translation key.
// you can either adjust/create/remove this translation key, or return a different value here directly.
return parent::getHelp();
}

public function getCategory()
{
return Piwik::translate('TagManager_ConsentManagement');
}

public function getIcon()
{
// You may optionally specify a path to an image icon URL, for example:
//
// return 'plugins/TagManager/images/MyIcon.png';
//
// to not return default icon call:
// return parent::getIcon();
//
// The image should have ideally a resolution of about 64x64 pixels.
return 'plugins/TagManager/images/icons/google-consent-mode.svg';
}

public function getParameters()
{
$default = [
['consent_type' => 'ad_storage', 'consent_state' => 'granted'],
['consent_type' => 'ad_user_data', 'consent_state' => 'granted'],
['consent_type' => 'ad_personalization', 'consent_state' => 'granted'],
['consent_type' => 'analytics_storage', 'consent_state' => 'granted'],
['consent_type' => 'functionality_storage', 'consent_state' => 'granted'],
['consent_type' => 'personalization_storage', 'consent_state' => 'granted'],
['consent_type' => 'security_storage', 'consent_state' => 'granted'],
];

return array(
$this->makeSetting('consentAction', 'update', FieldConfig::TYPE_ARRAY, function (FieldConfig $field) {
$field->title = Piwik::translate('TagManager_GoogleConsentModeV2TagConsentActionTitle');
$field->description = Piwik::translate('TagManager_GoogleConsentModeV2TagConsentActionDescription');
$field->uiControl = FieldConfig::UI_CONTROL_SINGLE_SELECT;
$field->availableValues = array(
'default' => 'default',
'update' => 'update',
);
$field->validators[] = new NotEmpty();
}),

$this->makeSetting('consentTypes', $default, FieldConfig::TYPE_ARRAY, function (FieldConfig $field) {
$field->uiControl = FieldConfig::UI_CONTROL_MULTI_TUPLE;
$field->title = Piwik::translate('TagManager_GoogleConsentModeV2TagConsentTypesTitle');
$faqURL = Url::addCampaignParametersToMatomoLink('https://matomo.org/faq/tag-manager/google-consent-tag-in-matomo-tag-manager/', null, null, 'Tag.TagManager.GoogleConsentMode');
$field->inlineHelp = Piwik::translate('TagManager_GoogleConsentModeV2TagConsentTypesDescription', ['<a href="' . $faqURL . '" target="_blank" rel="noreferrer noopener">', '</a>']);

$field1 = new FieldConfig\MultiPair(Piwik::translate('TagManager_GoogleConsentModeV2TagConsentTypeTitle'), 'consent_type', FieldConfig::UI_CONTROL_TEXT);
$field1->customFieldComponent = self::FIELD_VARIABLE_COMPONENT;

$field2 = new FieldConfig\MultiPair(Piwik::translate('TagManager_GoogleConsentModeV2TagConsentStateTitle'), 'consent_state', FieldConfig::UI_CONTROL_TEXT);
$field2->customFieldComponent = self::FIELD_VARIABLE_COMPONENT;

$field->uiControlAttributes['field1'] = $field1->toArray();
$field->uiControlAttributes['field2'] = $field2->toArray();
}),
);
}
}
23 changes: 23 additions & 0 deletions Template/Tag/GoogleConsentModeV2Tag.web.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
(function () {
return function (parameters, TagManager) {
this.fire = function () {

var consentAction = parameters.get("consentAction")[0];
var consentTypes = parameters.get("consentTypes");

var typesObject = {};
consentTypes.forEach(function (type) {
if (type.consent_type && type.consent_state) {
typesObject[type.consent_type] = type.consent_state;
}
});

window.dataLayer = window.dataLayer || [];
function gtag() {
window.dataLayer.push(arguments);
}
gtag("consent", consentAction, typesObject);

};
};
})();
2 changes: 1 addition & 1 deletion Template/Tag/OneTrustTag.php
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@ public function getDescription()

public function getCategory()
{
return Piwik::translate('TagManager_ConsentManagementPlatform');
return Piwik::translate('TagManager_ConsentManagement');
}

public function getIcon()
Expand Down
10 changes: 10 additions & 0 deletions images/icons/google-consent-mode.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
11 changes: 10 additions & 1 deletion lang/en.json
Original file line number Diff line number Diff line change
Expand Up @@ -994,6 +994,7 @@
"GoogleTagTagIdTitle": "Tag ID",
"GoogleTagTagIdDescription": "A tag ID is an identifier that you put on your page to load a given Google tag. %1$sLearn more.%2$s",
"ConsentManagementPlatform": "Consent Management Platform",
"ConsentManagement": "Consent Management",
"CookiebotTagName": "Cookiebot",
"CookiebotTagDescription": "Cookiebot CMP makes the use of cookies and online tracking of your website GDPR compliant.",
"CookiebotTagHelp": "",
Expand Down Expand Up @@ -1167,6 +1168,14 @@
"MatomoConfigurationMatomoSetCountPreRenderedDescription": "If enabled, it will count sites in pre-rendered state.",
"MatomoConfigurationMatomoSetRequestQueueIntervalTitle": "Set Request Queue Interval",
"MatomoConfigurationMatomoSetRequestQueueIntervalDescription": "Defines after how many ms a queued requests will be executed after the request was queued initially. The higher the value the more tracking requests can be sent together at once. interval has to be at least 1000 (1000ms = 1s) and defaults to 2.5 seconds.",
"ErrorDeleteReferencedVariable": "This variable is in use elsewhere and cannot be deleted. Please remove all references to it and try again."
"ErrorDeleteReferencedVariable": "This variable is in use elsewhere and cannot be deleted. Please remove all references to it and try again.",
"GoogleConsentModeV2TagName": "Google Consent Mode",
"GoogleConsentModeV2TagDescription": "Consent mode v2 allows you to communicate to Google the consent status of your users regarding cookies or application IDs.",
"GoogleConsentModeV2TagConsentActionTitle": "Consent mode action",
"GoogleConsentModeV2TagConsentActionDescription": "Select 'default' to set default values, and 'update' to handle users consent.",
"GoogleConsentModeV2TagConsentTypesTitle": "Consent type",
"GoogleConsentModeV2TagConsentTypesDescription": "The consent state must be 'denied' before the user gives consent. Once consent is received, you can trigger this tag with the action mode set to 'update' and all consents state set to 'granted' for all consent types. (All consent types are available in the Google documentation). Consent state must be 'denied' or 'granted', no other values are allowed. %1$sLearn more%2$s.",
"GoogleConsentModeV2TagConsentTypeTitle": "Consent type",
"GoogleConsentModeV2TagConsentStateTitle": "Consent state"
}
}
4 changes: 4 additions & 0 deletions stylesheets/manageEdit.less
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,10 @@
width: ~"calc(100% - 60px)";
}

.fieldUiControl:has(input[id^='consentTypes-p1-']) {
width: 300px !important;
}

.innerFormField input, select{
width: 100%;
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -1477,13 +1477,13 @@
</types>
</row>
<row>
<name>Consent Management Platform</name>
<name>Consent Management</name>
<types>
<row>
<id>Axeptio</id>
<name>Axeptio</name>
<description>Axeptio is a low-code Consent Management Platform.</description>
<category>Consent Management Platform</category>
<category>Consent Management</category>
<icon>plugins/TagManager/images/icons/axeptio.svg</icon>
<help />
<order>9999</order>
Expand Down Expand Up @@ -1519,7 +1519,7 @@
<id>CookieYes</id>
<name>CookieYes</name>
<description>CookieYes is a cookie consent solution that helps your website achieve GDPR and CCPA compliance.</description>
<category>Consent Management Platform</category>
<category>Consent Management</category>
<icon>plugins/TagManager/images/icons/cookieyes.svg</icon>
<help />
<order>9999</order>
Expand Down Expand Up @@ -1555,7 +1555,7 @@
<id>Cookiebot</id>
<name>Cookiebot</name>
<description>Cookiebot CMP makes the use of cookies and online tracking of your website GDPR compliant.</description>
<category>Consent Management Platform</category>
<category>Consent Management</category>
<icon>plugins/TagManager/images/icons/cookiebot.svg</icon>
<help />
<order>9999</order>
Expand Down Expand Up @@ -1587,11 +1587,140 @@
</row>
</parameters>
</row>
<row>
<id>GoogleConsentModeV2</id>
<name>Google Consent Mode</name>
<description>Consent mode v2 allows you to communicate to Google the consent status of your users regarding cookies or application IDs.</description>
<category>Consent Management</category>
<icon>plugins/TagManager/images/icons/google-consent-mode.svg</icon>
<help />
<order>9999</order>
<contexts>
<row>web</row>
</contexts>
<hasAdvancedSettings>1</hasAdvancedSettings>
<isCustomTemplate>0</isCustomTemplate>
<parameters>
<row>
<name>consentAction</name>
<title>Consent mode action</title>
<value>update</value>
<defaultValue>update</defaultValue>
<type>array</type>
<uiControl>select</uiControl>
<uiControlAttributes>
</uiControlAttributes>
<availableValues>
<default>default</default>
<update>update</update>
</availableValues>
<description>Select 'default' to set default values, and 'update' to handle users consent.</description>
<inlineHelp />
<introduction />
<condition />
<fullWidth>0</fullWidth>
</row>
<row>
<name>consentTypes</name>
<title>Consent type</title>
<value>
<row>
<consent_type>ad_storage</consent_type>
<consent_state>granted</consent_state>
</row>
<row>
<consent_type>ad_user_data</consent_type>
<consent_state>granted</consent_state>
</row>
<row>
<consent_type>ad_personalization</consent_type>
<consent_state>granted</consent_state>
</row>
<row>
<consent_type>analytics_storage</consent_type>
<consent_state>granted</consent_state>
</row>
<row>
<consent_type>functionality_storage</consent_type>
<consent_state>granted</consent_state>
</row>
<row>
<consent_type>personalization_storage</consent_type>
<consent_state>granted</consent_state>
</row>
<row>
<consent_type>security_storage</consent_type>
<consent_state>granted</consent_state>
</row>
</value>
<defaultValue>
<row>
<consent_type>ad_storage</consent_type>
<consent_state>granted</consent_state>
</row>
<row>
<consent_type>ad_user_data</consent_type>
<consent_state>granted</consent_state>
</row>
<row>
<consent_type>ad_personalization</consent_type>
<consent_state>granted</consent_state>
</row>
<row>
<consent_type>analytics_storage</consent_type>
<consent_state>granted</consent_state>
</row>
<row>
<consent_type>functionality_storage</consent_type>
<consent_state>granted</consent_state>
</row>
<row>
<consent_type>personalization_storage</consent_type>
<consent_state>granted</consent_state>
</row>
<row>
<consent_type>security_storage</consent_type>
<consent_state>granted</consent_state>
</row>
</defaultValue>
<type>array</type>
<uiControl>multituple</uiControl>
<uiControlAttributes>
<field1>
<key>consent_type</key>
<title>Consent type</title>
<uiControl>text</uiControl>
<component>
<plugin>TagManager</plugin>
<name>FieldVariableTemplate</name>
</component>
<availableValues />
</field1>
<field2>
<key>consent_state</key>
<title>Consent state</title>
<uiControl>text</uiControl>
<component>
<plugin>TagManager</plugin>
<name>FieldVariableTemplate</name>
</component>
<availableValues />
</field2>
</uiControlAttributes>
<availableValues />
<description />
<inlineHelp>The consent state must be 'denied' before the user gives consent. Once consent is received, you can trigger this tag with the action mode set to 'update' and all consents state set to 'granted' for all consent types. (All consent types are available in the Google documentation). Consent state must be 'denied' or 'granted', no other values are allowed. &lt;a href="https://matomo.org/faq/tag-manager/google-consent-tag-in-matomo-tag-manager/?mtm_campaign=Matomo_App&amp;mtm_source=Matomo_App_OnPremise&amp;mtm_medium=Tag.TagManager.GoogleConsentMode" target="_blank" rel="noreferrer noopener"&gt;Learn more&lt;/a&gt;.</inlineHelp>
<introduction />
<condition />
<fullWidth>0</fullWidth>
</row>
</parameters>
</row>
<row>
<id>OneTrust</id>
<name>OneTrust</name>
<description>The OneTrust Consent Management Platform orchestrates the collection of consent across web, mobile, and CTV.</description>
<category>Consent Management Platform</category>
<category>Consent Management</category>
<icon>plugins/TagManager/images/icons/one-trust.svg</icon>
<help />
<order>9999</order>
Expand Down
4 changes: 2 additions & 2 deletions tests/UI/expected-screenshots/ContainerTag_create_new.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading

0 comments on commit c2345e7

Please sign in to comment.