• Courses
    • Courses
    • Course bundles
  • Blog
  • Resources
    • Youtube channel
    • E-books and Guides
    • GTM Recipes
    • View All Resources
    • GTM Community
    • GA4 community
  • Services
  • About
    • About
    • Contact
  • Login
  • Courses
    • Courses
    • Course bundles
  • Blog
  • Resources
    • Youtube channel
    • E-books and Guides
    • GTM Recipes
    • View All Resources
    • GTM Community
    • GA4 community
  • Services
  • About
    • About
    • Contact
  • Login

March 29, 2025

Google Analytics 4 cross-domain tracking not working? Here are the fixes

Cross-domain tracking in GA4 is a built-in workaround that allows you to send user information from one domain to another, preserving session data across domains. This makes sure that the same user is consistently tracked across multiple websites, enabling more accurate and unified analytics.

If you’re reading this article, chances are you already know this and were eager to set it up–only to find that it didn’t work as expected. It happens to the best of us!

In this article, we will review several possibilities for why your Google Analytics 4 cross-domain tracking is not working, as well as potential solutions.

Subscribe and Get the Ebook - Mastering GA4 event tracking

Table of Contents

Here’s what you will learn in this article

  • Cross-domain tracking in GA44
  • Incorrectly configured domain
  • Server redirects
  • Javascript redirects
  • .stopPropogation()
  • Regular buttons are not supported by GA4 cross-domain tracking
  • Form submission
  • iFrame
  • Different measurement IDs between both domains
  • Missing tracking code on website B
  • Content Security Policy (CSP) blocks GA4 (or GTM) on website B
  • Consent
  • Conflicting scripts on a website
  • accept_incoming on website B is set to false
  • Browser privacy features and/or ad blockers
  • Final Words

 

Cross-domain tracking in Google Analytics 4

If you want to learn more about cross-domain tracking in Google Analytics 4, check out my blog post on the topic. This article walks through the process of setting up cross-domain tracking, so it might be useful to review it and check for any missteps in your setup that could be causing the issues you’re facing.

If you’re still facing issues, let’s dive into some other potential reasons why cross-domain tracking might not be working as expected!

 

Incorrectly configured domain

This is a pretty simple explanation, but if the domains (you want to track across) are configured incorrectly, GA4 won’t be able to attribute data to a single user across those domains accurately.

To check this, go to Admin > Data streams and select the relevant data stream.

Under Configure tag settings, click “Configure your domains” and check that the list of domains in the Domains section includes any and all domains you want to track.

Make sure that you add all relevant domains and double-check for typos in the existing domains.

 

Server redirects

If the page a user lands on either redirects the user to another page or doesn’t support arbitrary query parameters, you will see issues with your tracking. Cross-domain tracking relies on the _gl parameter used by GA4 to carry user data across domains.

A Chrome extension called Redirect Path will show you any redirects that happen after a specified URL. Choose a link you know sends users to another domain you want to track and test whether a redirect is affecting cross-domain tracking.

Go to the webpage that contains the link, click on the link, and then open the extension.

In the screenshot above, you will see two things: the top section shows the link with the _gl parameter, and the bottom section shows that the user was eventually redirected to the /password page, and the _gl parameter is gone. This is a problem because GA4 would have been loaded on the second page (without the parameter).

The only solution is to work with the developers on your team. Explain the issues to them and see if there is a way they can reconfigure things on the server level to preserve the URL query parameters after the redirect.

 

Javascript redirects

Similar to the above, a redirect caused by the JavaScript code on your site can also strip parameters from the URL. When a user clicks a link to the domain you want to track, the JavaScript redirect sends them to another page, removing the _gl parameter from the URL.

You can, again, use the Redirect Path extension to test this. Click on the link to the second domain, wait for the redirect, and click the Redirect Path extension to see what is causing the redirect!

This time, the extension mentions that there was a “JAVASCRIPT” redirect.

Again, the solution is to work with your developers to have them remove the JavaScript causing this issue or at least the code so that the _gl parameter persists in the URL.

In rare cases, I have seen situations where the redirecting JS code was in the GTM itself. So, if developers do not know where the redirect is coming from, it might be worth checking your Google Tag Manager container.

Subscribe and Get the Ebook - working with reports in ga4

.stopPropogation()

When a user clicks on a link on website A leading to website B, the browser triggers a click event. In the Document Object Model (DOM), events are handled in a hierarchical manner through a process called event propagation. This means when an event occurs, such as a button click, it doesn’t just stay on the element where the event originated—instead, it “bubbles up” through the DOM.

Event propagation is crucial for cross-domain tracking because the click event must make its way to the document (or “climb the ladder,” if you will) for GA4 to detect the event and add the _gl parameter to the URL before the user is redirected to website B.

If your team’s developers are using the JavaScript event.stopPropogation() method, it will prevent any events from being able to make their way up to the document where GA4 is listening for them.

The solution is to collaborate with your developers to identify any JavaScript on your site preventing the click event from reaching the document. Make sure that no scripts stop event propagation.

 

Regular buttons are not supported by GA4 cross-domain tracking

GA4 cross-domain tracking is designed to work with links by default. So, suppose a button is coded as a hyperlink (using a <a> tag in HTML). In that case, GA4 will properly track the user across the website because the link click will trigger the necessary tracking parameters, like the _gl parameter.

However, if the element that the user clicks is a <button> or another non-link element (such as a <div>), cross-domain tracking will fail. In these cases, you must complete a manual setup to ensure that the tracking parameters are passed between domains.

Currently, Google’s “recommended solution” for this issue is to implement a custom setup yourself, as there isn’t an out-of-the-box fix for non-link elements. This means working with developers to handle the tracking manually, making sure that clicks on buttons or other elements trigger the same behaviour as links for cross-domain tracking to work properly.

 

Form submission

Cross-domain tracking will not work by default if a visitor is redirected to website B after submitting a form on website A. This is because when a form submission redirects a user, the tracking parameters that GA4 needs (such as the _ga parameter) are not passed between the domains.

However, if you’re using the native gtag.js tracking code to install GA4, you can try to modify the code to set the linker parameter with decorate_forms: true. This configuration attempts to “decorate” the URL to which the form redirects, which might enable cross-domain tracking. You can find more details on this approach in the Google documentation.

gtag('set', 'linker', {
  'domains': ['domainA.com', 'domainB.com'],
  'decorate_forms': true
});

If you have installed GA4 via Google Tag Manager, unfortunately, the decorate_forms option won’t work. In this case, you must implement a custom solution, which your developer can help you with. The general process would be as follows:

  1. Capture the client_id and session_id from the visitor’s session. These are key identifiers that GA4 uses to track users across domains.
  2. Append these values as query parameters to the URL where the form redirects, e.g. websiteb.com?session_id=123&client_id=321
  3. In the GTM container for website B, create two variables to read the query parameters from the URL.
  4. Configure GTM to pass the client_id and session_id parameters to the Google Tag as additional fields. If a URL contains these query parameters, the Google Tag will use the URL variables to set the cookie accordingly. If the URL does not contain these parameters, the URL variables will be undefined, and the Google Tag will ignore them, setting the cookies as usual.

It’s important to note that this method is more of a proof of concept. While it works, I haven’t thoroughly tested it for all edge cases. For example, this method does not account for situations where users might share a URL (with the client_id and session_id parameters) on social media or other platforms, which could result in multiple users receiving the same session and client IDs, compromising tracking accuracy.

To address this issue, you should work with your developers to build an additional mechanism to handle such cases. An option would be to have developers add a timestamp to the decorated URL to record when the URL was created. Then, in GTM, you could use custom JavaScript to check whether the timestamp is newer than five minutes (or so). If it is, the Google Tag would use those variables. If not, the variables would return as undefined, and the Google Tag would ignore them.

If you’re thinking, “That’s a little confusing,” you’re not alone. This solution is beyond the scope of the current article and could be the topic of an entire blog post (which, maybe, I’ll write someday).

 

iFrame

You’ve certainly noticed that our issues stem from losing the query parameters with vital information for cross-domain tracking between the user travelling from website A to website B. Another way this could happen is if the link click to website B is installed in an iFrame, and you have installed GA4 on the parent page.

To resolve this, you must pass the tracking parameters from the parent page to the iFrame and make sure the iFrame sends them to website B. You will need to double-check that you have properly configured the iFrame’s content and the parent page to allow cross-origin communication.

Let’s break down this solution:

  1. On the parent page (the page where you have installed GA4), read the client_id (stored in the _ga cookie) and session_id (stored in the _ga_XXXXXXX cookie, where XXXXXXX is the measurement ID).
  2. Once you have the client_id and session_id parameters, append them as query parameters to the iFrame’s URL, e.g. <iframe src=”website.com?session_id=123&client_id=321″ />
  3. Inside the iframe, check if the query parameter can be captured and used for tracking.
  4. For any links that redirect to website B (inside the iFrame), you need to append the client_id and session_id parameters from the iFrame’s URL.
  5. On website B, similar to the method I described for form tracking, you need to read the query parameters from the URL and pass them to the Google Tag so that GA4 can use them to successfully complete the cross-domain tracking.
Subscribe and Get the Ebook - 20 GA4 mistakes

Different measurement IDs between both domains

For cross-domain tracking in GA4 to work correctly, using the same data stream across all the domains you want to track is essential. When you use the same data stream, GA4 can consistently share user session data, such as client_id and session_id, between domains.

This makes sure that a user is tracked as the same individual across different domains, preserving session continuity and allowing for accurate attribution. So, when using a different data stream, GA4 will start new sessions on each domain, leading to misattribution.

To get to the data streams setting in GA4, go to Admin > Data streams and select the relevant data stream.

You can find the measurement ID under Stream details. Confirm this is the measurement ID in the tracking script on all the domains you want to enable for cross-domain tracking.

In most cases, you should be able to check the measurement ID on your site by going to developer tools (right-click on your webpage and select “Inspect”) and opening the Elements tab.

Here, click “control-F” to open the search bar and search for the measurement ID. If you can’t find it, try searching “G-” and see if there is a different measurement ID somewhere.

If you notice that the measurement IDs are different, you must update your GA4 installation. Check out my blog post on how to install GA4 (multiple ways) if you need a refresher.

 

Missing tracking code on website B

It’s not enough to have GA4 installed on just website A; both websites (A and B) must use the same GA4 data stream’s tracking code for cross-domain tracking to function properly. So, both websites must be configured under the same GA4 property and linked to the same data stream.

If you’re new to this (and one of your sites has existing tracking) or want to brush up on your skills, check out my blog post on how to install GA4 (multiple ways). Make sure you have access to the GA4 property of the website that has tracking so that you can install the same tracking script onto your other domains.

 

Content Security Policy (CSP) blocks GA4 (or GTM) on website B

A Content Security Policy (CSP) is a browser security feature that helps prevent certain types of attacks, like data injection attacks. To do this, it restricts the sources from which content can be loaded (like JavaScript).

Suppose the CSP is misconfigured on website B. In that case, it can block necessary resources, such as Google Analytics 4 or Google Tag Manager scripts, since cross-domain tracking relies on the ability to load and execute these tracking scripts.

How can you determine if this is the issue you’re facing? Go to your browser’s developer console (right-click on your webpage and select “Inspect”) and refresh the page. If you find an error that looks like this (or something similar), your Content Security Policy is causing issues for cross-domain tracking.

But in this case, the URL of the error should contain google-analytics.com.

In 2022, Google changed the URL for where GA4 sends data. Previously, it was just www.google-analytics.com, now it might be region1.google-analytics.com (or something similar). So, it would be best if your developers updated the CSP to support all domains containing google-analytics.com.

This means that developers should add *.google-analytics.com and *.analytics.google.com to the “connect-src” and “img-src” instructions in the content security policy (*. at the start is important).

You can learn more about this in Google’s documentation on using Google Tag Manager with a Content Security Policy.

 

Consent

Cross-domain tracking may fail to work as expected if a visitor grants consent for tracking on website A but then denies consent on website B. Consent preferences set on one domain are only automatically carried over to another domain if the setup up is specifically configured to share this data (and, of course, if consent management platform (CMP) supports such feature. Because, by default, consent is not carried over across domains).

Depending on your implementation, if the user denies consent on website B, GA4 will be blocked, and tracking will be interrupted.

There are many nuances and edge cases to consider when it comes to consent management and its impact on cross-domain tracking, which makes it difficult to cover all possible scenarios.

The key takeaway is that ensuring consistent consent management across all domains involved in your tracking setup is very important to avoid issues where tracking is blocked.

Subscribe and Get the Ebook - Server-side tagging

Conflicting scripts on a website

Conflicting scripts on a website, while not very common, can sometimes interfere with GA4’s linker or even disrupt other tracking features of the Google Tag.

If you suspect a script might be causing issues with cross-domain tracking, you can troubleshoot using your browser’s developer tools. Here’s how you can check:

  • Open the developer tools in your browser (right-click and select “Inspect”) and go to the Network tab.
  • Use the filter to narrow down the list to only JavaScript files by selecting “JS”.
  • One by one, block each script (right-click and select “Block request URL”).
  • After blocking each script, check if cross-domain tracking starts working.

If, at some point, cross-domain tracking starts to work after blocking a specific script, that script is likely causing the issue. In that case, you should consult with your website’s developers to see if anything can be done–whether by modifying the script or adjusting its behaviour to allow GA4 tracking to function properly.

 

accept_incoming on website B is set to false

Another rare scenario (but it’s important to check) is if the accept_incoming parameter is set in the linker parameter by using gtag.js on website B (this tip applies if GA4 on your website is installed by using gtag.js). The accept_incoming parameter controls whether cross-domain tracking data can be received from other domains.

If accept_incoming is present and set to true, cross-domain tracking will work as expected.

gtag('set','linker', {
'accept_incoming': true
});

If the link parameter is not explicitly mentioned in the code at all, that is also fine because the default value, in this case, for the parameter, is true.

However, cross-domain tracking will not function properly if someone has set accept_incoming to false in the gtag.js code. This is because the setting prevents incoming session data from being accepted, breaking the link between domains.

gtag('set','linker', {
'accept_incoming': false
});

If the latter case is true for your website, ask your developer to update the code to set the parameter to true.

 

Browser privacy features and/or ad blockers

One tricky part of collecting user analytics is that, even if you do everything right on your end, you can still fail to collect data if a user has certain browser settings (like ad blockers) or privacy features enabled.

As we have discussed throughout this article, cross-domain tracking relies on URL parameters, like the _gl parameter. Browser privacy features and ad blockers can interfere with cross-domain tracking by removing or blocking these important URL parameters, preventing GA4 from properly associating a user’s session on one domain with their actions on another. For example, Brave browser does that.

While not all users will be affected, those using ad blockers or privacy-focused tools that block or strip URL parameters may experience tracking issues.

Unfortunately, there is no surefire way to completely bypass the impact of these tools and features.

 

Google Analytics 4 cross-domain tracking not working: Final Words

Anytime something goes wrong with data collection in Google Analytics 4, it can be very frustrating trying to figure out where the problem originated from and how to resolve it. Cross-domain tracking is tricky since, as you can tell, there are many areas that problems can originate from.

I hope this article has provided you with more answers than questions regarding your cross-domain tracking setup. Remember to collaborate with the developers on your team as they will have extensive knowledge on the backend of your site that will help to better understand many of the different scenarios we talked about above.

Subscribe and Get the Ebook - JavaScript for Google Tag Manager
Julius Fedorovicius
In Google Analytics Tips
2 COMMENTS
Adam Mothersbaugh
  • Dec 14 2024
  • Reply

Hey, Julius.

Thanks for another helpful blog post.

Is it true that GA4's cross-domain measurement feature does not work when you have renamed GA4 cookies via the "cookie_prefix" parameter?

I believe I read that somewhere, but I wasn't sure if it's (still) true.

Marcin
  • Feb 6 2025
  • Reply

Waht about this: Google has released their "Storage Partition" feature with Chrome 115.
This essentially means that in newer versions of the Chromium browsers it is now only possible to share consent between domains that share the same top-level domain. This means that consent submitted on a sub-domain can be shared with other sub-domains and the top-level domain, but not the other way around.
Consent submitted on the top-level domain can not be shared with a sub-domain.

for GA4 cross domain is still working if we have CMP on both domains in Google Consent Mode v2 Advanced?

Leave a comment Cancel reply

Your email address will not be published. Required fields are marked *


 

Hi, I'm Julius Fedorovicius and I'm here to help you learn Google Tag Manager and Google Analytics. Join thousands of other digital marketers and digital analysts in this exciting journey. Read more
Analytics Mania
  • Google Tag Manager Courses
  • Google Tag Manager Recipes
  • Google Tag Manager Resources
  • Google Tag Manager Community
  • Login to courses
Follow Analytics Mania
  • Subscribe to newsletter
Recent Posts
  • Setting up cookie consent for Microsoft Clarity (V2)
  • Conversion rate in Google Analytics 4
  • Google Tag Manager Data Layer Explained
Analytics Mania - Google Tag Manager and Google Analytics Blog | Privacy Policy
Manage Cookie Settings