google / site-kit-wp

Site Kit is a one-stop solution for WordPress users to use everything Google has to offer to make them successful on the web.
https://sitekit.withgoogle.com
Apache License 2.0
1.25k stars 291 forks source link

Compatibility to Real Cookie Banner #8913

Open matzeeable opened 4 months ago

matzeeable commented 4 months ago

Feature Description

Hey, Matthew here from devowl.io! 😊

We had a talk with one of the Google Site Kit developers in the WordCamp Europe 2024 in Torino about the compatibility between our plugin Real Cookie Banner and Google Site Kit. The developer recommended to us to open an issue here on GitHub to evaluate further things.

First: Our plugin Real Cookie Banner offers some functions only in the PRO version, including the Google Consent Mode. If any of you need the PRO version, please write to me at https://devowl.io/support and I will send you a license accordingly.

Google Consent Mode

The first thing we need to do is to make the implementation of the Google Consent Mode work. Currently, Google Site Kit provides the following option:

image

When this option is enabled, Google Site Kit will add the gtag('consent', 'default', ...) snippet to the HTML head:

https://github.com/google/site-kit-wp/blob/da09975064917b82dc3f331b9872e37bd7cb78c0/includes/Core/Consent_Mode/Consent_Mode.php#L91-L96

This conflicts with our Google Consent Mode implementation. Here it would be practical if you provided a filter that completely deactivates the Google Consent Mode functionality of your plugin and lets it be taken over by another plugin. In practice, this could be a filter that simply takes over the plugin name. As a result, for a better user experience, you could also display a corresponding notice:

add_filter('googlesitekit_consent_responsible_plugin', function($name) {
  return 'Real Cookie Banner';
});

image

For example, WooCommerce Google Analytics provides a similar hook: GA4W overwrites the consent mode defaults set by the other extension

Why do we not want to use the WP Consent API plugin? We've had this discussion several times and can only say that the Consent API strictly does not correspond to our point of view. The main reason for this is that the Consent API grants consent per category, but not per service as required by the GDPR (see a similar discussion https://github.com/elementor/elementor/pull/12567#issuecomment-814173249).

Integration in our scanner

Our plugin offers a scanner which scans for used services in all subpages of the WordPress instance. This currently finds Google Analytics when used through Google Site Kit. But when creating the service in our plugin, this could lead to multiple embed codes and therefore lead to conflicts. For this, we have introduced a filter, which allows us to do a "native" integration into any other plugin: https://docs.devowl.io/real-cookie-banner/hooks/RCB_Templates_TechnicalHandlingIntegration.html

This could potentially look like this:

image

From coding perspective, it is just this code snippet:

add_action('RCB/Templates/TechnicalHandlingIntegration', function ($integration) {
    if (
        defined('GOOGLESITEKIT_PLUGIN_MAIN_FILE') &&
        // google_analytics_embed_active() is a example function which checks if Google Analytics embed is active in your plugin
        google_analytics_embed_active() &&
        // Replace __FILE__ with your main plugin file (the absolute path to your `your-plugin/your-plugin.php` file)
        // See also https://developer.wordpress.org/plugins/plugin-basics/header-requirements/
        $integration->integrate(constant('GOOGLESITEKIT_PLUGIN_MAIN_FILE'), 'google-analytics-analytics-4')) {
        // Disable opt-in and opt-out script
        $integration->setCodeOptIn('');
        $integration->setCodeOptOut('');
    }
});

Whether we can add this hook within our plugin or your plugin is up to you. All we need is a function or API that allows us to check whether Google Site Kit inserts the embed code in the HTML (replacement for google_analytics_embed_active()).

Further outlook

These things would be the first things we should tackle together. To summarize again:

Once we have implemented this, we can check and implement further compatibility. We would like to implement all services provided by Google Site Kit.

What do you think?


Do not alter or remove anything below. The following sections will be managed by moderators only.

Acceptance criteria

Implementation Brief

Test Coverage

QA Brief

Changelog entry

aaemnnosttv commented 4 months ago

Hi @matzeeable, thank you for opening this detailed issue! PS. I spoke with you at WCEU, it was nice to meet you 🀝

Add a filter to disable the implementation of Google Site Kit's Consent Mode

This sounds reasonable – we already expose filters for blocking the output of specific tags.

Show a notice that another plugin is responsible for the Google Consent Mode

This sounds like more of a nice-to-have but also reasonable. I'll check with our UX team about how this might best be applied and follow up.

Provide API's to check if Google Site Kit is embedding snippets for the available services so we can create a scanner compatibility

This is a bit complicated because as mentioned above, the tag output can be suppressed via a filter or other conditions such as the environment type, or something else so it depends how accurate you're interested in regarding the return value.

You can already detect if the tag for GA will be output or not but on page load only after template_redirect. We fire a googlesitekit_analytics-4_init_tag action or googlesitekit_analytics-4_init_tag_amp action if the tag is going to be placed on the page. Would that be sufficient, or are you looking for something that you could call at any time?

Would it be sufficient to be able to check if the tag is enabled more generally? Each module with a tag has a setting useSnippet which controls the enabled state of its tag output. If that would work, you could already check that in its respective option, but we could also see about providing it via something you could call.

For example, WooCommerce Google Analytics provides a similar hook: GA4W overwrites the consent mode defaults set by the other extension

We recently added a googlesitekit_consent_defaults filter to modify these as well. Removing everything currently doesn't suppress the rest of the output though.


Thanks for your patience and suggestions πŸ‘

matzeeable commented 4 months ago

Hey @aaemnnosttv !

It was really great to meet you, too! I also think it's great that things are now moving towards implementation because we really have a lot of Real Cookie Banner users who are waiting for the integration with Google Site Kit. 😎

we already expose filters for blocking the output of specific tags. [...] We recently added a googlesitekit_consent_defaults filter to modify these as well. Removing everything currently doesn't suppress the rest of the output though.

You mean googlesitekit_consent_defaults, correct? When I hook into this filter and return an empty array, it generates - as you already mentioned - the following JavaScript what is wrong for us:

<script id='google_gtagjs-js-consent-mode'>
window.dataLayer = window.dataLayer || [];function gtag(){dataLayer.push(arguments);}
gtag('consent', 'default', []); // <---
window._googlesitekitConsentCategoryMap = /* [...] */
</script>

You can already detect if the tag for GA will be output or not but on page load only after template_redirect. We fire a googlesitekit_analytics-4_init_tag action or googlesitekit_analytics-4_init_tag_amp action if the tag is going to be placed on the page. Would that be sufficient, or are you looking for something that you could call at any time?

I assume you are suggesting that we should use did_action to check whether the Google Analytics code has been output. This will not work because the check whether a template is proposed in the scanner is not carried out by the frontend, but can also be a REST API call, for example.

Would it be sufficient to be able to check if the tag is enabled more generally? Each module with a tag has a setting useSnippet which controls the enabled state of its tag output. If that would work, you could already check that in its respective option, but we could also see about providing it via something you could call.

We have already built several integrations and are now at a stage where we can provide a stable hook here: RCB/Templates/TechnicalHandlingIntegration. If you could provide us a simple API function to check if e.g. Google Analytics output is enabled, I think this is enough. Additionally, we need a hook which gets fired when the state of activation gets modified (e.g. user activates/deactivates Google Analytics) so we can reset our scanner cache (see section The filter is not fired, why? in hook doc).

If you want to discuss it a bit more, we can also do this via Slack or a video call? 😊