Artikel über: Integrationen
Dieser Artikel ist auch verfügbar in:

Google Consent Mode in einem Shopify Custom Pixel (gtag.js)

Übersicht


Manche Shops laden Google Analytics 4 (G-) oder Google Ads (AW-) direkt mit gtag.js von Shopify custom pixel (Settings > Customer events). Dieser Artikel stellt fertigen Pixel-Code bereit, der Google Consent Mode Advanced auf diese Properties anwendet, und zwar mit der Einwilligung, die Besucher im Pandectes-Banner geben.


Wenn Ihre Google-Properties über einen Google-Tag-Manager-Container geladen werden, verwenden Sie stattdessen Google Consent Mode in einem Shopify Custom Pixel (Google Tag Manager).


Dies ist eine Umsetzungsanleitung. Hintergrundinformationen zu den Befehlen default und update sowie zum Advanced-Modus finden Sie in Googles Consent Mode mit gtag.js.


Bevor Sie beginnen



Dieses Pixel ist eine von zwei Hälften der Einrichtung. Gehen Sie im Shopify-Admin zu Apps > Pandectes GDPR > Integrations, klicken Sie auf der Karte Google Consent Mode auf Configure und schalten Sie die Integration ein. Siehe Verwendung der Google Consent Mode Integration. Google Consent Mode funktioniert ab dem Tarif Plus und höher.


Ein Shopify Custom Pixel läuft in einem Sandbox-iFrame mit eigenem window, dataLayer und einer eigenen Kopie von gtag.js. Es ist von der Storefront-Seite getrennt, und eine in einem der beiden gesetzte Einwilligung ist für das andere nicht sichtbar. Deshalb braucht jeder Bereich seine eigene Einrichtung:


Ort

Was dort läuft

Was den Consent Mode setzt

Storefront-Seite

Google-Tags in theme.liquid, Ihr GTM-Container, Tags anderer Apps

Die Integration Google Consent Mode von Pandectes

Pixel-Sandbox

Die gtag.js, die Sie im Pixel laden, und deren Properties

Der Code in diesem Artikel


Das Pixel ersetzt die Integration nicht. Nichts im Pixel kann die Storefront-Seite erreichen. Ohne die Integration hat Ihr Storefront daher überhaupt keinen Consent Mode.


Verwenden Sie Google Tag Manager?


Wenn Ihr Shop einen GTM-Container hat, prüfen Sie, ob Ihre Google-Properties dort bereits geladen werden. Das ist meist der Fall. Ein Pixel, das dieselbe GA4- oder Google-Ads-Property erneut lädt, verdoppelt Ihre Seitenaufrufe, Sitzungen, Käufe und Conversions und erzeugt zwei konkurrierende Einwilligungsstatus.


Ihr Setup

Vorgehen

GA4 oder Google Ads, geladen über einen GTM-Container

Google Consent Mode in einem Shopify Custom Pixel (Google Tag Manager)

Kein GTM, Properties mit gtag.js in einem Custom Pixel geladen

Dieser Artikel


Was dieser Code abdeckt


Der Code setzt nur den Einwilligungsstatus und nichts sonst. Er sendet Google die Standardrichtlinie des Shops, wendet die Auswahl des Besuchers an, hält sie mit dem Banner synchron und lädt den Google-Tag, damit die Einwilligungssignale ein Ziel haben. Er sendet selbst keine Analyse- oder Conversion-Daten.


Pandectes stellt nur die Einwilligungsebene bereit. Welche Events Sie senden, welche Daten sie enthalten, wie sie Ihren GA4-Properties oder Google-Ads-Conversions zugeordnet werden und ob Ihre Auswertung korrekt ist, liegt in Ihrer Verantwortung. Pandectes unterstützt das auf diesem Code aufbauende Tracking nicht und überprüft es auch nicht.


Ihre Event-Abonnements gehören in dasselbe Pixel


Das Senden der Customer Events von Shopify an Google ist der eigentliche Zweck des Pixels, und diese Abonnements müssen im selben Pixel stehen, unterhalb des Einwilligungscodes. Die Beispiele in jedem Snippet sind absichtlich auskommentiert. Entfernen Sie die Kommentarzeichen oder ersetzen Sie die Beispiele durch Ihre eigenen.


Jedes Pixel, das eine Google-Property lädt, braucht seine eigene Kopie


Sie können den Einwilligungscode nicht in einem Custom Pixel und Ihre Events in einem anderen platzieren. Jedes Pixel ist eine eigene Sandbox. Ein Pixel, das GA4 oder Google Ads ohne Einwilligungscode lädt, löst alles nach den Standardeinstellungen von Google aus, als gäbe es keinen Consent Mode, und Shopify warnt Sie nicht.


  • Ein Pixel lädt Ihre Properties: eine Kopie des Codes, mit den Events dieses Pixels darunter.
  • Drei Pixel laden jeweils eine Google-Property: drei Kopien, je eine in jedem Pixel.
  • Wenn mehrere Pixel dieselbe Property laden, beheben Sie zuerst diese Doppelung.


Advanced-Modus und die Pixel-Berechtigung


Dieser Code ergibt Google Consent Mode Advanced: Der Google-Tag lädt bei jedem Seitenaufruf, sendet cookielose Pings, solange die Einwilligung verweigert ist, und wechselt zur vollständigen Messung, sobald die Einwilligung erteilt wird. So kann Google Conversions auch für Besucher modellieren, die nicht zustimmen.


Dafür muss das Pixel vor der Einwilligung laufen dürfen. Gehen Sie im Shopify-Admin zu Settings > Customer events, öffnen Sie Ihr Custom Pixel und setzen Sie unter Customer privacy den Wert Permission auf Not required. Bei Required hält Shopify das Pixel zurück, bis der Besucher zustimmt. Der Google-Tag lädt dann nie vor der Einwilligung, und es werden keine cookielosen Pings gesendet.


Wenn Sie Basic mode möchten (nichts wird geladen, bis eine Einwilligung erteilt wird), brauchen Sie diesen Code nicht. Setzen Sie Permission auf Required, wählen Sie die benötigten Kategorien aus und lassen Sie Shopify das Pixel zurückhalten.


So funktioniert der Code


Shopify gibt dem Pixel die Einwilligung des Besuchers in init.customerPrivacy, sagt aber nicht, ob es sich um die Standardeinstellung des Shops oder um eine bereits getroffene Auswahl des Besuchers handelt. Deshalb führt der Code immer diese Schritte in dieser Reihenfolge aus:


  1. consent default: die Richtlinie des Shops, direkt in den Code geschrieben.
  2. consent update: was init.customerPrivacy enthält. War es nur der Standardwert, ändert sich nichts. War es eine gespeicherte Auswahl, wird sie vor dem ersten Treffer angewendet.
  3. gtag.js laden und Ihre Google-Properties konfigurieren.
  4. Auf visitorConsentCollected lauschen und bei jeder Änderung der Auswahl durch den Besucher ein update senden.


In einem Custom Pixel stehen analytics, browser und init direkt zur Verfügung, customerPrivacy wird jedoch über api erreicht. Ein Aufruf von customerPrivacy.subscribe(...) ohne api. löst einen ReferenceError aus.


Die Einwilligungswerte von Shopify werden so den Einwilligungstypen von Google zugeordnet:


Shopify

Google

analyticsProcessingAllowed

analytics_storage

marketingAllowed

ad_storage, ad_user_data, ad_personalization

preferencesProcessingAllowed

functionality_storage, personalization_storage

saleOfDataAllowed

Kein Consent-Mode-Äquivalent. Es ist ein Signal für Verkauf oder Weitergabe in US-Bundesstaaten (siehe restricted_data_processing).

(immer)

security_storage ist immer granted


Welches Snippet brauche ich?


Richtlinie Ihres Shops

Verwenden Sie

Weltweit dieselbe Richtlinie: Nichts wird ausgeführt, bis der Besucher zustimmt

Snippet 1 (ein Standardbefehl)

Einwilligung nur in manchen Regionen eingeholt, anderswo erlaubt

Snippet 2 (Standardbefehle pro Region)


Beide Snippets unterstützen GA4, Google Ads oder beides.


  1. Gehen Sie im Shopify-Admin zu Settings > Customer events und klicken Sie auf Add custom pixel.
  2. Geben Sie dem Pixel einen Namen und fügen Sie eines der Snippets ein.
  3. Tragen Sie Ihre IDs zwischen START_MODIFY_FOR_YOUR_STORE und END_MODIFY_FOR_YOUR_STORE ein.
  4. Fügen Sie unten Ihre eigenen Event-Abonnements hinzu.
  5. Legen Sie die Berechtigung wie oben beschrieben fest, klicken Sie auf Save und dann auf Connect.


Snippet 1: ein Standardbefehl


Ein Befehl default ohne Region, sodass er für jeden Besucher gilt. Alles wird verweigert, außer security_storage.


/* START_MODIFY_FOR_YOUR_STORE */
const GA4_ID = ""; // e.g. "G-XXXXXXXXXX", leave empty if not used
const AW_ID = ""; // e.g. "AW-XXXXXXXXXX", leave empty if not used
const DEBUG = false; // true sends GA4 hits to DebugView while testing
/* END_MODIFY_FOR_YOUR_STORE */

const GRANTED = "granted";
const DENIED = "denied";
const GOOGLE_URL = "https://www.googletagmanager.com/gtag/js?id=";
const DEVELOPER_ID = "dMTZkMj";

/* Shopify customerPrivacy -> Google consent state */
const toConsentState = (cp) => ({
ad_storage: cp.marketingAllowed ? GRANTED : DENIED,
ad_user_data: cp.marketingAllowed ? GRANTED : DENIED,
ad_personalization: cp.marketingAllowed ? GRANTED : DENIED,
analytics_storage: cp.analyticsProcessingAllowed ? GRANTED : DENIED,
functionality_storage: cp.preferencesProcessingAllowed ? GRANTED : DENIED,
personalization_storage: cp.preferencesProcessingAllowed ? GRANTED : DENIED,
security_storage: GRANTED,
});

/* The pixel sandbox has its own dataLayer. */
window.dataLayer = window.dataLayer || [];
function gtag() {
dataLayer.push(arguments);
}

/* Pandectes developer ID. Identifies the implementation to Google,
* has no effect on your data. Leave it as it is. */
gtag("set", `developer_id.${DEVELOPER_ID}`, true);

/* STEP 1: store policy, before gtag.js loads. Applies to everyone. */
gtag("consent", "default", {
ad_storage: DENIED,
ad_user_data: DENIED,
ad_personalization: DENIED,
analytics_storage: DENIED,
functionality_storage: DENIED,
personalization_storage: DENIED,
security_storage: GRANTED,
});

/* STEP 2: visitor state, always sent. If it is only the default,
* nothing changes. If it is a saved choice, it lands before the first hit. */
gtag("consent", "update", toConsentState(init.customerPrivacy));

/* STEP 3: load the Google tag once and configure each property. */
const TAG_IDS = [GA4_ID, AW_ID].filter(Boolean);

if (TAG_IDS.length) {
gtag("js", new Date());

if (GA4_ID) {
gtag("config", GA4_ID, {
send_page_view: false,
...(DEBUG ? { debug_mode: true } : {}),
});
}

if (AW_ID) {
gtag("config", AW_ID);
}

const script = document.createElement("script");
script.async = true;
script.src = GOOGLE_URL + TAG_IDS[0];
document.head.appendChild(script);
}

/* STEP 4: follow the visitor's choices. Note the api. prefix. */
api.customerPrivacy.subscribe("visitorConsentCollected", (event) => {
gtag("consent", "update", toConsentState(event.customerPrivacy));
});

/* YOUR EVENT SUBSCRIPTIONS GO HERE, IN THIS SAME PIXEL.
* The examples are commented out on purpose. What you send is yours
* to own and verify. */

/* Page view: only if the storefront does not already send page_view
* for the same property, or it is counted twice. */
// analytics.subscribe("page_viewed", (event) => {
// gtag("event", "page_view", {
// page_path: event.context.document.location.pathname,
// page_title: event.context.document.title,
// page_location: event.context.window.location.href,
// });
// });

/* Purchase: if GA4 and Google Ads are linked, import the GA4 purchase
* as a conversion in Google Ads and delete the conversion block below,
* or every order is counted twice. */
// analytics.subscribe("checkout_completed", (event) => {
// const checkout = event.data.checkout;
// const items = checkout.lineItems.map((line) => ({
// item_id: "shopify_" + line.variant.product.id + "_" + line.variant.id,
// item_name: line.title,
// item_variant: line.variant.title,
// price: line.variant.price.amount,
// quantity: line.quantity,
// }));
//
// gtag("event", "purchase", {
// transaction_id: checkout.token,
// currency: checkout.currencyCode,
// value: checkout.totalPrice.amount,
// tax: checkout.totalTax.amount,
// shipping: checkout.shippingLine ? checkout.shippingLine.price.amount : 0,
// items: items,
// });
//
// // Google Ads conversion, ONLY when GA4 and Google Ads are NOT linked.
// // Use the conversion label from your Google Ads conversion action.
// gtag("event", "conversion", {
// send_to: "AW-XXXXXXXXXX/AbC-D_efGhIjKlMnOp",
// transaction_id: checkout.token,
// currency: checkout.currencyCode,
// value: checkout.totalPrice.amount,
// });
// });


Snippet 2: Standardbefehle pro Region


Für Shops, die Einwilligung nur dort einholen, wo sie gesetzlich vorgeschrieben ist. Es gibt zwei Befehle default: einen globalen, der alles erlaubt, und einen für die aufgeführten Regionen, der alles verweigert außer security_storage. Treffen beide auf einen Besucher zu, gewinnt die spezifischere Region.


Der Rest ist identisch mit Snippet 1.


/* START_MODIFY_FOR_YOUR_STORE */
const GA4_ID = ""; // e.g. "G-XXXXXXXXXX", leave empty if not used
const AW_ID = ""; // e.g. "AW-XXXXXXXXXX", leave empty if not used

/* ISO 3166-2 codes where the store collects consent: EEA + UK below.
* Add US states ("US-CA", "US-CO", ...) if you treat them as opt-in.
* This list MUST match the regions where your banner collects consent. */
const RESTRICTED_REGIONS = [
"AT", "BE", "BG", "HR", "CY", "CZ", "DK", "EE", "FI", "FR",
"DE", "GR", "HU", "IE", "IT", "LV", "LT", "LU", "MT", "NL",
"PL", "PT", "RO", "SK", "SI", "ES", "SE", "GB", "LI", "NO", "IS",
];

const DEBUG = false; // true sends GA4 hits to DebugView while testing
/* END_MODIFY_FOR_YOUR_STORE */

const GRANTED = "granted";
const DENIED = "denied";
const GOOGLE_URL = "https://www.googletagmanager.com/gtag/js?id=";
const DEVELOPER_ID = "dMTZkMj";

/* Shopify customerPrivacy -> Google consent state */
const toConsentState = (cp) => ({
ad_storage: cp.marketingAllowed ? GRANTED : DENIED,
ad_user_data: cp.marketingAllowed ? GRANTED : DENIED,
ad_personalization: cp.marketingAllowed ? GRANTED : DENIED,
analytics_storage: cp.analyticsProcessingAllowed ? GRANTED : DENIED,
functionality_storage: cp.preferencesProcessingAllowed ? GRANTED : DENIED,
personalization_storage: cp.preferencesProcessingAllowed ? GRANTED : DENIED,
security_storage: GRANTED,
});

/* The pixel sandbox has its own dataLayer. */
window.dataLayer = window.dataLayer || [];
function gtag() {
dataLayer.push(arguments);
}

/* Pandectes developer ID. Identifies the implementation to Google,
* has no effect on your data. Leave it as it is. */
gtag("set", `developer_id.${DEVELOPER_ID}`, true);

/* STEP 1a: policy for everyone outside the listed regions. */
gtag("consent", "default", {
ad_storage: GRANTED,
ad_user_data: GRANTED,
ad_personalization: GRANTED,
analytics_storage: GRANTED,
functionality_storage: GRANTED,
personalization_storage: GRANTED,
security_storage: GRANTED,
});

/* STEP 1b: policy for the listed regions. Google resolves the region
* from the IP address, so test it with a VPN. */
gtag("consent", "default", {
ad_storage: DENIED,
ad_user_data: DENIED,
ad_personalization: DENIED,
analytics_storage: DENIED,
functionality_storage: DENIED,
personalization_storage: DENIED,
security_storage: GRANTED,
region: RESTRICTED_REGIONS,
});

/* STEP 2: visitor state, always sent. Shopify has already applied your
* regional settings to init.customerPrivacy, so this matches 1a or 1b. */
gtag("consent", "update", toConsentState(init.customerPrivacy));

/* STEP 3: load the Google tag once and configure each property. */
const TAG_IDS = [GA4_ID, AW_ID].filter(Boolean);

if (TAG_IDS.length) {
gtag("js", new Date());

if (GA4_ID) {
gtag("config", GA4_ID, {
send_page_view: false,
...(DEBUG ? { debug_mode: true } : {}),
});
}

if (AW_ID) {
gtag("config", AW_ID);
}

const script = document.createElement("script");
script.async = true;
script.src = GOOGLE_URL + TAG_IDS[0];
document.head.appendChild(script);
}

/* STEP 4: follow the visitor's choices. Note the api. prefix. */
api.customerPrivacy.subscribe("visitorConsentCollected", (event) => {
gtag("consent", "update", toConsentState(event.customerPrivacy));
});

/* YOUR EVENT SUBSCRIPTIONS GO HERE, IN THIS SAME PIXEL.
* Use the same page view and purchase examples as in Snippet 1. */


Prüfen Sie, ob es funktioniert


Tag Assistant kann das Pixel nicht sehen


Google Tag Assistant prüft nur die Storefront-Seite. Die gtag, dataLayer und die Properties des Pixels liegen in einem Sandbox-iFrame, das er nicht erreicht. Er meldet daher nichts (oder nur die eigenen Tags des Storefronts), selbst wenn das Pixel korrekt funktioniert. Das ist erwartet und kein Fehler.


Prüfen Sie das dataLayer im Frame des Pixels


  1. Öffnen Sie die Chrome DevTools und wechseln Sie zum Tab Console.
  2. Öffnen Sie in der Symbolleiste des Console-Tabs das Frame-Auswahlmenü (es zeigt normalerweise top) und wählen Sie das Sandbox-Frame des Pixels aus (sein Name beginnt mit web-pixel). Shopify erstellt ein Frame pro Custom Pixel, wählen Sie also das richtige aus, wenn Sie mehrere haben.
  3. Führen Sie die folgenden Prüfungen aus.


Im Frame top ist dataLayer das dataLayer des Storefronts und sagt Ihnen nichts über das Pixel.


  • Kommen die Standardwerte zuerst? In dataLayer müssen die Einträge consent vor den Einträgen config erscheinen.
  • Erreicht die Einwilligung den Tag? Setzen Sie DEBUG = true, entkommentieren Sie ein Event, damit etwas gesendet wird, und öffnen Sie in GA4 DebugView. Wenn analytics_storage verweigert ist, sehen Sie einen cookielosen Ping statt eines normalen Treffers.
  • Lädt das Pixel vor der Einwilligung? Das muss für den Advanced-Modus der Fall sein. Erscheint der Google-Tag erst, nachdem der Besucher zugestimmt hat, ist die Pixel-Berechtigung auf Required gesetzt und Sie befinden sich im Basic-Modus.
  • Funktioniert die Regionslogik? Testen Sie mit einem VPN innerhalb und außerhalb eines aufgeführten Landes.
  • Wird das Abonnement ausgelöst? Fügen Sie vorübergehend ein console.log im Callback visitorConsentCollected hinzu und ändern Sie Ihre Auswahl im Banner.


Häufige Fehler


Fehler

Was passiert

Einwilligungscode in einem Pixel, Events im anderen

Das Event-Pixel hat kein gtag und keinen Einwilligungsstatus. Seine Events gehen ins Leere.

Mehrere Pixel laden eine Google-Property, nur eines hat den Einwilligungscode

Die anderen laufen ohne Consent Mode, ohne Warnung.

Pixel Permission auf Required gesetzt

Der Tag lädt nie vor der Einwilligung: keine cookielosen Pings und keine Modellierung. Das ist der Basic-Modus.

Google-Ads-Event conversion gesendet, während der GA4-Kauf auch als Conversion importiert wird

Jede Bestellung wird in Google Ads doppelt gezählt.

customerPrivacy.subscribe(...) ohne api.

ReferenceError. Die Einwilligung wird nach dem Banner nie aktualisiert.

Überspringen von update, weil init.customerPrivacy wie der Standardwert aussieht

Wiederkehrende Besucher mit gespeicherter Einwilligung erhalten beim ersten Seitenaufruf verweigerte Tags.

default nach config gesendet

Consent Mode wird auf die ersten Treffer nicht angewendet.

Google Consent Mode Integration in Pandectes nicht aktiviert

Nur die Properties des Pixels erhalten den Consent Mode. Google-Tags auf dem Storefront laufen ohne ihn.

Pixel gebaut, obwohl GTM dieselbe Property bereits lädt

Doppelte Seitenaufrufe, Sitzungen, Käufe und Conversions sowie zwei Einwilligungsstatus.

Test mit Tag Assistant oder Auslesen von dataLayer im Frame top

Beides sieht nicht in die Pixel-Sandbox.

security_storage verweigert

Schwächt die Signale zur Betrugsprävention, ohne Compliance-Nutzen.

RESTRICTED_REGIONS entspricht nicht den Regionen des Banners

Standardwert und Aktualisierung widersprechen sich. Die Aktualisierung gewinnt und die Regionsrichtlinie wird ignoriert.


Einstellungen, die dieser Artikel nicht behandelt


Die Snippets lassen Googles Einstellungen auf Kontoebene aus, daher gelten Googles Standardwerte:


Einstellung

Was sie steuert

url_passthrough

Ob Anzeigen-Klick-IDs wie GCLID zwischen Seiten in der URL übergeben werden, wenn keine Cookies gesetzt werden können

ads_data_redaction

Ob Anzeigen-Klick-IDs aus cookielosen Pings entfernt werden, solange ad_storage verweigert ist

allow_enhanced_conversions

Ob gehashte Kundendaten zusammen mit Conversions gesendet werden dürfen

restricted_data_processing

Die Einschränkung für Verkauf oder Weitergabe in US-Bundesstaaten, verbunden mit Shopifys saleOfDataAllowed

wait_for_update

Wie lange Tags auf eine Einwilligungsaktualisierung warten, bevor sie ausgelöst werden


Pandectes kann dazu nicht beraten. Die richtigen Werte hängen von Ihren Google-Konten, der Modellierung, auf die Sie sich verlassen, und der rechtlichen Situation Ihres Unternehmens ab. Besprechen Sie das mit der Person, die Ihr Google-Setup betreut, oder bei datenschutzrechtlichen Fragen mit Ihrer Rechtsberatung.


Wenn Sie einen Wert setzen möchten, fügen Sie ihn als Aufruf gtag("set", ...) vor den Befehlen consent default hinzu:


// gtag("set", "url_passthrough", true);
// gtag("set", "ads_data_redaction", true);


wait_for_update ist die Ausnahme: Es gehört in einen Befehl default. Diese Snippets brauchen es nicht, weil init.customerPrivacy sofort verfügbar ist und das update direkt nach den Standardwerten gesendet wird.

Aktualisiert am: 30/10/2026

War dieser Beitrag hilfreich?

Teilen Sie Ihr Feedback mit

Stornieren

Danke!