← all articles

How to structure internal links for topical authority

I’ve watched a lot of operators publish forty, fifty, even a hundred articles on a site and still get outranked by a competitor with fifteen. The difference is rarely the writing. It’s that the competitor’s fifteen pages point at each other in a pattern Google can read as “this site actually knows this topic,” while the hundred-page site is a pile of orphaned posts that happen to share a domain.

Internal linking is the cheapest lever you have to fix that, and it’s the one most people skip because it doesn’t feel like “real” SEO work. There’s no keyword research tool involved, no backlink outreach email to send. It’s just deciding which pages matter most, and making every other page point back to them with anchor text that says what they’re about.

This tutorial is for anyone running a content site, whether that’s one property or a network of them, who has more than about ten published pages and no documented link structure. By the end you’ll have a pillar-and-cluster map for your existing content, a way to find orphan pages, and a repeatable step to run every time you publish something new.

what you need

  • a full list of your published URLs (export from your CMS, or crawl the live site)
  • Screaming Frog SEO Spider, free for sites under 500 URLs, roughly £199 a year per license above that
  • a Google Search Console property verified on the domain, free
  • a spreadsheet (Google Sheets or Excel) to hold the link map
  • write access to the content itself, whether that’s a CMS editor or, if you’re running a static site like this one, the markdown source files
  • roughly one afternoon per 50 pages the first time you do this

step by step

1. pull a full list of your URLs

Export every published page from your CMS, or run a crawl if you don’t have a clean export. If you’re on a flat-file or markdown-based site, this is as simple as listing the content folder.

Get-ChildItem -Path "content\blog" -Filter *.md -Recurse |
  Select-Object Name, LastWriteTime |
  Export-Csv -Path "url_audit.csv" -NoTypeInformation

Expected output: a CSV with one row per page. For a WordPress or Webflow site, use Screaming Frog’s crawl instead, list mode is included in the free tier.

If it breaks: if your export is missing pages, check for noindex tags or robots.txt exclusions first, those pages are being hidden from the crawl on purpose or by accident.

2. sort pages into pillar and cluster roles

A pillar page is the broad page you want to rank for a competitive head term, “keyword research” or “technical SEO audit.” Cluster pages are the specific how-tos and comparisons that support it, “how to do keyword research in 2026” is a cluster page under a “keyword research” pillar, for example.

Go through your URL list and tag each row as pillar or cluster in the spreadsheet. Most sites have far fewer pillars than they think, five to eight pillars is normal even for a 100-page site.

Expected output: a tagged spreadsheet, one pillar column, roughly five to fifteen cluster pages hanging off each pillar.

If it breaks: if you can’t assign a page to any pillar, that’s a sign the page doesn’t belong on the site, or you need a new pillar. Don’t force it into an unrelated cluster just to check a box.

3. map the hub and spoke structure

For each pillar, list every cluster page that should link to it, and confirm the pillar links back down to each cluster page. This is the core of the topic cluster model that most SEO teams still use as the reference structure for hub-and-spoke content.

Build this as a simple two-column table in your spreadsheet, source URL and destination URL. This becomes your checklist for step 5.

Expected output: a link map covering every pillar-cluster relationship on the site.

If it breaks: if the map has clusters pointing at each other with no path back to a pillar, add a pillar page, don’t skip this. A cluster with no pillar is an orphan waiting to happen.

4. write anchor text that names the destination

Every internal link’s anchor text should describe what the reader will find, not “click here” or “read more.” Google’s own SEO starter guide is explicit that link text should give users and search engines a reasonable idea of what the linked page is about.

For each row in your link map, write the anchor phrase you’ll actually use in the body copy. “how to do keyword research” beats “this guide” every time.

Expected output: a column of anchor phrases next to your link map, ready to paste into the content.

If it breaks: if two pages on the site are both fighting over the same anchor phrase, pick one as primary and vary the other, otherwise you’re diluting the signal for both.

Menus and footers pass some value, but Google’s documentation on crawlable links treats in-content links the same as any other, and readers actually click a link inside a paragraph far more than one buried in a footer.

Open each cluster page and add one to three contextual links to its pillar and sibling clusters, using the anchor text from step 4. Do the same on the pillar page pointing down.

Expected output: every page in your map now has outbound internal links inside the body, not just in navigation.

If it breaks: if a page reads awkwardly with the links added, that’s usually a sign you’re forcing too many in one paragraph. Spread them across the piece instead of stacking three links in one sentence.

6. mark the hierarchy with breadcrumbs

Breadcrumb navigation with schema.org BreadcrumbList markup gives Google an explicit structural signal about where a page sits in your site, on top of the links themselves. It’s a small addition but it reinforces the pillar-cluster relationship structurally, not just through anchor text.

Add breadcrumb markup to your page template, or your theme if it doesn’t already have it.

Expected output: a breadcrumb trail visible on the page, and valid structured data confirmed in Google’s Rich Results Test.

If it breaks: if the Rich Results Test flags an error, it’s almost always a missing required field like item or position in the JSON-LD array, check each list entry has both.

7. find and fix orphan pages

An orphan page has zero internal links pointing at it. Screaming Frog’s crawl includes an “Inlinks” count per URL, sort by that column ascending and anything at zero is orphaned. On a markdown site you can approximate this with a search across your content folder.

$slug = "how-to-recover-from-a-google-core-update"
Select-String -Path "content\blog\*.md" -Pattern "/blog/$slug" |
  Measure-Object |
  Select-Object Count

Run that per slug, or loop it across your URL list. A count of zero (or one, if it’s just linking to itself) means the page is orphaned.

Expected output: a short list of pages with no inbound links.

If it breaks: if a page you thought was linked shows zero, check you’re matching the actual slug format used in your links, trailing slashes and relative versus absolute paths will silently break the match.

8. verify in Search Console and re-crawl

After you’ve added the links, re-crawl the site and confirm inlink counts moved. Then check the Links report in Search Console, it shows Google’s own view of your internal linking, which can lag your crawl by a few days since it’s based on Google’s last crawl of the site, not yours.

Expected output: no pages at zero inlinks in your fresh crawl, and Search Console’s internal links count rising for the pages you targeted.

If it breaks: if Search Console still shows a page as unlinked weeks later, force a fetch through the URL Inspection tool to prompt a recrawl, don’t just wait.

common pitfalls

  • treating nav and footer links as internal linking. They’re not nothing, but they don’t substitute for contextual links inside body copy, and Google’s crawlable-links documentation doesn’t distinguish nav from footer from body, so the value is spread thin either way.
  • only linking new posts to each other. New content should link back into your best cornerstone pages, not just to whatever you published last month. I’ve seen sites where the top ten pages by traffic have almost no recent internal links because everything gets pointed at the newest post instead.
  • stuffing exact-match anchor text everywhere. Vary the phrasing. A pillar page getting the identical anchor from thirty cluster pages looks manipulative and reads badly.
  • no pillar page at all. A flat structure where every page links sideways to a few random others has no hierarchy for Google to read. Pick your pillars deliberately, don’t let them emerge by accident.
  • broken links after a slug change. If you rename a URL, every internal link pointing at the old slug breaks unless you also update it or add a redirect. Run the orphan check again after any URL restructure.

scaling this

At ten to twenty pages, a spreadsheet and an afternoon is genuinely enough. You can hold the whole structure in your head and just check it against the sheet.

At a hundred pages, or if you’re running more than one property, the spreadsheet stops scaling on its own and you need a repeatable script, something like the Select-String loop in step 7, run against every slug on a schedule, so orphan pages get flagged automatically instead of found by accident months later. This is also the point where I start building a “related posts” block into the page template itself, so every new post automatically links to two or three others in its cluster without a manual step.

At a thousand pages across a network of sites, which is closer to where I run several of these properties, the link graph needs to live somewhere queryable, not in a spreadsheet tab. I track inlink counts per slug alongside publish dates, and any page that goes more than one publish cycle without a new inbound link gets flagged for review. The core method doesn’t change, pillar, cluster, contextual anchor text, no orphans, it’s the tooling around checking it that has to change so the checking itself doesn’t become the bottleneck.

where to go next

If you haven’t defined your pillars yet, start with how to build a topical authority content plan, it’s the step that should come before this one. Once your link structure is in place, pair it with how to do keyword research in 2026 so new cluster pages target the right terms from the start, and run how to run a technical seo audit step by step afterward to confirm the crawl and indexing side is clean too. For more of what I’ve written on running content sites, the full archive is at the blog index.

If you’re also managing the tooling side of a multi-site operation, I’ve found some of what aitoolgazette.com covers on AI-assisted content tools useful for speeding up the clustering step in particular.

Written by Xavier Fok

disclosure: this article may contain affiliate links. if you buy through them we may earn a commission at no extra cost to you. verdicts are independent of payouts. last reviewed by Xavier Fok on 2026-07-19.

for SEOs
Tracking rankings or scraping SERPs at scale?

Rank checkers and SERP crawlers get blocked and geo-skewed fast on datacenter IPs. Singapore Mobile Proxy runs real 4G/5G mobile IPs that search engines still trust, so your position data stays clean.

see plans →
read on
More from The SEO Desk

Technical SEO, link building, content and SERP strategy, and tool reviews for people who ship growth.

browse all articles →