Back to Tools

Keyword Cannibalisation Finder

Use cases

Identifying content consolidation opportunities Finding internal linking improvements Prioritising page optimisation Cleaning up site architecture

Groups GSC data by query-page combinations using pandas transform("count") to detect competing pages per query.

Calculates mean position and CTR per entry.

Filters by position range, minimum impressions, minimum clicks, and minimum competing pages thresholds.

Parses percentage CTR strings automatically.

Sorts by competing page count and impressions.

Streamlit App GSC Data

Platform

Browser-based (no installation required)

Input

GSC export CSV

CTR column optional (set to 0 when missing)

Flexible column naming with auto-detection

Output

Grouped view: cannibalisation summary by query with totals. Detailed view: all query-page combinations with metrics. Summary cards in dashboard.

Launch App View Source

Features

  • Position range filter (1-100, default 1-20)
  • Minimum impressions threshold (0-100,000)
  • Minimum clicks threshold (0-10,000)
  • Minimum competing pages filter (2-10, default 2)
  • Automatic CTR percentage parsing
  • Grouped view and detailed view exports

How to use

  1. 1 Export GSC data with query and page in each row (API export; the UI export splits them)
  2. 2 Upload CSV (columns auto-detected)
  3. 3 Set position range (default 1-20)
  4. 4 Configure impression, click and competing page minimums
  5. 5 Tick Show full URLs before downloading if you need complete URLs in the grouped CSV
  6. 6 Download grouped or detailed CSV

Frequently asked questions

What input format is required?
A CSV where every row has query, page, clicks, impressions and position together. The GSC UI export splits queries and pages into separate files, so you need an API-style export with both per row. Common column name variants (Top queries, Landing Page, Avg. position and so on) are auto-mapped, and percentage CTR strings like '5.2%' are parsed.
Is a CTR column required?
No. If there is no CTR column the tool fills it with 0 rather than deriving it from clicks and impressions, so the CTR figures in the output are only meaningful if your export included them.
Why are the URLs in my grouped CSV cut short?
The 'Show full URLs' checkbox affects the grouped export as well as the on-screen table: with it off (the default), Best Page is truncated to the last path segment, capped at 50 characters, before the CSV is written. Tick 'Show full URLs' before downloading if you need complete URLs. The detailed CSV always contains full URLs.
How is cannibalisation actually decided?
Rows are filtered by position range (default 1-20) and the minimum impressions and clicks thresholds, then aggregated per query-page pair (clicks and impressions summed, position and CTR averaged). Any query left with at least the minimum number of pages (default 2) is flagged. Because the position filter runs first, a competing page averaging position 25 is not counted under the default range.

Need something built for your business?

This tool started as bespoke client work. I build custom scripts, data pipelines, and full apps for SEO and product data problems that off-the-shelf tools don't solve.

Tell Me What You Need