
How to Redirect a Page in WordPress?
Every time you delete a page, rename a slug, or restructure how your site's URLs are organized, every existing link pointing to the old address, from Google's index, other websites, bookmarks, and social shares, starts leading to a 404 instead. A redirect fixes that by automatically sending visitors (and search engine crawlers) from the old URL to the correct new one, without them ever seeing a broken page.
WordPress doesn't include a page-level redirect setting out of the box, so in this guide, you'll set one up three ways: with a dedicated plugin (the easiest, best option for most sites), directly in your server config for maximum performance, and in code if you want redirect logic tied to specific conditions in your theme or a custom plugin.
301 vs. 302: Which One Do You Actually Need?
Before setting anything up, pick the right status code, since using the wrong one causes real, if subtle, problems:
- 301 (Permanent Redirect) tells browsers and search engines the move is permanent. Google will transfer the old URL's search ranking and indexed status to the new one, and browsers are allowed to cache this redirect long-term.
- 302 (Temporary Redirect) tells them the move is temporary, so Google keeps the original URL indexed and doesn't transfer ranking signals to the destination, and browsers won't cache it long-term.
For almost every real-world case, changed permalinks, deleted pages replaced by new ones, domain migrations, you want a 301. Reach for a 302 only for genuinely temporary situations, like redirecting to a maintenance page during a specific window.
Method 1: Use a Redirect Plugin (Recommended for Most Sites)
Redirection is a free, well-maintained plugin that handles this without touching a single file, and it's the right choice for most sites because it also logs 404 errors, so you can see exactly which broken URLs actually need a redirect instead of guessing.
- Install and activate Redirection from Plugins → Add New.
- Go to Tools → Redirection.
- Under the Redirects tab, enter the Source URL (the old path, for example
/old-page/) and the Target URL (the new path, for example/new-page/). - Leave the group and match settings on their defaults for a simple one-to-one redirect, and click Add Redirect.
The redirect takes effect immediately, no caching or saving step required. If you're migrating a large number of URLs at once (for example, after a site restructure), Redirection also supports importing a CSV file of source/target pairs from Tools → Redirection → Import/Export, which is far faster than adding hundreds of redirects one at a time through the UI.
Checking What's Actually 404ing
Before setting up redirects for a whole site migration, check Redirection → 404s, which logs every URL that's returned a 404 to a real visitor. This turns "which old URLs do I need to redirect?" from a guess into a data-driven list, prioritized by what's actually still being requested.
Method 2: Redirect With .htaccess (Apache)
If your site runs on Apache (most shared hosting does), redirects added directly to .htaccess are faster than a plugin, because Apache handles them before WordPress even loads, without the overhead of bootstrapping PHP for a request that's just going to redirect anyway.
Connect via FTP or your host's file manager, and open .htaccess in your WordPress root. Add your redirect above the # BEGIN WordPress block, since rules placed inside or after WordPress's own rewrite block can behave unpredictably:
Redirect 301 /old-page/ https://yoursite.com/new-page/
# BEGIN WordPress
...
# END WordPress
For redirecting an entire old section of URLs to a new one, use RedirectMatch with a regular expression instead of listing every URL individually:
RedirectMatch 301 ^/old-category/(.*)$ https://yoursite.com/new-category/$1
The (.*)$ captures whatever follows /old-category/ in the original URL, and $1 reinserts it into the destination, so /old-category/post-name/ correctly becomes /new-category/post-name/ rather than every URL under the old category collapsing to the same destination.
Method 3: Redirect With Nginx
If your site runs on Nginx instead of Apache, .htaccess has no effect at all, since Nginx doesn't read it. Add the redirect to your site's server block configuration instead:
location = /old-page/ {
return 301 /new-page/;
}
location ~ ^/old-category/(.*)$ {
return 301 /new-category/$1;
}
Unlike Apache, changes to an Nginx config require reloading the service to take effect:
sudo nginx -t && sudo systemctl reload nginx
Always run nginx -t first, since it validates your configuration syntax before reloading; skipping this step and reloading a broken config can take your entire site down.
Method 4: Redirect With Code
If you want redirect logic that depends on something dynamic (a user's role, a query parameter, or a condition your theme already checks), or you'd rather keep this logic version-controlled with your codebase instead of stored in a plugin's database table, hook into template_redirect:
add_action( 'template_redirect', function () {
if ( is_page( 'old-page-slug' ) ) {
wp_redirect( home_url( '/new-page-slug/' ), 301 );
exit;
}
} );
template_redirect is the correct hook for this, rather than something earlier like init, because it fires after WordPress has already determined which page matched the request, so conditional tags like is_page(), is_single(), and is_category() are fully available. The exit immediately after wp_redirect() is required, since without it, WordPress would continue loading and rendering the original page's template even after sending the redirect header.
For redirecting several specific pages at once, an array lookup keeps this readable as it grows:
add_action( 'template_redirect', function () {
$redirects = [
'old-page-one' => '/new-page-one/',
'old-page-two' => '/new-page-two/',
];
foreach ( $redirects as $old_slug => $new_path ) {
if ( is_page( $old_slug ) ) {
wp_redirect( home_url( $new_path ), 301 );
exit;
}
}
} );
Testing That a Redirect Actually Works
Don't just click the old link in a browser and eyeball where it lands, since browsers cache 301s aggressively, which can make a broken redirect look like it's still working from a previous successful test. Use curl to see the raw response instead:
curl -I https://yoursite.com/old-page/
A working redirect returns something like:
HTTP/2 301
location: https://yoursite.com/new-page/
If you see a 200 instead of a 301, the redirect isn't active yet. If you see a location header pointing somewhere unexpected, or a chain of multiple redirects before landing on the final URL, that's worth fixing directly, since redirect chains slow down the request for both crawlers and visitors, and each hop in the chain is a place where the redirect can silently break later.
Avoiding Redirect Loops and Chains
Two mistakes are common enough to call out specifically:
- A redirect loop happens when a URL eventually redirects back to itself, directly or through a chain of other redirects, and browsers will show an error like "too many redirects" rather than a page. This usually happens when a source and target URL get swapped by mistake, or when both a plugin and a manual
.htaccessrule redirect the same URL to two different destinations that then bounce between each other. - A redirect chain is when URL A redirects to B, which redirects to C, instead of A redirecting straight to C. These accumulate naturally over time as a page moves more than once; periodically check your redirect list (or the Redirection plugin's log) for any source that also appears as a target elsewhere, and collapse the chain down to a single hop.
Frequently Asked Questions (FAQ) About Redirecting Pages in WordPress
Yes, this is the main reason to use a 301 specifically. Google treats a 301 as a signal that the content has permanently moved and transfers the accumulated ranking signals to the new URL over time, though it's not always instant, it can take days to weeks for search results to fully update.
Redirect it if the page had any incoming links, search traffic, or indexed history, since a 404 discards all of that. If a page truly had no traffic or backlinks and the content genuinely no longer exists anywhere on your site, a 404 (or a 410 Gone, which more explicitly signals permanent removal) is reasonable.
.htaccess redirects are technically faster, since Apache handles them before PHP and WordPress even load. In practice, this difference is negligible for a normal number of redirects; reach for .htaccess when you want redirects independent of WordPress being installed at all (like during a migration), and a plugin for everything else, since it's easier to manage and audit later.
Yes, add a rule like RedirectMatch 301 ^(.*)$ https://newdomain.com$1 to the old domain's .htaccess file (with the old domain still pointed at hosting that can serve this rule), which preserves the full path and query string across the move. This is typically combined with a WP-CLI wp search-replace on the database if you're also migrating the WordPress installation itself.
The most common cause is a caching layer serving a stale response: a full-page caching plugin, your host's server-level cache, or a CDN like Cloudflare can all continue serving the old page after a redirect is added. Clear each layer, then retest with curl -I rather than a browser, since browsers also cache 301 responses aggressively.
It depends on whether anything relies on them. The .htaccess and Nginx examples above redirect the path but don't automatically preserve query strings; if /old-page/?ref=email needs to become /new-page/?ref=email rather than just /new-page/, add the [QSA] flag to an Apache RewriteRule, or reference $args explicitly in the Nginx return directive.
Conclusion
A redirect is one of the smallest changes you can make to a WordPress site with outsized consequences if skipped: broken links, lost search rankings, and visitors hitting dead ends instead of the content they were looking for. For most sites, the Redirection plugin covers everything you need, including the 404 log that tells you exactly which old URLs are worth fixing. Reach for .htaccess or Nginx config when you want the redirect to happen before WordPress loads at all, and reach for code when the redirect needs to depend on logic your theme already has access to.
Whichever method you use, always verify the result with curl -I rather than trusting what a browser shows you, since that's the only way to be certain you're seeing a real 301, not a cached response from a previous attempt.
Here are a few additional resources if you want to go deeper:
- Redirection Plugin Documentation — the official guide covering groups, regex matching, and CSV import/export.
- WordPress Developer Reference: wp_redirect() — the function reference used in the code examples above.
- Google Search Central: 301 Moved Permanently — how Google specifically handles 301 redirects for indexing and ranking.


