Keep a page that earns clicks, improve one that gets impressions but few clicks, merge or redirect one with weak impressions into a better page, redirect any page that other sites link to, and delete or noindex pages with no clicks, no impressions and no links. Check the exceptions by hand.

Key takeaways

  • Three signals cover most decisions: clicks over a long window, impressions, and referring domains.
  • Redirect before you delete if anything links to the page. Google documents permanent redirects as a signal that the target should be canonical, so the redirect carries the old page forward.
  • 404 and 410 both remove a page. Google documents that it treats a 410 much like a 404, so the choice is not a ranking lever.
  • Noindex keeps the page for readers but out of search. It only works if the page stays crawlable; see the robots.txt trap below.
  • Pruning is not a proven ranking boost. Google publishes no rule that deleting thin pages raises the rest, so remove pages because they are useless, not for a promised lift.

The three signals

  • Clicks over 12 months from the Performance report (use a long window so seasonal pages are not cut).
  • Impressions, which tell you whether Google shows the page at all.
  • Referring domains from a backlink export. Even a free backlink report is enough for a yes/no.

The decision rules

The rules the script applies. The thresholds are mine, not Google's.
SituationActionBasis
10+ clicks and a healthy click rateKeepPractice
10+ clicks, very low click rateImprove the title and snippetPractice
Few clicks, but another site links to itRedirect to the closest page, or mergeDocumented: permanent redirects signal the target as canonical
Few clicks, some impressions, no linksMerge into a stronger page, then redirectPractice
No clicks, no impressions, no linksDelete (404 or 410) or noindexDocumented: 404 and 410 both drop a URL

The sorting script

Give it the Performance export (Page, Clicks, Impressions) and, optionally, a CSV of Page, Referring domains. Pages that only appear in the links file are included, so an orphan with backlinks is not missed:

import csv, sys

# argv: pages.csv (Page, Clicks, Impressions over 12 months)  [links.csv (Page, Referring domains)]
num = lambda s: int(str(s).replace(',', '') or 0)
pages = {r['Page']: (num(r['Clicks']), num(r['Impressions'])) for r in csv.DictReader(open(sys.argv[1], encoding='utf-8-sig'))}
links = {}
if len(sys.argv) > 2:
    links = {r['Page']: num(r['Referring domains']) for r in csv.DictReader(open(sys.argv[2], encoding='utf-8-sig'))}
for u in links:
    pages.setdefault(u, (0, 0))

groups = {'KEEP': [], 'IMPROVE': [], 'REDIRECT or MERGE (has links)': [], 'MERGE (has impressions)': [], 'DELETE or noindex (no clicks, impressions or links)': []}
for u, (clicks, imp) in sorted(pages.items()):
    rd = links.get(u, 0)
    if clicks >= 10:
        g = 'KEEP' if imp and clicks / imp >= .01 else 'IMPROVE'
    elif rd >= 1:
        g = 'REDIRECT or MERGE (has links)'
    elif imp >= 100:
        g = 'MERGE (has impressions)'
    elif imp == 0:
        g = 'DELETE or noindex (no clicks, impressions or links)'
    else:
        g = 'MERGE (has impressions)'
    groups[g].append((u, clicks, imp, rd))
for g, items in groups.items():
    print('\n%s: %d' % (g, len(items)))
    for u, c, i, rd in items[:8]:
        print('   %-34s clicks %-4d impressions %-5d linking domains %d' % (u, c, i, rd))

I tested it on seven pages built to cover each rule once. All seven landed in the intended group, including a page with zero clicks and zero impressions but four linking domains, which went to redirect rather than delete, and a page with 30 clicks out of 9,000 impressions, which went to improve rather than keep.

Exceptions to check by hand

  • New pages. Anything younger than a few months has no history, so it will sort into "delete" for the wrong reason.
  • Pages that serve other goals: legal, contact, pricing, conversion pages that get no search traffic by design.
  • Seasonal pages, which a short window will undercount.
  • Pages that are noindexed already, which show no impressions for a reason.

When you noindex, do not also block the URL in robots.txt. A crawler that cannot fetch the page never sees the tag, which is the trap explained in noindex vs robots.txt disallow. If you redirect many URLs at once, test the map with the redirect checker.

What this does not cover

The thresholds are judgment calls. The 10-click and 100-impression cut-offs, and the 1% click rate, are mine and should be adjusted for your traffic. The test used seven invented pages, so it proves the rules do what they say, not that they are right for a given site. Search Console exports are capped at 1,000 rows and sampled by query privacy, so very large sites need the API. Nothing here predicts a ranking change.

Badri Dutta

Software engineer · 8 years technical SEO

Written after building the sorter and checking it against known cases. It does not tell you how many pages to cut, because nobody can.

Full background →