GA4 attribution goes wrong in one of two directions, and they need different fixes. Either Direct is overreported, because real referred visits fell into the Direct bucket when the referrer got stripped in transit. Or a channel is collecting credit it never earned, usually because a login or payment domain shows up as a self-referral and overwrites the source that actually drove the visit. Both quietly defund whatever's working. Here's how to tell which one is happening in your property, and how to find the channel that's being robbed.
Last week I opened my own GA4, this site's, and found accounts.google.com sitting in the referral report with 150 sessions. Next to it, mail.google.com at 26 and checkout.stripe.com at 14. None of those is a traffic source. They're the Google sign-in screen, Gmail, and the Stripe checkout page, places my own users pass through and bounce back from. Every one of those sessions had a real source before the round trip, usually a google / cpc campaign. GA4 threw that away and stamped the return leg as the source. So the campaign that paid for the signup got nothing, and a login page took the medal.
That's the thing about wrong attribution. It almost never shows up as a number that looks broken. It shows up as a number that looks fine, Direct a little fat, one campaign a little thin, and you make budget decisions on it for months before you notice.
The two shapes of wrong attribution
Before you touch anything, work out which shape you have, because the fixes don't overlap.
The first shape is inflated Direct. Your Direct channel is bigger than it has any right to be, padded with visits that came from somewhere real. GA4 just couldn't read the referrer, so it shrugged and filed them under Direct. Nothing is stealing credit here exactly. The credit is simply going nowhere.
Then there's stolen credit. A source shows up that shouldn't be one at all: your own domain, a payment processor, an OAuth screen. It's sitting in the last-click slot where the real campaign belongs. The conversion still gets counted. It just gets counted for the wrong channel.
You can have both at once, and most sites do. But they answer to different tools, so name the one that's costing you money first.
Why Direct is lying
Direct is supposed to mean "typed the URL, used a bookmark, no referrer." In practice it's become GA4's junk drawer for every visit it couldn't classify, and the drawer keeps filling.
A referrer gets lost in a dozen ordinary ways. A link tapped inside a mobile app hands over nothing. Copy a URL out of a chat, paste it into a fresh tab, and it arrives naked. The jump from an https:// page to an http:// one strips it for browser security, and PDFs, slide decks, and desktop clients never carry one to begin with. Untagged newsletter links, the ones without UTM parameters, land in Direct when they open in a desktop mail client (in webmail they show up as a mail.google.com referral instead, its own kind of misattribution, more below).
The self-inflicted ones sting most, because they're yours to fix. A mis-cased UTM that GA4 silently ignores (utmSource instead of utm_source). A redirect in the chain that drops your query string before GA4 ever reads it. Your own links, losing your own tags.
Two more are subtler because they're about timing, not the link. If your consent banner blocks GA4 on the first page and the tag only fires on page two, the original source is already gone by the time GA4 wakes up, so the whole session goes to Direct. And a session that resumes after GA4's 30-minute inactivity timeout starts fresh, which lands in Direct too when no campaign data is attached and the original source has aged out of the attribution lookback. If that timeout is your bulk of Direct, the lever is the session-timeout setting itself, or a GTM keep-alive: a timer that fires a heartbeat event about every 25 minutes, safely under the cutoff, so an idle tab doesn't roll into a fresh, source-less session.
Then there's the fast-growing slice. AI assistants send real buyers now, and a lot of those clicks arrive with no referrer: the ChatGPT app, in-app browsers, the free tier that doesn't pass one reliably. That traffic piles onto Direct too, which is its own diagnosis; I wrote the full version in tracking AI traffic in GA4. If your Direct has been climbing on deep product URLs rather than the homepage, that's the tell. Genuine direct traffic hits your brand pages, not /products/obscure-sku. As a rough yardstick, Direct much above 20% of sessions on a site that isn't a household name is worth a second look.
Those are the chronic causes, the steady leak. A sudden spike in Direct is usually a different animal: a bot or a consent-scanner crawling the site, a campaign that just launched without UTMs, an influencer who dropped your bare URL somewhere. Chronic Direct is a tracking gap; a spike is an event, and you chase them differently.
The honest part nobody likes: you can't fully recover a referrer that never arrived. What you can do is size it. Inside GA4, a free-form Exploration does it fast: set the dimension to Session default channel group plus Landing page, the metric to Sessions, and filter to Direct. A big share of Direct landing on deep URLs instead of the homepage is misfiled referrals, counted. For a second opinion, open Search Console next to GA4 for the same dates, the same cross-check that settles a sudden GA4 traffic drop: if organic clicks held steady while GA4's organic looks thin and Direct looks fat, you've found where the traffic went. Tag every campaign link you control, and the self-inflicted half disappears.
Self-referral: when your own funnel robs the campaign
This is the one that cost me those 150 sessions, and the one worth checking first because it's specific and fixable.
Any time a user leaves your domain and comes back, the browser reports that other domain as the referrer. A Google or social login, a hosted checkout, an email confirmation link: all of them. GA4 often reads the return leg as a fresh session and stamps that referrer as its source. So accounts.google.com or checkout.stripe.com ends up as the last non-direct source, and the campaign that actually brought the person in gets erased from the conversion path.
The fix lives in a setting most people configured once in the Universal Analytics days and never migrated:
- Open Admin → Data Streams and click your web stream.
- Go to Configure tag settings → Show all → List unwanted referrals.
- Add a condition for each domain your users bounce through:
accounts.google.com, your payment host (checkout.stripe.com,paypal.com), your email link tracker. - Save. GA4 now treats a return trip from those as a continuation of the same session instead of a new source, so the original campaign survives the round trip.
A paste-ready starting set for most sites, one domain per condition (add your own email link tracker):
accounts.google.com
checkout.stripe.com
paypal.com
One thing before you start adding domains: if the offender is a subdomain or another site you own, the root fix is cross-domain measurement (in the same tag settings, under Configure your domains), telling GA4 the two hosts are one property. The unwanted-referrals list is the catch for the third-party round trips you don't control, like a payment host or an OAuth screen. It holds far more domains than a normal site needs, so list every round-trip host you can think of.
Quick map of what goes where:
| What's showing up as a source | The right fix |
|---|---|
Payment host (checkout.stripe.com, paypal.com) | Unwanted-referrals list |
OAuth / login screen (accounts.google.com) | Unwanted-referrals list |
| Your email link tracker | Unwanted-referrals list, or UTM-tag the links |
| A subdomain or another site you own | Cross-domain measurement (Configure your domains) |
| A real referrer (an AI assistant, a blog, a partner) | Leave it. That's traffic you want credited |
Two things the how-to posts skip. It isn't retroactive, so it only cleans data going forward; don't expect last quarter to heal. And the credit lands right either way. Excluding a domain stops GA4 from recording it as a source: the return hop reads as direct, not as a new referral. Traffic-acquisition reports then use last-non-direct-click logic, so they look past the direct hop to the last real source. The login page never gets to keep it. Your conversion attribution model is a separate setting, data-driven by default, but it works the same way: the campaign gets its medal back.
One caution while you're in there. Exclude the round-trip domains, not the ones that are real traffic. gemini.google.com sending you visitors is a genuine AI referral; don't bury it with the sign-in screen.
Half of "wrong attribution" is reading the wrong column
Before you conclude your data is broken, make sure you're not looking at the wrong dimension. This one isn't a bug. It's a scope mix-up, and it's a common cause of reports that look like they contradict each other.
GA4 keeps two different answers to "where did this person come from." First user source is the acquisition source, the very first touch, frozen for the life of that user. Session source is where this particular session started, which changes every visit. Someone who first found you through a google / cpc ad in March and came back last night by typing your URL shows google / cpc as first-user source and (direct) as session source. Both are correct. They answer different questions.
Traffic acquisition reports use session source; user acquisition reports use first-user source. Read a conversion against the wrong one and the same purchase looks like it came from two different channels. When a report contradicts itself, check which scope you're on before you decide GA4 is lying. Usually it isn't. You're comparing a first touch to a last one.
The 2026 changes that moved your numbers while you sat still
If your attribution held steady for a year and suddenly drifted in 2026, you probably didn't break anything. Google did the moving.
GA4 restructured its attribution model in April 2026 and reshuffled how credit lands in conversion reports. That's why a lot of people watched a channel gain or lose credit overnight with no change in their own setup. Then in June it added a Source Group dimension that folds facebook, fb, and m.facebook.com into one value, applied to historical data so year-over-year comparisons don't snap. Days later Google retired Signals as a separate control over the data GA4 shares with Ads, leaving the ad_storage consent parameter as the only gate, quieter to break and harder to spot when it does.
None of this is a bug to fix. It's context. If the shape of your attribution changed and your tags didn't, check the date against Google's GA4 release notes before you go hunting for a tracking fault that isn't there.
What "wrong" actually costs
Here's the part that reframes the whole thing. Wrong attribution almost never loses you a conversion. The purchase still fires, the revenue still lands. GA4's attribution model only redistributes credit among channels, it never changes the total. Total revenue is the sum of your purchase events whatever the model does with the channel column, which is the same reason GA4 and Shopify can disagree on the number without either being wrong about sales.
So the cost isn't lost sales. It's misallocated budget. When a self-referral hands your paid campaign's conversions to Direct, the campaign's ROAS reads worse than it is, and the obvious "data-driven" move is to cut spend on the thing that's actually working. Wrong attribution doesn't empty your funnel. It gets you to defund it yourself. If the metric genuinely fell rather than just moved columns, that's a different investigation, the conversion rate drop diagnostic, but rule out the credit shuffle first.
The faster way to find it: ask instead of click
Everything above is doable by hand: open the referral report, eyeball Direct against Search Console, cross-check scopes, read the dates. It works. It's also tedious enough that most people run it once after something breaks and never again, which is how a self-referral sits there for three months.
The 2026 shortcut is to wire GA4 to an assistant over MCP and just ask. With a GA4 MCP server attached to Claude or ChatGPT, the whole diagnosis collapses into a few questions against your live data:
- "List my top referral sources for the last 90 days. Flag any that look like login, checkout, or payment domains stealing session credit."
- "Is my Direct channel overreported? Compare Direct sessions landing on deep pages versus the homepage, and compare organic sessions to Search Console clicks for the same dates."
- "Which channels gained or lost conversion credit in the last 30 days versus the 30 before, and did anything change in my tagging or just in the model?"
- "Show first-user source next to session source for my converting users. Where do they disagree?"
There are more in the GA4 prompts library, and either assistant will run them (where Claude and ChatGPT differ for analytics is its own comparison). That's the job the connector is actually good at. It isn't for building the report. It's for reading the property and telling you which channel got mis-credited. It only reads GA4, so it knows exactly what GA4 knows, the Direct blind spot included, but it turns a half-hour of clicking into a question you'll bother to ask.
That's what we built ConvRadar for (yes, this site is ours). Point its traffic-quality scoring at your property and the polluted sources come back flagged instead of buried: self-referrals, login domains wearing your campaign's credit, Direct that's really misfiled referrals. It's a hosted GA4 MCP server you set up in the browser, no terminal and no service account (the tradeoff against Google's official server), and it hands Claude and ChatGPT the conversion-diagnostic tools to answer "which of my sources is fake, and who's getting robbed?" in one message. Setup runs about five minutes in Claude or ChatGPT, free during the open beta, email signup, no card. It won't touch your GA4 settings for you; the unwanted-referrals list is still a thing you go flip. What it will do is find the flip you needed before you'd have noticed on your own.
FAQ
Why is my GA4 attribution wrong?
Two usual causes. Either the referrer got stripped and a real visit fell into Direct (mobile apps, copied links, https→http, untagged email, a consent banner that fires late, a session resuming after the 30-minute timeout), or a domain your users bounce through, a login screen, a payment host, your own site, registered as a self-referral and overwrote the campaign that actually drove the visit. The first inflates Direct; the second hands credit to the wrong channel. They need different fixes, so identify which one you have first.
Why is my direct traffic so high in GA4? Direct is GA4's catch-all for any session it can't attribute, and modern browsing keeps feeding it: in-app clicks, pasted URLs, referrer-blind PDFs, AI assistants that don't pass a referrer, and consent setups that lose the source before the tag fires. A quick sanity check: real direct traffic lands on your homepage and brand URLs. When Direct climbs on deep internal pages, or sits much above 20% of sessions for a site that isn't a household name, it's misfiled referred traffic, not people typing your address.
How do I fix a self-referral in GA4? Add the offending domains under Admin → Data Streams → your web stream → Configure tag settings → List unwanted referrals: your payment host, OAuth and login domains, email link tracker. GA4 then treats a return trip from those as the same session instead of a new source. It isn't retroactive, so it fixes data going forward only. Exclude round-trip domains only; don't bury a genuine referrer like an AI assistant that's actually sending you traffic. For subdomains or other sites you own, set up cross-domain measurement instead.
What's the difference between first user source and session source?
First user source is the acquisition touch, the very first source for that user, frozen. Session source is where the current session started, which changes every visit. A user acquired via paid search who returns directly shows google / cpc as first-user source and (direct) as session source. Both are right; they answer different questions. Reading a conversion against the wrong scope is a common cause of "attribution that contradicts itself."
Did GA4 change attribution in 2026?
Yes. GA4 restructured its attribution model in April 2026, reshuffling how credit lands in conversion reports, and in June added a Source Group dimension that groups variant source strings (facebook, fb, m.facebook.com) into one value, applied to historical data, while retiring Google Signals as a separate control over data shared with Ads. If your attribution drifted in 2026 and your tags didn't change, check the dates against Google's GA4 release notes before hunting for a fault.
Does wrong attribution mean I'm losing conversions? No. The attribution model only moves credit between channels; it never changes total conversions or revenue. Your sales are intact. What you lose is an accurate read on which channel earned them, which leads to cutting budget on the thing that's quietly working. It's a decision problem, not a lost-revenue problem.
Find the channel that's getting robbed
Open your referral report and read the list like a skeptic. A login screen, a checkout page, your own domain: that's credit in the wrong pocket, the same medal accounts.google.com was wearing on my own site. Anything padding Direct on deep pages is a source GA4 couldn't read. Neither cost you the sale. Both are costing you the next budget decision. Wire GA4 to your assistant and ask it straight: "which of my traffic sources is fake, and which real channel is it stealing credit from?" The answer is usually one line, and usually one you've been paying for.