Full URL in PHP: How to Get It Quickly and Without Errors

Online Python Trainer for Beginners

Learn Python easily without overwhelming theory. Solve practical tasks with automatic checking, get hints in Russian, and write code directly in your browser — no installation required.

Start Course

How to Get the Full URL in PHP Without Losing Your Mind?

\n\n

Every PHP developer has faced the task at least once: "How do I get the full URL of the current page?" It seems simple enough — just take $_SERVER['HTTP_HOST'], add $_SERVER['REQUEST_URI'] — and you're done. But reality, as always, throws in its own twists. HTTP or HTTPS? What about a non-standard port? What if the site is behind a proxy? What if you need not just to get it, but to do it quickly, without memory leaks, and with future-proofing?

\n\n

The question "Get the full URL in PHP" on Stack Overflow has thousands of views and dozens of answers. This is no coincidence: the topic seems simple, but it's full of hidden pitfalls. Today we'll break down not just "how to do it", but how to do it correctly, quickly, and reliably. Let's go!

\n\n

Why is simple copying from $_SERVER a bad idea?

\n\n

Beginner developers often write this:

\n\n
$url = 'http://' . $_SERVER['HTTP_HOST'] . $_SERVER['REQUEST_URI'];
\n\n

At first glance, it works. But let's look at the problems:

\n
    \n
  • No HTTPS. If the site runs on HTTPS, you'll get http:// — and the browser will complain about mixed content.
  • \n
  • Port. If the port is non-standard (e.g., 8080), it will be lost if you don't use $_SERVER['SERVER_PORT'].
  • \n
  • Proxies and load balancers. Behind a reverse proxy (Nginx, Cloudflare), $_SERVER['HTTP_HOST'] may not be what the user sees.
  • \n
  • Security. The HTTP_HOST value can be manipulated by an attacker (Host header injection).
  • \n
\n\n

In short, copy-pasting from the first Stack Overflow answer is not the best option. Let's write a correct and performant function.

\n\n

The Reference Function: Getting the Full URL Correctly

\n\n

Here is a reliable function that handles all the main scenarios:

\n\n
function getFullUrl(): string {\n    $protocol = 'http';\n    if (\n        (!empty($_SERVER['HTTPS']) && $_SERVER['HTTPS'] !== 'off')\n        || (int)$_SERVER['SERVER_PORT'] === 443\n    ) {\n        $protocol = 'https';\n    }\n\n    // Consider headers from proxy (if trusted)\n    $host = $_SERVER['HTTP_HOST'] ?? '';\n    if (empty($host) && !empty($_SERVER['SERVER_NAME'])) {\n        $host = $_SERVER['SERVER_NAME'];\n    }\n\n    // Port check\n    $port = (int)$_SERVER['SERVER_PORT'];\n    $portSuffix = '';\n    if (\n        ($protocol === 'http' && $port !== 80)\n        || ($protocol === 'https' && $port !== 443)\n    ) {\n        $portSuffix = ':' . $port;\n    }\n\n    $uri = $_SERVER['REQUEST_URI'] ?? '/';\n\n    return $protocol . '://' . $host . $portSuffix . $uri;\n}
\n\n

What's important here?

\n
    \n
  • We check HTTPS — the standard method, works in 99% of cases.
  • \n
  • We account for SERVER_PORT — if the site is on a non-standard port, we don't lose it.
  • \n
  • A fallback via SERVER_NAME — in case HTTP_HOST is empty.
  • \n
  • We don't use $_SERVER['SCRIPT_URI'] — it's not available everywhere.
  • \n
\n\n

Performance Optimization: When Every Millisecond Counts

\n\n

If you call this function on every page or in a loop, it's worth thinking about speed. Here are a few techniques:

\n\n

1. Caching the Result

\n

If the URL doesn't change within a single request (and it doesn't), cache it:

\n\n
function getFullUrlCached(): string {\n    static $url = null;\n    if ($url === null) {\n        $url = getFullUrl(); // use our function above\n    }\n    return $url;\n}
\n\n

A static variable retains the value after the first call — no repeated calculations.

\n\n

2. Avoid Unnecessary Operations

\n

Don't use filt

Blogs

Book Recommendations