← Back to Google Consent Mode v2
Google Consent Mode v2

Default denied, then update after the visitor chooses

Default must fire synchronously before Google tags. Update fires when the visitor accepts or declines. Geo can relax analytics only after that first default.

The required order

  1. Page starts.
  2. gtag('consent', 'default', { …denied…, wait_for_update: 500 }) runs.
  3. Only then may GTM, GA4, or Google Ads load.
  4. The visitor accepts or declines, or a stored choice is replayed.
  5. gtag('consent', 'update', { … }) runs with the matching granted or denied values.

If GA4 loads before default, Google never saw a denied start. That is a failed Consent Mode install even if the banner later appears.

What the widget does on every page

On load, consent-widget.js immediately fires a strict default: all four signals denied, wait_for_update: 500, url_passthrough: true, ads_data_redaction: true.

It then asks https://ipapi.co/json/ for country. EEA member states plus the United Kingdom (GB) and Switzerland (CH) keep the strict default. Other countries get a second default that grants analytics_storage only. Ads signals stay denied. If the lookup errors, the widget stays strict.

If localStorage.sitetrust_consent already exists, the widget applies that choice and fires update so a returning visitor does not start from a blank slate.

What Accept and Decline send

Accept All writes granted Analytics and Marketing (and Functional) on the receipt, then updates Consent Mode to granted on all four signals.

Decline writes optional categories off, then updates all four signals to denied. Necessary tools stay on. That is expected.

GTM still needs its own default tag

When you install through GTM, the widget runs inside a tag. Tags can be milliseconds late. That is why the GTM guide starts with a Consent Default Custom HTML tag on Consent Initialization, then sequences the widget after it:

<script>
  window.dataLayer = window.dataLayer || [];
  function gtag(){dataLayer.push(arguments);}
  gtag('consent', 'default', {
    ad_storage: 'denied',
    analytics_storage: 'denied',
    ad_user_data: 'denied',
    ad_personalization: 'denied',
    wait_for_update: 500
  });
</script>

Head-only installs do not need this extra tag. The widget itself fires default as soon as it runs. The extra tag is for GTM timing.

Do not write your own update

Let the banner own update. A hardcoded granted update in another tag undoes Decline and fails Run C. If you must debug, log dataLayer consent events. Do not push a second policy.

Next

Prove the order with Verify Consent Mode.

Need help?

Email wecare@sitetrust.com with your site URL and platform. One business day response, Monday through Friday.