Duplicate Site / Domain Confusion in AdSense Review (2026)

Same content on yourbrand.com and yourbrand.net gets AdSense flagged as duplicate or stuck in review. Pick one canonical domain, 301 the rest, fix it.

You bought yourbrand.com and also yourbrand.net “just in case,” and both serve identical content. AdSense review fails, or your site sits in “Getting ready” / “Needs attention” for weeks. The reviewer sees two copies of the same site and can’t tell which one is real. In 2026 this usually surfaces as a “Low value content” rejection with the sub-reason “Copied or duplicate content,” not a friendly “you already have this site” message.

Fastest fix: pick ONE canonical domain, 301-redirect every other domain to it, make sure your alternates return 301 (not 200), then request review on the canonical in AdSense. Don’t try to make the duplicates “unique” and don’t add every variant to AdSense Sites.

This applies equally to apex/www splits, .com/.net/.org sets, staging subdomains that got indexed, and old domains that were never 301’d after a rename.

Which bucket are you in?

SymptomLikely causeJump to
Two+ root domains both return 200Defensive backup domain serving contentCause 1
Old brand still loads after a renameMigrated but old domain still servesCause 2
www and apex both load the pagewww/apex not redirectedCause 3
staging. shows up in GoogleStaging publicly indexedCause 4
*.vercel.app / *.netlify.app in GooglePreview deployment indexedCause 5
AdSense keeps rejecting one root domainA second root domain serves the same contentCause 6

Common causes

Ordered by hit rate, highest first.

1. Defensive backup domain serving content

You bought yourbrand.net and .org for protection and pointed them at the same hosting. All of them now resolve and serve identical pages, so AdSense (and Google) see multiple properties with identical content.

How to spot it:

for d in yourbrand.com yourbrand.net yourbrand.org; do
  echo -n "$d: "
  curl -sI "https://$d" | head -1
done

If all return 200 (instead of 301 to the canonical), you have duplicates.

2. Domain migrated but old domain still serves

You renamed from oldbrand.com to newbrand.com. The new site is live, but old DNS still points at hosting and the old domain still returns content with the old URLs.

How to spot it: curl -sI https://oldbrand.com. If it returns 200, you didn’t fully migrate. It should be a 301 to newbrand.com.

3. www and apex both serving content independently

www.yourdomain.com and yourdomain.com both resolve and serve the page. Google may index both, and they compete as duplicates.

How to spot it:

curl -sI https://yourdomain.com | head -3
curl -sI https://www.yourdomain.com | head -3

One should be a 301 to the other (your choice which is canonical).

4. Staging subdomain is publicly indexed

You have staging.yourdomain.com for QA with no auth. Google found it and indexed it, so it now reads as a duplicate of production.

How to spot it: search site:staging.yourdomain.com on Google. If results appear, staging is publicly indexed.

5. Preview deployments (Vercel/Netlify) indexed

Worth knowing first: by default this is mostly a non-issue. As of June 2026, Vercel sets X-Robots-Tag: noindex automatically on *.vercel.app preview deployments, and Netlify sets X-Robots-Tag: noindex on Deploy Previews, unpublished deploys, and older branch deploys. The real trap is a custom domain attached to a non-production branch on Vercel — in that one case Vercel does NOT set the noindex header, so the preview is crawlable.

How to spot it: search site:vercel.app yourbrand and site:netlify.app yourbrand, then confirm the header directly:

curl -sI https://yourapp-git-feature-yourteam.vercel.app | grep -i x-robots-tag

If x-robots-tag: noindex is missing (typical only on a custom-domain preview branch), you need to add it.

6. Two AdSense Sites for the same content

This is the one that changed. AdSense Site management now operates at the domain (root) level — you can no longer add www.yourdomain.com, https://yourdomain.com/, a trailing-slash variant, or an arbitrary subdomain as a separate Sites entry. AdSense only accepts the registrable domain (for example yourbrand.com, yourbrand.net). So the modern duplication problem isn’t variant entries; it’s adding two genuinely different root domains (yourbrand.com AND yourbrand.net) that serve the same pages.

How to spot it: AdSense → Sites. If two root domains are listed and both serve the same content, that’s your duplicate signal.

Shortest path to fix

Step 1: Decide ONE canonical domain

Usually the shortest, most-marketed, or oldest version. Common choices:

  • yourbrand.com (the .com you actually market)
  • www.yourbrand.com if SSL or CDN constraints favor it
  • The apex if your CDN supports ALIAS / ANAME at root

Pick one and stop second-guessing. Write the decision down somewhere obvious (a CANONICAL_DOMAIN.md in the repo works) so future-you doesn’t flip it.

Step 2: 301-redirect every alternative to canonical

A 301 (permanent) is the strongest canonicalization signal Google supports — stronger than a rel="canonical" tag — so prefer it whenever users don’t need to reach the alternate URL directly.

Cloudflare — Rules → Redirect Rules (the newer UI; Page Rules still works on older accounts):

If: hostname equals yourbrand.net
Then: Static redirect to https://yourbrand.com${path}${query}
Status: 301 (permanent)

Vercelvercel.json on the alternate domain’s project:

{
  "redirects": [
    { "source": "/:path*", "destination": "https://yourbrand.com/:path*", "permanent": true }
  ]
}

"permanent": true emits a 308 (which Google treats like a 301); use "permanent": false only if you genuinely need a temporary redirect. Add this only to the alternate domain’s project — the canonical project gets no redirect.

Netlify_redirects on the alternate site:

https://yourbrand.net/*   https://yourbrand.com/:splat   301!

The trailing ! (“forced”) makes the rule fire even if a matching file exists.

Step 3: Keep staging and previews out of the index

Staging — gate it behind basic auth (best), or block crawling with robots.txt plus a header:

User-agent: *
Disallow: /

robots.txt only stops crawling, not indexing of already-known URLs, so also send a real noindex on every page. The header is the most reliable form:

X-Robots-Tag: noindex

In HTML, the equivalent is a static tag on every page (no framework conditionals needed):

<meta name="robots" content="noindex">

Previews — leave Vercel/Netlify defaults alone; they already send X-Robots-Tag: noindex. The only thing to fix is a Vercel custom domain on a preview branch, which loses the auto-header. Re-add it in vercel.json:

{
  "headers": [
    { "source": "/(.*)", "headers": [{ "key": "X-Robots-Tag", "value": "noindex" }] }
  ]
}

Scope that to the preview project only — never ship noindex to production.

Step 4: Keep AdSense Sites to one root domain per real site

AdSense → Sites. Because management is now domain-level, you generally won’t see www/https/trailing-slash variants here. What you can have is two real root domains. Remove any defensive domain (yourbrand.net, .org) once it 301s to the canonical, and keep a single entry for the domain you’re actually monetizing.

Step 5: Verify the redirects with curl

for d in yourbrand.net yourbrand.org www.yourbrand.com staging.yourbrand.com; do
  echo "=== $d ==="
  curl -sI "https://$d" | head -3
done

Each should return HTTP/2 301 (or 308 from Vercel) and a location: header pointing at https://yourbrand.com/.... A bare path redirect that drops the path (everything lands on the homepage) is a common mistake — confirm https://yourbrand.net/some/article lands on https://yourbrand.com/some/article.

Step 6: Confirm Google’s chosen canonical, then wait

Google has to recrawl every duplicate and follow the 301s, which takes a couple of weeks. Speed it up in Search Console:

  1. URL Inspection → enter your canonical URL.
  2. Check the “Google-selected canonical” field — it should match your canonical.
  3. If it shows a duplicate instead, click Request Indexing, and inspect a few alternate URLs to confirm they report “Page with redirect.”

Expect roughly 2-4 weeks (as of June 2026) for consolidation across a small site; larger sites take longer.

Step 7: Request review on the canonical in AdSense

Once duplicates are 301’d and Search Console shows the right canonical, go to AdSense → Sites and request review on your canonical entry. If the earlier rejection said “Low value content / Copied or duplicate content,” this is the change it was waiting for.

How to confirm it’s fixed

  • curl -sI on every alternate returns 301/308 with a path-preserving location:.
  • site:yourbrand.net and site:staging.yourbrand.com return nothing (or only the canonical) after a recrawl.
  • Search Console “Google-selected canonical” equals your canonical for spot-checked pages.
  • AdSense → Sites lists exactly one entry per genuinely-distinct site, all marked Ready.

When it’s not on you

Even with 301s in place and one AdSense entry, the review queue can lag. AdSense detects consolidation on its next crawl, not instantly, so a correctly-fixed site can still read as “Needs attention” for weeks. If curl, Search Console canonical, and your Sites list all check out, you’ve done your part — wait for the recrawl before changing anything else.

Easy to misdiagnose as

People add multiple variants to “cover all bases,” but that backfires: it tells Google your one site is several properties of identical content, feeding the duplicate-content signal. Keep it minimal — one canonical domain, everything else 301’d, one AdSense Sites entry per truly-different site.

Prevention

  • Pick a canonical domain on day one and document it somewhere obvious.
  • Set up www → apex (or vice versa) redirects before publishing the first article.
  • Leave Vercel/Netlify preview defaults in place; only patch the Vercel custom-domain-on-preview-branch case.
  • Gate staging behind auth, or noindex + robots.txt it.
  • Defensive domains (.net, .org, common typos) should 301 from day one — never let them serve content.

FAQ

  • Can I monetize multiple domains with one AdSense account? Yes, if each hosts genuinely unique content. A movie site and a recipe site under one account are fine; two domains serving the same articles are not.
  • 301 or rel="canonical"? Use a 301 when users don’t need the alternate URL (the case here). Use rel="canonical" only when both URLs must stay reachable, like filtered or print versions of a page.
  • Will Google deindex the duplicate? With 301s in place, Google drops the alternate from the index and consolidates link equity onto the canonical; rankings move with it.
  • AdSense already rejected me for “duplicate content” — do I reapply or wait? Fix the 301s first, confirm the Search Console canonical, then request review again. Reapplying before the redirects are live just earns the same rejection.
  • My Vercel preview is in Google even though I never changed anything. Why? Almost always a custom domain attached to a non-production branch — that’s the one case Vercel skips the auto X-Robots-Tag: noindex. Add the header back (Step 3).

Tags: #AdSense #Monetization #Troubleshooting #Duplicate domain