预定义变量
在线手册:中文 英文
PHP手册

$_SERVER

$HTTP_SERVER_VARS [已弃用]

$_SERVER -- $HTTP_SERVER_VARS [已弃用]服务器和执行环境信息

说明

$_SERVER 是一个包含了诸如头信息(header)、路径(path)、以及脚本位置(script locations)等等信息的数组。这个数组中的项目由 Web 服务器创建。不能保证每个服务器都提供全部项目;服务器可能会忽略一些,或者提供一些没有在这里列举出来的项目。这也就意味着大量的此类变量都会在» CGI 1.1 规范中说明,所以应该仔细研究一下。

$HTTP_SERVER_VARS 包含着相同的信息,但它不是一个超全局变量。 (注意 $HTTP_SERVER_VARS$_SERVER 是不同的变量,PHP处理它们的方式不同)

目录

$_SERVER 中,你也许能够,也许不能够找到下面的这些元素。注意,如果以命令行方式运行 PHP,下面列出的元素几乎没有有效的(或是没有任何实际意义的)。

'PHP_SELF'
当前执行脚本的文件名,与 document root 有关。例如,在地址为 http://example.com/test.php/foo.bar 的脚本中使用 $_SERVER['PHP_SELF'] 将得到 /test.php/foo.bar__FILE__ 常量包含当前(例如包含)文件的完整路径和文件名。 从 PHP 4.3.0 版本开始,如果 PHP 以命令行模式运行,这个变量将包含脚本名。之前的版本该变量不可用。
'argv'
传递给该脚本的参数的数组。当脚本以命令行方式运行时,argv 变量传递给程序 C 语言样式的命令行参数。当通过 GET 方式调用时,该变量包含query string。
'argc'
包含命令行模式下传递给该脚本的参数的数目(如果运行在命令行模式下)。
'GATEWAY_INTERFACE'
服务器使用的 CGI 规范的版本;例如,“CGI/1.1”。
'SERVER_ADDR'
当前运行脚本所在的服务器的 IP 地址。
'SERVER_NAME'
当前运行脚本所在的服务器的主机名。如果脚本运行于虚拟主机中,该名称是由那个虚拟主机所设置的值决定。
'SERVER_SOFTWARE'
服务器标识字符串,在响应请求时的头信息中给出。
'SERVER_PROTOCOL'
请求页面时通信协议的名称和版本。例如,“HTTP/1.0”。
'REQUEST_METHOD'
访问页面使用的请求方法;例如,“GET”, “HEAD”,“POST”,“PUT”。

Note:

如果请求方法为 HEAD,PHP 脚本将在发送 Header 头信息之后终止(这意味着在产生任何输出后,不再有输出缓冲)。

'REQUEST_TIME'
请求开始时的时间戳。从 PHP 5.1.0 起可用。
'QUERY_STRING'
query string(查询字符串),如果有的话,通过它进行页面访问。
'DOCUMENT_ROOT'
当前运行脚本所在的文档根目录。在服务器配置文件中定义。
'HTTP_ACCEPT'
当前请求头中 Accept: 项的内容,如果存在的话。
'HTTP_ACCEPT_CHARSET'
当前请求头中 Accept-Charset: 项的内容,如果存在的话。例如:“iso-8859-1,*,utf-8”。
'HTTP_ACCEPT_ENCODING'
当前请求头中 Accept-Encoding: 项的内容,如果存在的话。例如:“gzip”。
'HTTP_ACCEPT_LANGUAGE'
当前请求头中 Accept-Language: 项的内容,如果存在的话。例如:“en”。
'HTTP_CONNECTION'
当前请求头中 Connection: 项的内容,如果存在的话。例如:“Keep-Alive”。
'HTTP_HOST'
当前请求头中 Host: 项的内容,如果存在的话。
'HTTP_REFERER'
引导用户代理到当前页的前一页的地址(如果存在)。由 user agent 设置决定。并不是所有的用户代理都会设置该项,有的还提供了修改 HTTP_REFERER 的功能。简言之,该值并不可信。
'HTTP_USER_AGENT'
当前请求头中 User-Agent: 项的内容,如果存在的话。该字符串表明了访问该页面的用户代理的信息。一个典型的例子是:Mozilla/4.5 [en] (X11; U; Linux 2.2.9 i586)。除此之外,你可以通过 get_browser() 来使用该值,从而定制页面输出以便适应用户代理的性能。
'HTTPS'
如果脚本是通过 HTTPS 协议被访问,则被设为一个非空的值。

Note: 注意当使用 IIS 上的 ISAPI 方式时,如果不是通过 HTTPS 协议被访问,这个值将为 off

'REMOTE_ADDR'
浏览当前页面的用户的 IP 地址。
'REMOTE_HOST'
浏览当前页面的用户的主机名。DNS 反向解析不依赖于用户的 REMOTE_ADDR

Note: 你的服务器必须被配置以便产生这个变量。例如在 Apache 中,你需要在 httpd.conf 中设置 HostnameLookups On 来产生它。参见 gethostbyaddr()

'REMOTE_PORT'
用户机器上连接到 Web 服务器所使用的端口号。
'SCRIPT_FILENAME'

当前执行脚本的绝对路径。

Note:

如果在命令行界面(Command Line Interface, CLI)使用相对路径执行脚本,例如 file.php../file.php,那么 $_SERVER['SCRIPT_FILENAME'] 将包含用户指定的相对路径。

'SERVER_ADMIN'
该值指明了 Apache 服务器配置文件中的 SERVER_ADMIN 参数。如果脚本运行在一个虚拟主机上,则该值是那个虚拟主机的值。
'SERVER_PORT'
Web 服务器使用的端口。默认值为 “80”。如果使用 SSL 安全连接,则这个值为用户设置的 HTTP 端口。
'SERVER_SIGNATURE'
包含了服务器版本和虚拟主机名的字符串。
'PATH_TRANSLATED'
当前脚本所在文件系统(非文档根目录)的基本路径。这是在服务器进行虚拟到真实路径的映像后的结果。

Note: 自 PHP 4.3.2 起,PATH_TRANSLATED 在 Apache 2 SAPI 模式下不再和 Apache 1 一样隐含赋值,而是若 Apache 不生成此值,PHP 便自己生成并将其值放入 SCRIPT_FILENAME 服务器常量中。这个修改遵守了 CGI 规范,PATH_TRANSLATED 仅在 PATH_INFO 被定义的条件下才存在。 Apache 2 用户可以在 httpd.conf 中设置 AcceptPathInfo = On 来定义 PATH_INFO

'SCRIPT_NAME'
包含当前脚本的路径。这在页面需要指向自己时非常有用。__FILE__ 常量包含当前脚本(例如包含文件)的完整路径和文件名。
'REQUEST_URI'
URI 用来指定要访问的页面。例如 “/index.html”。
'PHP_AUTH_DIGEST'
当作为 Apache 模块运行时,进行 HTTP Digest 认证的过程中,此变量被设置成客户端发送的“Authorization” HTTP 头内容(以便作进一步的认证操作)。
'PHP_AUTH_USER'
当 PHP 运行在 Apache 或 IIS(PHP 5 是 ISAPI)模块方式下,并且正在使用 HTTP 认证功能,这个变量便是用户输入的用户名。
'PHP_AUTH_PW'
当 PHP 运行在 Apache 或 IIS(PHP 5 是 ISAPI)模块方式下,并且正在使用 HTTP 认证功能,这个变量便是用户输入的密码。
'AUTH_TYPE'
当 PHP 运行在 Apache 模块方式下,并且正在使用 HTTP 认证功能,这个变量便是认证的类型。
'PATH_INFO'
包含由客户端提供的、跟在真实脚本名称之后并且在查询语句(query string)之前的路径信息,如果存在的话。例如,如果当前脚本是通过 URL http://www.example.com/php/path_info.php/some/stuff?foo=bar 被访问,那么 $_SERVER['PATH_INFO'] 将包含 /some/stuff
'ORIG_PATH_INFO'
在被 PHP 处理之前,“PATH_INFO” 的原始版本。

更新日志

版本 说明
4.1.0 引入 $_SERVER,弃用 $HTTP_SERVER_VARS

范例

Example #1 $_SERVER 范例

<?php
echo $_SERVER['SERVER_NAME'];
?>

以上例程的输出类似于:

www.example.com

注释

Note:

“Superglobal”也称为自动化的全局变量。 这就表示其在脚本的所有作用域中都是可用的。不需要在函数或方法中用 global $variable; 来访问它。

参见


预定义变量
在线手册:中文 英文
PHP手册
PHP手册 - N: 服务器和执行环境信息

用户评论:

LOL (05-Apr-2012 09:26)

For an hosting that use windows I have used this script to make REQUEST_URI to be correctly setted on IIS
<?php
function request_URI() {
    if(!isset(
$_SERVER['REQUEST_URI'])) {
       
$_SERVER['REQUEST_URI'] = $_SERVER['SCRIPT_NAME'];
        if(
$_SERVER['QUERY_STRING']) {
           
$_SERVER['REQUEST_URI'] .= '?' . $_SERVER['QUERY_STRING'];
        }
    }
    return
$_SERVER['REQUEST_URI'];
}
$_SERVER['REQUEST_URI'] = request_URI();
?>

Anonymous (13-Feb-2012 07:54)

concerning my former note. the function is not right, please use the following instead:

$DocumentRoot = str_replace ("//", "/", $_SERVER['DOCUMENT_ROOT']."/");

mdlamar at gmail dot com (12-Dec-2011 11:04)

$_SERVER['SERVER_ADDR'] contains my LAN IP rather than the public IP. I used the function gethostbyname() to get my public IP rather than the router assigned local IP.

picov at e-link dot it (13-Oct-2011 06:59)

A simple function to detect if the current page address was rewritten by mod_rewrite:

<?php
public function urlWasRewritten() {
 
$realScriptName=$_SERVER['SCRIPT_NAME'];
 
$virtualScriptName=reset(explode("?", $_SERVER['REQUEST_URI']));
  return !(
$realScriptName==$virtualScriptName);
}
?>

MarkAgius at markagius dot co dot uk (31-Aug-2011 10:18)

You have missed 'REDIRECT_STATUS'

Very useful if you point all your error pages to the same file.

File; .htaccess
# .htaccess file.

ErrorDocument 404 /error-msg.php
ErrorDocument 500 /error-msg.php
ErrorDocument 400 /error-msg.php
ErrorDocument 401 /error-msg.php
ErrorDocument 403 /error-msg.php
# End of file.

File; error-msg.php
<?php
  $HttpStatus
= $_SERVER["REDIRECT_STATUS"] ;
  if(
$HttpStatus==200) {print "Document has been processed and sent to you.";}
  if(
$HttpStatus==400) {print "Bad HTTP request ";}
  if(
$HttpStatus==401) {print "Unauthorized - Iinvalid password";}
  if(
$HttpStatus==403) {print "Forbidden";}
  if(
$HttpStatus==500) {print "Internal Server Error";}
  if(
$HttpStatus==418) {print "I'm a teapot! - This is a real value, defined in 1998";}

?>

Jamie (02-Mar-2011 09:18)

Note that on real paths, aliases are not resolved

$_SERVER["DOCUMENT_ROOT"] => /var/services/web/mysite
$_SERVER["SCRIPT_FILENAME"] => /var/services/web/mysite/admin/products.php

(but __FILE__ => /volume1/web/mysite/admin/inc/includeFile.inc.php)
Use realpath to resolve the $_SERVER value.

Virtual paths also have some differences:
$_SERVER["SCRIPT_NAME"] => /admin/products.php (virtual path)
$_SERVER["PHP_SELF"] => /admin/products.php/someExtraStuff (virtual path)

SCRIPT_NAME is defined in the CGI 1.1 specification, PHP_SELF is created by PHP itself. See http://php.about.com/od/learnphp/qt/_SERVER_PHP.htm for tests.

sainthyoga2003 at gmail dot com (25-Feb-2011 08:37)

$_SERVER["SCRIPT_FILENAME"] returns the path including the filename, like __DIR__

Josh Fremer (20-Dec-2010 06:47)

HTTPS

Set to a non-empty value if the script was queried through the HTTPS protocol.

Note: Note that when using ISAPI with IIS, the value will be off if the request was not made through the HTTPS protocol.

=-=-=

To clarify this, the value is the string "off", so a specific non-empty value rather than an empty value as in Apache.

rulerof at gmail dot com (17-Nov-2010 06:12)

I needed to get the full base directory of my script local to my webserver, IIS 7 on Windows 2008.

I ended up using this:

<?php
function GetBasePath() {
    return
substr($_SERVER['SCRIPT_FILENAME'], 0, strlen($_SERVER['SCRIPT_FILENAME']) - strlen(strrchr($_SERVER['SCRIPT_FILENAME'], "\\")));
}
?>

And it returned C:\inetpub\wwwroot\<applicationfolder> as I had hoped.

Stefano (info at sarchittu dot org) (12-Nov-2010 02:07)

A way to get the absolute path of your page, independent from the site position (so works both on local machine and on server without setting anything) and from the server OS (works both on Unix systems and Windows systems).

The only parameter it requires is the folder in which you place this script
So, for istance, I'll place this into my SCRIPT folder, and I'll write SCRIPT word length in $conflen

<?php
$conflen
=strlen('SCRIPT');
$B=substr(__FILE__,0,strrpos(__FILE__,'/'));
$A=substr($_SERVER['DOCUMENT_ROOT'], strrpos($_SERVER['DOCUMENT_ROOT'], $_SERVER['PHP_SELF']));
$C=substr($B,strlen($A));
$posconf=strlen($C)-$conflen-1;
$D=substr($C,1,$posconf);
$host='http://'.$_SERVER['SERVER_NAME'].'/'.$D;
?>

$host will finally contain the absolute path.

Anonymous (12-Nov-2010 12:22)

Use Strict-Transport-Security (STS) to force the use of SSL.
<?php
$use_sts
= TRUE;

if (
$use_sts && isset($_SERVER['HTTPS']) {
 
header('Strict-Transport-Security: max-age=500');
} elseif (
$use_sts && !isset($_SERVER['HTTPS']) {
 
header('Status-Code: 301');
 
header('Location: https://'.$_SERVER["HTTP_HOST"].$_SERVER['REQUEST_URI']);
}
?>

dtomasiewicz at gmail dot com (15-Aug-2010 04:03)

To get an associative array of HTTP request headers formatted similarly to get_headers(), this will do the trick:

<?php
/**
 * Transforms $_SERVER HTTP headers into a nice associative array. For example:
 *   array(
 *       'Referer' => 'example.com',
 *       'X-Requested-With' => 'XMLHttpRequest'
 *   )
 */
function get_request_headers() {
   
$headers = array();
    foreach(
$_SERVER as $key => $value) {
        if(
strpos($key, 'HTTP_') === 0) {
           
$headers[str_replace(' ', '-', ucwords(str_replace('_', ' ', strtolower(substr($key, 5)))))] = $value;
        }
    }
    return
$headers;
}
?>

wbeaumo1 at gmail dot com (14-Jun-2010 04:43)

Don't forget $_SERVER['HTTP_COOKIE']. It contains the raw value of the 'Cookie' header sent by the user agent.

kamazee at gmail dot com (15-Apr-2010 02:41)

$_SERVER['DOCUMENT_ROOT'] in different environments may has trailing slash or not, so be careful when including files from $_SERVER['DOCUMENT_ROOT']:
<?php
include(dirname($_SERVER['DOCUMENT_ROOT']) . DIRECTORY_SEPARATOR . 'file.php')
?>

php at isnoop dot net (01-Apr-2010 05:38)

Use the apache SetEnv directive to set arbitrary $_SERVER variables in your vhost or apache config.

SetEnv varname "variable value"

piana at pyrohawk dot com (18-Mar-2010 05:26)

There are two different variables that I find very useful in Caching and similar.

$_SERVER['REQUEST_URI'] and $_SERVER['REQUEST_URL']

URI provides the entire request path (/directory/file.ext?query=string)
URL provides the request path, without the query string (/directory/file.ext)
It also differs from __FILE__ in that it's not the file name.  So, if you go to /directory/anotherfile.ext and get silently redirected to file.ext, these variables are anotherfile.ext, while __FILE__ is still file.ext.

Megan Mickelson (22-Feb-2010 11:36)

It makes sense to want to paste the $_SERVER['REQUEST_URI'] on to a page (like on a footer), but be sure to clean it up first with htmlspecialchars() otherwise it poses a cross-site scripting vulnerability.

htmlspecialchars($_SERVER['REQUEST_URI']);

e.g.
http://www.example.com/foo?<script>...

becomes
http://www.example.com/foo?&lt;script&gt;...

admin at NOSpAM dot sinfocol dot org (15-Jan-2010 06:31)

I was testing with the $_SERVER variable and some request method, and I found that with apache I can put an arbitrary method.

For example, I have an script called "server.php" in my example webpage with the next code:

<?php
echo $_SERVER['REQUEST_METHOD'];
?>

And I made this request:
c:\>nc -vv www.example.com 80
example.com [x.x.x.x] 80 (http) open
ArbitratyMethod /server.php HTTP/1.1
Host: wow.sinfocol.org
Connection: Close

The response of the server is the next:
HTTP/1.1 200 OK
Date: Fri, 15 Jan 2010 05:14:09 GMT
Server: Apache
Connection: close
Transfer-Encoding: chunked
Content-Type: text/html

ArbitratyMethod

So, be carefully when include the $_SERVER['REQUEST_METHOD'] in any script, this kind of "bug" is old and could be dangerous.

mirko dot steiner at slashdevslashnull dot de (24-Oct-2009 10:43)

<?php

// RFC 2616 compatible Accept Language Parser
// http://www.ietf.org/rfc/rfc2616.txt, 14.4 Accept-Language, Page 104
// Hypertext Transfer Protocol -- HTTP/1.1

foreach (explode(',', $_SERVER['HTTP_ACCEPT_LANGUAGE']) as $lang) {
   
$pattern = '/^(?P<primarytag>[a-zA-Z]{2,8})'.
   
'(?:-(?P<subtag>[a-zA-Z]{2,8}))?(?:(?:;q=)'.
   
'(?P<quantifier>\d\.\d))?$/';

   
$splits = array();

   
printf("Lang:,,%s''\n", $lang);
    if (
preg_match($pattern, $lang, $splits)) {
       
print_r($splits);
    } else {
        echo
"\nno match\n";
    }
}

?>

example output:

Google Chrome 3.0.195.27 Windows xp

Lang:,,de-DE''
Array
(
    [0] => de-DE
    [primarytag] => de
    [1] => de
    [subtag] => DE
    [2] => DE
)
Lang:,,de;q=0.8''
Array
(
    [0] => de;q=0.8
    [primarytag] => de
    [1] => de
    [subtag] =>
    [2] =>
    [quantifier] => 0.8
    [3] => 0.8
)
Lang:,,en-US;q=0.6''
Array
(
    [0] => en-US;q=0.6
    [primarytag] => en
    [1] => en
    [subtag] => US
    [2] => US
    [quantifier] => 0.6
    [3] => 0.6
)
Lang:,,en;q=0.4''
Array
(
    [0] => en;q=0.4
    [primarytag] => en
    [1] => en
    [subtag] =>
    [2] =>
    [quantifier] => 0.4
    [3] => 0.4
)

Lord Mac (15-Oct-2009 03:56)

An even *more* improved version...

<?php
phpinfo
(32);
?>

steve at sc-fa dot com (17-Sep-2009 08:20)

If you are serving from behind a proxy server, you will almost certainly save time by looking at what these $_SERVER variables do on your machine behind the proxy.  

$_SERVER['HTTP_X_FORWARDED_FOR'] in place of $_SERVER['REMOTE_ADDR']

$_SERVER['HTTP_X_FORWARDED_HOST'] and
$_SERVER['HTTP_X_FORWARDED_SERVER'] in place of (at least in our case,) $_SERVER['SERVER_NAME']

cupy at email dot cz (20-Aug-2009 04:24)

Tech note:
$_SERVER['argc'] and $_SERVER['argv'][] has some funny behaviour,
used from linux (bash) commandline, when called like
"php ./script_name.php 0x020B"
there is everything correct, but
"./script_name.php 0x020B"
is not correct - "0" is passed instead of "0x020B" as $_SERVER['argv'][1] - see the script below.
Looks like the parameter is not passed well from bash to PHP.
(but, inspected on the level of bash, 0x020B is understood well as $1)

try this example:

------------->8------------------
cat ./script_name.php
#! /usr/bin/php

if( $_SERVER['argc'] == 2)
  {
    // funny... we have to do this trick to pass e.g. 0x020B from parameters
    // ignore this: "PHP Notice:  Undefined offset:  2 in ..."
    $EID = $_SERVER['argv'][1] + $_SERVER['argv'][2] + $_SERVER['argv'][3];
  }
 else
   {        // default
     $EID = 0x0210; // PPS failure
   }

jarrod at squarecrow dot com (11-Aug-2009 04:31)

$_SERVER['DOCUMENT_ROOT'] is incredibly useful especially when working in your development environment. If you're working on large projects you'll likely be including a large number of files into your pages. For example:

<?php
//Defines constants to use for "include" URLS - helps keep our paths clean

       
define("REGISTRY_CLASSES"$_SERVER['DOCUMENT_ROOT']."/SOAP/classes/");
       
define("REGISTRY_CONTROLS", $_SERVER['DOCUMENT_ROOT']."/SOAP/controls/");

       
define("STRING_BUILDER",     REGISTRY_CLASSES. "stringbuilder.php");
       
define("SESSION_MANAGER",     REGISTRY_CLASSES. "sessionmanager.php");
       
define("STANDARD_CONTROLS",    REGISTRY_CONTROLS."standardcontrols.php");
?>

In development environments, you're rarely working with your root folder, especially if you're running PHP locally on your box and using DOCUMENT_ROOT is a great way to maintain URL conformity. This will save you hours of work preparing your application for deployment from your box to a production server (not to mention save you the headache of include path failures).

Richard York (09-Jul-2009 07:19)

Not documented here is the fact that $_SERVER is populated with some pretty useful information when accessing PHP via the shell.

 ["_SERVER"]=>
  array(24) {
    ["MANPATH"]=>
    string(48) "/usr/share/man:/usr/local/share/man:/usr/X11/man"
    ["TERM"]=>
    string(11) "xterm-color"
    ["SHELL"]=>
    string(9) "/bin/bash"
    ["SSH_CLIENT"]=>
    string(20) "127.0.0.1 41242 22"
    ["OLDPWD"]=>
    string(60) "/Library/WebServer/Domains/www.example.com/private"
    ["SSH_TTY"]=>
    string(12) "/dev/ttys000"
    ["USER"]=>
    string(5) "username"
    ["MAIL"]=>
    string(15) "/var/mail/username"
    ["PATH"]=>
    string(57) "/usr/bin:/bin:/usr/sbin:/sbin:/usr/local/bin:/usr/X11/bin"
    ["PWD"]=>
    string(56) "/Library/WebServer/Domains/www.example.com/www"
    ["SHLVL"]=>
    string(1) "1"
    ["HOME"]=>
    string(12) "/Users/username"
    ["LOGNAME"]=>
    string(5) "username"
    ["SSH_CONNECTION"]=>
    string(31) "127.0.0.1 41242 10.0.0.1 22"
    ["_"]=>
    string(12) "/usr/bin/php"
    ["__CF_USER_TEXT_ENCODING"]=>
    string(9) "0x1F5:0:0"
    ["PHP_SELF"]=>
    string(10) "Shell.php"
    ["SCRIPT_NAME"]=>
    string(10) "Shell.php"
    ["SCRIPT_FILENAME"]=>
    string(10) "Shell.php"
    ["PATH_TRANSLATED"]=>
    string(10) "Shell.php"
    ["DOCUMENT_ROOT"]=>
    string(0) ""
    ["REQUEST_TIME"]=>
    int(1247162183)
    ["argv"]=>
    array(1) {
      [0]=>
      string(10) "Shell.php"
    }
    ["argc"]=>
    int(1)
  }

chris (03-Jul-2009 12:01)

A table of everything in the $_SERVER array can be found near the bottom of the output of phpinfo();

pudding06 at gmail dot com (02-May-2009 10:44)

Here's a simple, quick but effective way to block unwanted external visitors to your local server:

<?php
// only local requests
if ($_SERVER['REMOTE_ADDR'] !== '127.0.0.1') die(header("Location: /"));
?>

This will direct all external traffic to your home page. Of course you could send a 404 or other custom error. Best practice is not to stay on the page with a custom error message as you acknowledge that the page does exist. That's why I redirect unwanted calls to (for example) phpmyadmin.

dragon[dot]dionysius[at]gmail[dot]com (29-Apr-2009 06:53)

I've updated the function of my previous poster and putted it into my class.

<?php
   
/**
     * Checking HTTP-Header for language
     * needed for various system classes
     *
     * @return    boolean    true/false
     */
   
private function _checkClientLanguage()
    {   
       
$langcode = (!empty($_SERVER['HTTP_ACCEPT_LANGUAGE'])) ? $_SERVER['HTTP_ACCEPT_LANGUAGE'] : '';
       
$langcode = (!empty($langcode)) ? explode(";", $langcode) : $langcode;
       
$langcode = (!empty($langcode['0'])) ? explode(",", $langcode['0']) : $langcode;
       
$langcode = (!empty($langcode['0'])) ? explode("-", $langcode['0']) : $langcode;
        return
$langcode['0'];
    }
?>

Please note, you have to check additional the result! Because the header may be missing or another possible thing, it is malformed. So check the result with a list with languages you support and perhaps you have to load a default language.

<?php

// if result isn't one of my defined languages
           
if(!in_array($lang, $language_list)) {
               
$lang = $language_default; // load default

?>

My HTTP_ACCEPT_LANGUAGE string:
FF3: de-de,de;q=0.8,en-us;q=0.5,en;q=0.3
IE7: de-ch

So, take care of it!

dalys at chokladboll dot se (15-Apr-2009 10:03)

If you want en, sv-SE, da, es etc. to be returned from $_SERVER['HTTP_ACCEPT_LANGUAGE'] you can use this function:

<?php
function detectlanguage() {
   
$langcode = explode(";", $_SERVER['HTTP_ACCEPT_LANGUAGE']);
   
$langcode = explode(",", $langcode['0']);
    return
$langcode['0'];
    }

$language = detectlanguage();

echo
"You have chosen $language as your language in your web browser.";
?>

Vladimir Kornea (14-Mar-2009 01:06)

1. All elements of the $_SERVER array whose keys begin with 'HTTP_' come from HTTP request headers and are not to be trusted.

2. All HTTP headers sent to the script are made available through the $_SERVER array, with names prefixed by 'HTTP_'.

3. $_SERVER['PHP_SELF'] is dangerous if misused. If login.php/nearly_arbitrary_string is requested, $_SERVER['PHP_SELF'] will contain not just login.php, but the entire login.php/nearly_arbitrary_string. If you've printed $_SERVER['PHP_SELF'] as the value of the action attribute of your form tag without performing HTML encoding, an attacker can perform XSS attacks by offering users a link to your site such as this:

<a href='http://www.example.com/login.php/"><script type="text/javascript">...</script><span a="'>Example.com</a>

The javascript block would define an event handler function and bind it to the form's submit event. This event handler would load via an <img> tag an external file, with the submitted username and password as parameters.

Use $_SERVER['SCRIPT_NAME'] instead of $_SERVER['PHP_SELF']. HTML encode every string sent to the browser that should not be interpreted as HTML, unless you are absolutely certain that it cannot contain anything that the browser can interpret as HTML.

info at mtprod dot com (23-Jan-2009 10:13)

On Windows IIS 7 you must use $_SERVER['LOCAL_ADDR'] rather than $_SERVER['SERVER_ADDR'] to get the server's IP address.

jonbarnett at gmail dot com (24-Nov-2008 05:13)

It's worth noting that $_SERVER variables get created for any HTTP request headers, including those you might invent:

If the browser sends an HTTP request header of:
X-Debug-Custom: some string

Then:

<?php
$_SERVER
['HTTP_X_DEBUG_CUSTOM']; // "some string"
?>

There are better ways to identify the HTTP request headers sent by the browser, but this is convenient if you know what to expect from, for example, an AJAX script with custom headers.

Works in PHP5 on Apache with mod_php.  Don't know if this is true from other environments.

jette at nerdgirl dot dk (01-Nov-2008 07:43)

Windows running IIS v6 does not include $_SERVER['SERVER_ADDR']

If you need to get the IP addresse, use this instead:

<?php
$ipAddress
= gethostbyname($_SERVER['SERVER_NAME']);
?>

geoffrey dot hoffman at gmail dot com (26-Oct-2008 01:13)

If you are looking at $_SERVER['HTTP_USER_AGENT'] to determine whether your user is on a mobile device, you may want to visit these resources:

http://wurfl.sourceforge.net/

http://www.zytrax.com/tech/web/mobile_ids.html

Thomas Urban (22-Oct-2008 09:19)

Maybe you're missing information on $_SERVER['CONTENT_TYPE'] or $_SERVER['CONTENT_LENGTH'] as I did. On POST-requests these are available in addition to those listed above.

Taomyn (12-Oct-2008 03:21)

'HTTPS'
    Set to a non-empty value if the script was queried through the HTTPS protocol. Note that when using ISAPI with IIS, the value will be off if the request was not made through the HTTPS protocol.

Does the same for IIS7 running PHP as a Fast-CGI application.

Tonin (16-Sep-2008 06:43)

When using the $_SERVER['SERVER_NAME'] variable in an apache virtual host setup with a ServerAlias directive, be sure to check the UseCanonicalName apache directive.  If it is On, this variable will always have the apache ServerName value.  If it is Off, it will have the value given by the headers sent by the browser.

Depending on what you want to do the content of this variable, put in On or Off.

Andrew B (09-Sep-2008 12:26)

Please note on Windows/IIS - the variable 'USER_AUTH' will return the username/identity of the user accessing the page, i.e. if anonymous access is off, you would normally get back "$domain\$username".

jeff at example dot com (12-Aug-2008 07:24)

Note that, in Apache 2, the server settings will affect the variables available in $_SERVER. For example, if you are using SSL, the following directive will dump SSL-related status information, along with the server certificate and client certificate (if present) into the $_SERVER variables:

SSLOptions +StdEnvVars +ExportCertData

silverquick at gmail dot com (06-Aug-2008 01:55)

I think the HTTPS element will only be present under Apache 2.x. It's not in the list of "special" variables here:
http://httpd.apache.org/docs/1.3/mod/mod_rewrite.html#RewriteCond
But it is here:
http://httpd.apache.org/docs/2.0/mod/mod_rewrite.html#rewritecond

danny at orionrobots dot co dot uk (31-Jul-2008 10:25)

It is worth noting here that if you use $_SERVER['REQUEST_URI'] with a rewrite rule, the original, not rewritten URI will be presented.

emailfire at gmail dot com (26-May-2008 03:49)

REQUEST_URI is useful, but if you want to get just the file name use:

<?php
$this_page
= basename($_SERVER['REQUEST_URI']);
if (
strpos($this_page, "?") !== false) $this_page = reset(explode("?", $this_page));
?>