October DealsAmazon USOctober deal check: compare before you payAmazon US: current deals, useful picks and tech finds.Check DealsClean PCRecommendedOne scan can reveal what keeps slowing WindowsLook for cleanup and repair opportunities.Run ScanOctober DealsAmazon USDeal season is back - check today's better picksAmazon US: current deals, useful picks and tech finds.See Picks×
Skip to content
VGSources
Blog

How to Fix an Nginx Location Block That Isn’t Redirecting

A practical, detailed guide to diagnosing Nginx redirects: location precedence, exact and regex matches, return versus rewrite flags, try_files side effects, logs, curl tests, and safe reloads.
Length11 min Posted Quest giverVGSources Team
Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.

If an Nginx location block is not redirecting, first prove which server and location handled the request, then replace ambiguous rewrite logic with an explicit return. Nginx selects locations by a strict precedence algorithm; an exact match, a longer prefix, a ^~ prefix, or a regular expression can prevent the block you edited from running. A try_files, error_page, proxy, or upstream application can also perform a later internal or external redirect.

The dependable workflow is: inspect the loaded configuration with nginx -T, compare the real URI with every competing location, use return 301 (or a temporary status while testing) for a client-visible redirect, validate with nginx -t, reload the correct Nginx instance, and observe one request with curl and the access and error logs.

As an Amazon Associate I earn from qualifying purchases.

What’s actually slowing this PC down?

Pick the symptom - the matching free tool is one click away.

Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.

What Nginx is actually doing when a location does not redirect

A location block is not selected because it appears first in the file or because its text looks most specific. Nginx first chooses the appropriate server block for the connection, host, and port. It then tests the request URI against the locations in that server. The query string is not part of location matching, so /old?ref=mail is matched as /old.

NGINX documentation describes the process this way: it tests request URIs against the parameters of all location directives and applies the directives in the matching location. Understanding that process usually explains an apparently ignored redirect.

Location precedence

Syntax What it matches Effect on selection
location = /path Only the exact URI /path Wins immediately; Nginx does not continue searching.
location /path/ A prefix beginning with /path/ The longest matching prefix is retained as the current candidate.
location ^~ /path/ A prefix beginning with /path/ If this is the longest prefix, regular-expression locations are not tested against the request.
location ~ pattern or location ~* pattern A case-sensitive or case-insensitive regular expression After the prefix phase, the first matching regex in configuration order can take over, unless the retained prefix used ^~.

For example, location /old can be overtaken by a regex such as location ~ .php$ for /old/index.php. Conversely, location ^~ /old/ keeps that request in the prefix location and prevents the regex from overriding it. An exact block such as location = /old is decisive for that one URI, but it does not match /old/ or /old/index.php.

Start with the active configuration, not the file you edited

Multiple configuration files, include directories, containers, packages, or service instances can make an apparently correct edit ineffective. Inspect the complete expanded configuration from the same Nginx installation that will be reloaded.

Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.
  1. Identify the binary and compiled paths. Run nginx -V with the privileges required on your system. Its output exposes the configure arguments, including compiled-in paths that can differ from the file you expected.
  2. Dump the loaded configuration. Run sudo nginx -T. Search the output for the intended server_name, its listen directives, every include, and all locations that could match the URI. The dump is more authoritative than an unreferenced file on disk.
  3. Confirm the selected virtual server. Check the request’s host and port against server_name and listen. A request sent to an IP address, an alternate port, or a different hostname can reach the default server instead of the block you changed.
  4. Check that the request reaches this Nginx instance. In environments with a load balancer, reverse proxy, container, or multiple hosts, verify that DNS and the destination address point to the process whose configuration you inspected.

If the intended location is absent from nginx -T, fix the include path or edit the configuration actually loaded. Do not proceed by repeatedly reloading a different instance.

Compare the real URI with the location patterns

Write down the exact request path, including its leading slash, trailing slash, percent encoding, and case. Then compare it with each candidate location. These small differences are common causes of a missed match:

  • /old and /old/ are different for an exact match.
  • A case-sensitive regex does not match a different case; ~* makes the regex case-insensitive.
  • /old/file may match a prefix block even when you intended only the single path /old.
  • The query string, such as ?next=/new, does not influence location selection.
  • Percent-encoded characters and normalized paths can make what the client displays differ from the URI Nginx evaluates.

Use an exact location when one URL must redirect and a prefix location when an entire subtree must redirect. Add a trailing-slash rule deliberately rather than assuming a prefix will cover both forms.

Use return for a straightforward client redirect

For a redirect visible to the browser or API client, return is the clearest directive. NGINX documentation calls it the easiest way to issue this kind of response. It can be placed in server or location context.

Free tools Windows power users keep installed

One-click scans. No signup required.

Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.

Exact-path example

server {
    listen 80;
    server_name example.com;

    location = /old {
        return 301 https://example.com/new;
    }
}

A request for http://example.com/old receives a 301 response with a Location: https://example.com/new header. The browser then makes a second request to the destination. The exact block does not redirect /old/; add a separate exact rule or choose an intentional prefix rule if both URLs should move.

Redirecting a subtree

location ^~ /legacy/ {
    return 301 https://example.com/current$request_uri;
}

Here $request_uri preserves the original path and query string. Use variables only when you have verified the resulting destination; an accidental variable can create malformed URLs or reflect an untrusted host. If the old and new paths have different structures, write the destination explicitly instead of blindly appending the old URI.

Place a server-wide redirect at server context when appropriate

server {
    listen 80;
    server_name example.com;
    return 301 https://example.com$request_uri;
}

This pattern redirects every request handled by that HTTP server to HTTPS before any location-specific content processing. Do not put it in the TLS server as well unless you intentionally want another redirect; a duplicate rule can create a loop or obscure which block responded.

Choose the right status code while testing and deploying

Status Use Important behavior
301 Permanent move after the destination is confirmed Browsers and caches may retain it, making later tests appear to use an old result.
302 Temporary redirect during a short-term change or test Clients generally recheck the original URL more readily than with a 301.
307 Temporary redirect when the HTTP method and request body must be preserved Useful for method-sensitive APIs; test the client behavior explicitly.

A 301 is not a better debugging status simply because it is common. Use a temporary response while proving the match, then change it to a permanent status only when the move is final and caches should be updated.

Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.

Use rewrite only when you need conditional or captured logic

rewrite evaluates a regular expression and can construct a new URI from captures. It is useful for many source paths, conditional transformations, or rules that need flags, but it has more moving parts than return.

External rewrite

location /old/ {
    rewrite ^/old/(.*)$ https://example.com/new/$1 redirect;
}

The redirect flag produces a temporary client redirect. A permanent external rewrite can use permanent, which sends a 301. For a fixed destination, an explicit return remains easier to audit.

Internal rewrite and the last flag

location /legacy/ {
    rewrite ^/legacy/(.*)$ /current/$1 last;
}

location /current/ {
    # Content handling for the rewritten URI
}

last stops the current rewrite set and starts a new location search using the rewritten URI. That is intentional when another location must process /current/, but it also means the request can enter a different block than the one where the rule appears.

The break flag

location /legacy/ {
    rewrite ^/legacy/(.*)$ /current/$1 break;
    # Continue processing in this same location
}

break stops the current rewrite directives without performing a new location lookup. Use it when the current location should continue handling the changed URI. Choosing last when you meant break, or the reverse, is a frequent reason that a redirect appears to be ignored or that unexpected content is served.

Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.

Prevent rewrite cycles

Never rewrite a URI into a path that re-enters the same rule without a terminating condition. For example, a rule that changes /old to another URI still matched by the same expression can repeatedly trigger internal redirects. Check both the source and destination against every regex and prefix location. If Nginx reports too many internal redirects, remove the cycle, use a more precise pattern, or replace the rule with a direct return.

Check directives that can run after location selection

Finding the expected location does not prove that its response is the final response. Several directives and upstream components can change the request flow.

try_files can internally redirect

location / {
    try_files $uri $uri/ /index.php?$query_string;
}

location = /old {
    return 301 https://example.com/new;
}

try_files checks files and directories and can internally redirect to its final argument. If the request is handled by a broad location containing try_files, it may end up at an application entry point instead of producing the redirect you expected. Put a precise redirect location ahead of the broad handling logic, and verify that the actual URI still matches it.

index and slash normalization

A directory request can cause an internal redirect to an index URI, and Nginx may redirect a directory-like path to a trailing-slash form in some configurations. Decide whether /game, /game/, or both should redirect, then test each separately.

Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.

error_page and proxy responses

An error_page can route an error to another URI. A proxied server can return its own 3xx response, and an upstream application can emit a Location header even when Nginx itself did not issue the redirect. Inspect the response status and headers with verbose client output and correlate them with the logs before changing the location rule.

Diagnose with a controlled request

  1. Test headers without following the redirect. Run curl -I http://example.com/old. Record the status and every Location header.
  2. See the complete exchange. Run curl -v http://example.com/old. Confirm the host, scheme, destination address, request path, status, and whether a second response is coming from an upstream.
  3. Test the exact variants. Repeat for /old/, a representative child path, different case where relevant, and a query string. This distinguishes an exact-match mistake from a broader routing issue.
  4. Prevent client-side follow-up from hiding the first response. Do not start with -L. If you later use curl -IL, inspect every hop, because a first redirect can be followed by a second redirect or a loop.
  5. Use the intended scheme and port. Test HTTP and HTTPS separately when both servers exist. Include a non-default port in the URL when the listener requires it.
Independent reader supportYour contribution helps us test, update, and keep practical guides available for everyone.Support on Ko-Fi

Read access and error logs while making one request

Tail the configured access and error logs, issue one controlled request, and match its timestamp. The access log shows which request produced the status; the error log often explains rewrite processing, file checks, upstream behavior, or redirect loops.

The error_log directive sets up the error log. An error_log inside a server or location overrides inherited logging settings, so inspect the effective scope in nginx -T instead of assuming all messages go to one global file.

If normal logs are insufficient and the build supports it, temporarily raise the error_log level or enable debug logging for a controlled client address. Reproduce one request, collect the evidence, and return the logging level to normal; verbose debug logs can be large and may expose request details.

Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.

Validate and reload the same Nginx instance

  1. After editing, run sudo nginx -t. Do not reload if syntax or referenced-file validation fails.
  2. Use the configuration path and binary identified by nginx -V if several installations exist.
  3. Reload that instance using the service mechanism for your system, then confirm the worker processes received the new configuration.
  4. Run the same curl request again and compare the status, Location, host, scheme, and trailing slash with the previous result.

A successful syntax test means the configuration parses; it does not prove that the intended server handles the request or that the selected location is the one you expected. Keep the log and header check in the loop after every reload.

Common symptoms and targeted fixes

Symptom Likely cause What to check
The old page is served with 200 A different location or server won, or a broad handler such as try_files processed it. nginx -T, host/port, exact URI, and access logs.
A redirect occurs for one spelling but not another Exact matching, case sensitivity, or trailing-slash differences. Test each URI variant and adjust exact, prefix, or regex syntax.
Your regex never runs A longer ^~ prefix prevented regex evaluation. Compare all prefixes and remove or narrow ^~ only if regex handling is required.
The response has an unexpected Location header A proxy or upstream application issued it, or an error_page changed the flow. Verbose headers, upstream logs, proxy settings, and error-page directives.
Nginx reports an internal redirect cycle rewrite ... last, try_files, or an error-page target re-enters the same rule. Map source and destination URIs and add a terminating condition or use break where appropriate.
Changes have no effect The edited file is not included or a different Nginx process was reloaded. nginx -T, nginx -V, process/service identity, and reload output.
Only cached clients show the old behavior A previous 301 was cached. Use a temporary status during testing and inspect the first response with curl.

A repeatable configuration pattern

For a single legacy URL, keep the rule isolated and exact:

server {
    listen 80;
    server_name example.com;

    location = /old {
        return 302 https://example.com/new;
    }

    location / {
        try_files $uri $uri/ /index.php?$query_string;
    }
}

Use the 302 while verifying the destination and client behavior. Once the move is permanent, change only the status to 301 after testing both the source URL and any variants that should or should not match. For a subtree, replace the exact location with a deliberately scoped prefix and document whether a regex location is allowed to override it.

Production checklist

  • The request reaches the intended server_name and listen socket.
  • nginx -T contains the edited location and shows all competing locations and includes.
  • The location syntax matches the actual path, case, and trailing-slash policy.
  • An exact match is used for one URL; a prefix or regex is used only when its broader scope is intended.
  • ^~ is present only when regex locations must not override the prefix.
  • A fixed client-visible move uses return; rewrite is reserved for conditional or captured transformations.
  • last and break are chosen according to whether a new location search is required.
  • try_files, index, error_page, proxy behavior, and upstream redirects have been checked.
  • nginx -t succeeds before reload, and the same instance identified by nginx -V is reloaded.
  • curl -I or curl -v confirms the first status and Location header without hiding it behind automatic follow-up requests.
  • Access and error logs are correlated with one test request, with temporary debug logging removed afterward.

Following those checks turns an “ignored location” into a traceable routing decision: identify the winning server and location, make the response explicit, account for internal rematching, and verify the final headers from the running process.

Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.

Product prices and availability are accurate as of the date/time indicated and are subject to change. Any price and availability information displayed on Amazon at the time of purchase will apply.

Leave a Reply

Your email address will not be published. Required fields are marked *

Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.

More quests from Patch Notes

  1. How to Set Up a RedM (RDR2) Server in 2026: License Key, txAdmin and server.cfg, Step by StepBlog11min
  2. Best RedM (RDR2) Server Hosting in 2026: Comparing Four Hosts on Slots, Memory and PriceBlog10min
  3. How to Host a Mindustry Server in 2026: server-release.jar, Port 6567 and the Commands That MatterBlog7min
Recommended PC Tool
Recommended PC Tool
Windows Errors? Fix Them Before They SpreadFree repair scan
Crashes, No Sound, or Screen Glitches?Free driver scan

Two free Windows tools

One Free Minute Could Fix That PC

Before you go - each of these free tools takes about a minute and tackles what quietly slows a Windows PC down.

Special offer. View Outbyte info, uninstall instructions, EULA, and Privacy Policy.