如何确定您是否在没有 $_SERVER的情况下使用 HTTPS['HTTPS']

2022-08-30 06:21:53

我在网上看到许多教程,说你需要检查服务器是否连接是否使用HTTPS保护。我的问题是,在我使用的某些服务器上,是一个未定义的变量,会导致错误。是否有另一个可以检查的变量应始终定义?$_SERVER['HTTPS']$_SERVER['HTTPS']

为了清楚起见,我目前正在使用此代码来解决它是否是HTTPS连接:

if(isset($_SERVER['HTTPS'])) {
    if ($_SERVER['HTTPS'] == "on") {
        $secure_connection = true;
    }
}

答案 1

即使未定义,这应该始终有效:$_SERVER['HTTPS']

function isSecure() {
  return
    (!empty($_SERVER['HTTPS']) && $_SERVER['HTTPS'] !== 'off')
    || $_SERVER['SERVER_PORT'] == 443;
}

该代码与 IIS 兼容。

PHP.net 文档和用户评论

  1. 如果通过 HTTPS 协议查询脚本,则设置为非空值。

  2. 请注意,将 ISAPI 与 IIS 一起使用时,如果请求不是通过 HTTPS 协议发出的,则该值将为“关闭”。(对于运行 PHP 作为 Fast-CGI 应用程序的 IIS7,报告了相同的行为)。

此外,Apache 1.x服务器(和损坏的安装)可能还没有定义,即使连接安全也是如此。尽管不能保证,但按照惯例,端口 443 上的连接可能使用安全套接字,因此需要进行额外的端口检查。$_SERVER['HTTPS']

附加说明:如果客户端和服务器之间存在负载平衡器,则此代码不会测试客户端与负载平衡器之间的连接,而是测试负载平衡器与服务器之间的连接。要测试以前的连接,您必须使用标头进行测试,但这样做要复杂得多;请参阅此答案下方的最新评论HTTP_X_FORWARDED_PROTO


答案 2

我的解决方案(因为标准条件 [$_SERVER['HTTPS'] == 'on'] 在负载平衡器后面的服务器上不起作用)是:

$isSecure = false;
if (isset($_SERVER['HTTPS']) && $_SERVER['HTTPS'] == 'on') {
    $isSecure = true;
}
elseif (!empty($_SERVER['HTTP_X_FORWARDED_PROTO']) && $_SERVER['HTTP_X_FORWARDED_PROTO'] == 'https' || !empty($_SERVER['HTTP_X_FORWARDED_SSL']) && $_SERVER['HTTP_X_FORWARDED_SSL'] == 'on') {
    $isSecure = true;
}
$REQUEST_PROTOCOL = $isSecure ? 'https' : 'http';

HTTP_X_FORWARDED_PROTO:用于识别HTTP请求的原始协议的事实标准,因为反向代理(负载平衡器)可以使用HTTP与Web服务器进行通信,即使对反向代理的请求是HTTPS http://en.wikipedia.org/wiki/List_of_HTTP_header_fields#Common_non-standard_request_headers


推荐