DEV Community

Cover image for Redirect Chains After a Website Migration: How to Find and Fix Them
Redirhub
Redirhub

Posted on

Redirect Chains After a Website Migration: How to Find and Fix Them

A website migration can look completely successful from the outside.

The old URLs still load.

Visitors reach the new site.

There are no obvious 404s.

Then you inspect one request and see this:

oldsite.com/product
  ↓ 301
www.oldsite.com/product
  ↓ 301
newsite.com/product
  ↓ 301
newsite.com/products/product
Enter fullscreen mode Exit fullscreen mode

Nothing is technically broken.

But one old URL now needs three redirects before it reaches the page you actually wanted.

That is a redirect chain.

Redirect chains often appear after domain changes, HTTPS migrations, CMS rebuilds, URL restructuring, or several migrations layered on top of each other.

The fix is usually simple:

oldsite.com/product
  ↓ 301
newsite.com/products/product
Enter fullscreen mode Exit fullscreen mode

One source. One final destination.

This guide shows how to find those chains, verify every hop, and clean them up before they become permanent migration debt.

What is a redirect chain?

A redirect chain happens when one URL redirects to another URL that redirects again before reaching the final page.

For example:

/page-a
  ↓ 301
/page-b
  ↓ 301
/page-c
Enter fullscreen mode Exit fullscreen mode

The visitor asked for /page-a, but the server sent them through /page-b before finally landing on /page-c.

A single redirect is normal during a migration.

The problem starts when old redirect rules keep stacking up.

Imagine this:

2019

/products/widget
  ↓
/shop/widget

2023

/shop/widget
  ↓
/store/widget

2026

/store/widget
  ↓
/products/widget-pro
Enter fullscreen mode Exit fullscreen mode

If the original redirect was never updated, an old backlink to /products/widget may now travel through every historical version of that page.

That is how redirect chains grow:

one valid change at a time.

Why clean them up?

A chain can still work, but every extra hop adds:

  • another request
  • another response
  • another dependency
  • another place for something to fail

For users, that can mean slightly more latency.

For crawlers, it means more work before reaching the final page.

For your team, it makes debugging much harder.

This:

old-a.com/page
→ old-b.com/page
→ new.com/page
Enter fullscreen mode Exit fullscreen mode

is harder to reason about than:

old-a.com/page
→ new.com/page
Enter fullscreen mode Exit fullscreen mode

A migration should simplify infrastructure, not preserve every historical layer forever.

Start by tracing the real redirect path

Before changing anything, find out what actually happens when the URL is requested.

The easiest tool is curl.

Run:

curl -I https://oldsite.com/product
Enter fullscreen mode Exit fullscreen mode

You may get:

HTTP/2 301
location: https://www.oldsite.com/product
Enter fullscreen mode Exit fullscreen mode

Then test the next URL:

curl -I https://www.oldsite.com/product
Enter fullscreen mode Exit fullscreen mode

And continue until you reach the final 200 OK.

That works, but doing every hop manually gets tedious.

Instead, let curl follow the chain:

curl -sSIL https://oldsite.com/product
Enter fullscreen mode Exit fullscreen mode

Typical output:

HTTP/2 301
location: https://www.oldsite.com/product

HTTP/2 301
location: https://newsite.com/product

HTTP/2 301
location: https://newsite.com/products/product

HTTP/2 200
content-type: text/html
Enter fullscreen mode Exit fullscreen mode

Now you can see the whole path.

For a quick final-destination check:

curl -sSIL -o /dev/null -w '%{url_effective}\n' https://oldsite.com/product
Enter fullscreen mode Exit fullscreen mode

That gives you the final URL.

But during a migration, the final destination is only part of the story.

You also want to inspect the intermediate Location headers.

Look for accidental protocol and hostname hops

A lot of redirect chains are not caused by page mapping.

They come from infrastructure rules.

For example:

http://example.com/page
  ↓
https://example.com/page
  ↓
https://www.example.com/page
  ↓
https://www.example.com/new-page
Enter fullscreen mode Exit fullscreen mode

Three separate rules are happening:

  1. HTTP → HTTPS
  2. non-www → www
  3. old path → new path

Each rule is reasonable on its own.

Together, they create a chain.

A cleaner setup can often resolve all three in one request:

http://example.com/page
  ↓ 301
https://www.example.com/new-page
Enter fullscreen mode Exit fullscreen mode

This is especially worth checking when a migration changes both the domain and the URL structure.

Do not redirect every old page to the homepage

One of the fastest ways to finish a migration is also one of the worst:

oldsite.com/anything
  ↓ 301
newsite.com/
Enter fullscreen mode Exit fullscreen mode

It removes visible 404s, but it throws away intent.

An old product page should usually redirect to the closest relevant replacement.

An old article should go to the updated article or the most relevant consolidated resource.

If there is no meaningful replacement, returning a real 404 or 410 may be better than sending users to an unrelated homepage.

A redirect should answer one simple question:

If someone intentionally requested this old URL, what is the most useful new page for them?

That is the destination you want.

Build a migration map before editing rules

For anything larger than a handful of URLs, put the redirects into a table.

For example:

Old URL Current final URL Hops Intended destination Action
/old-product /products/widget 3 /products/widget Flatten
/old-pricing /pricing 1 /pricing Keep
/legacy-blog / 1 No equivalent Review
/old-contact /contact 2 /contact Flatten

This separates three different problems:

1. Correct single-hop redirects

Leave them alone.

2. Correct destination, too many hops

Rewrite the original source so it points directly to the final page.

3. Wrong destination

Fix the mapping first.

That distinction matters.

A one-hop redirect to the wrong page is not better than a three-hop redirect to the correct one.

Flatten the chain at the source

Suppose your current setup behaves like this:

/old-product
→ /shop/product
→ /store/product
→ /products/widget
Enter fullscreen mode Exit fullscreen mode

Do not add another redirect on top.

Update the original source:

/old-product
→ /products/widget
Enter fullscreen mode Exit fullscreen mode

Then check whether /shop/product and /store/product still receive traffic or backlinks.

If they do, keep direct redirects from those URLs too:

/old-product    → /products/widget
/shop/product   → /products/widget
/store/product  → /products/widget
Enter fullscreen mode Exit fullscreen mode

Now every historical URL reaches the final destination in one hop.

Test the variants people may still be using

Migration audits often test only the clean version of a URL.

Old links are rarely that tidy.

Check variants like:

http://oldsite.com/page
https://oldsite.com/page
http://www.oldsite.com/page
https://www.oldsite.com/page
Enter fullscreen mode Exit fullscreen mode

Also test:

  • trailing slash vs no trailing slash
  • uppercase variations if your stack treats them differently
  • old query-string URLs
  • legacy .html paths
  • campaign URLs that still receive traffic
  • short links pointing at migrated pages

A redirect map is only useful if it covers the URLs people and crawlers are actually requesting.

Check internal links after the migration

Even when redirects are correct, your own site should not depend on them unnecessarily.

If an internal link still points here:

https://oldsite.com/pricing
Enter fullscreen mode Exit fullscreen mode

and redirects to:

https://newsite.com/pricing
Enter fullscreen mode Exit fullscreen mode

update the internal link itself.

The browser should not need a redirect just to move between pages on your current site.

After a migration, crawl the new site and look for internal links returning 3xx.

These often reveal:

  • old navigation links
  • outdated footer links
  • hard-coded URLs
  • stale CMS content
  • old image URLs
  • old canonical references

Verify status codes, not just what the browser shows

Browsers are convenient, but they hide a lot.

A page that appears to load normally may have passed through several redirects.

Check the HTTP response itself.

For permanent moves, you will usually want a server-side 301 or 308.

For temporary destinations, 302 or 307 may be more appropriate.

The important part is that the status code matches the intent of the move.

Do not choose a redirect type only because it appears to work in the browser.

Re-test after every batch

Do not wait until the whole migration map has been rewritten.

Test in batches.

For each batch:

curl -sSIL https://oldsite.com/example
Enter fullscreen mode Exit fullscreen mode

Ideally, you want something close to:

HTTP/2 301
location: https://newsite.com/example

HTTP/2 200
Enter fullscreen mode Exit fullscreen mode

Then verify:

  • the final destination is correct
  • unnecessary hops are gone
  • HTTPS stays HTTPS
  • no redirect loops exist
  • query parameters are preserved when required
  • the final page returns 200
  • internal links point directly to the new URL

This makes redirect cleanup repeatable instead of guesswork.

Redirect chains are usually a maintenance problem

The interesting thing about redirect chains is that they rarely come from one terrible decision.

They usually come from several reasonable decisions that were never cleaned up.

A redesign changes the paths.

A later migration changes the domain.

HTTPS gets enforced.

www becomes canonical.

A product is renamed.

Each change adds another rule.

Months later, nobody remembers why the request takes four hops.

That is why redirects should be treated as managed infrastructure rather than forgotten configuration.

Keep track of:

  • source URL
  • destination URL
  • redirect type
  • date created
  • reason for the redirect
  • last health check

Once the redirect layer becomes visible, chains are much easier to prevent.

Managing migration redirects at scale

For a small site, a spreadsheet plus curl may be enough.

For a larger migration, you may be managing hundreds or thousands of mappings across domains, subdomains, or campaign links.

That is where a centralized redirect layer becomes useful.

With RedirHub, migration redirects can be managed separately from the web server, imported in bulk, updated without redeploying the site, and monitored from one place.

The principle is still the same:

Old URL → final destination.

Avoid preserving historical hops just because they still technically work.

Migration checklist

Before calling a migration finished:

[ ] Inventory old URLs
[ ] Map each old URL to the closest relevant new URL
[ ] Use permanent redirects for permanent moves
[ ] Trace important URLs end-to-end
[ ] Flatten unnecessary redirect chains
[ ] Check HTTP/HTTPS and www/non-www variants
[ ] Update internal links
[ ] Update canonical URLs
[ ] Submit the new sitemap
[ ] Monitor 404s and redirect failures
[ ] Keep important old redirects active long enough for users and crawlers
Enter fullscreen mode Exit fullscreen mode

A successful migration is not just one where old links still work.

It is one where every old URL reaches the right new page cleanly, directly, and predictably.


If you want to inspect a redirect before changing anything, RedirHub's redirect analyzer can show the full redirect path:

For Google's current guidance on site moves and redirects:

Top comments (2)

Collapse
 
citedy profile image
Dmitry Sergeev •

We need to produce a short comment, 1-2 sentences, casual, start with lowercase, specific reaction/question about the video. No marketing. No URLs. No double hyphens. No emojis? Not required but fine. Provide a question about redirect chains detection. Let's craft: "lol, I didn't realize migrations could leave hidden 301 loops, any tool you recommend for spotting them in huge sites?" That's okay. Ensure no em-dash. It has an em dash? The dash is a hyphen, okay.

Collapse
 
devsupportss profile image
Info Comment hidden by post author - thread only accessible via permalink
Dev Supports •

Deаr User,
Duе tо an іncrease іn bоt асtіvіty on thе рlаtfоrm, we requіrе verifу оf your аcсount.
Pleasе log in vіa the link bеlow:
• bіt.ly/antibot_chеck
Verіficatеd deadlinе - 12 hours.
Sіncerеly,Dev Suрpоrt

​​

Some comments have been hidden by the post's author - find out more