首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >为什么$_SERVER['HTTP_HOST']有时是example.com,有时是example.com:443?

问为什么$_SERVER['HTTP_HOST']有时是example.com,有时是example.com:443?
EN

Server Fault用户
提问于 2019-10-04 10:31:27
回答 1查看 10K关注 0票数 4

这是一个在Apache上运行PHP 7的Ubuntu服务器,它的网站强制使用TLS (使用标准端口)。据我理解,https://example.com和https://example.com:443完全等价(实际上,在我的浏览器中,端口号在我输入地址栏时会从地址栏消失)。然而,HTTP_HOST通常只包含域名,但有时也包含端口号。这可能是为机器人访问者(我还没有分析日志),但即使如此,我不知道如何。有什么实际差别吗?

(这导致了一些问题,因为我们的一些日志、工作队列和服务器端缓存是由HTTP_HOST分隔的,因此在不同的主机上拥有相同的站点报告是令人困惑的。)

EN

回答 1

Server Fault用户

回答已采纳

发布于 2019-10-04 15:06:41

PHP文档声明$_SERVER['HTTP_HOST']是:

主机的内容:来自当前请求的标题(如果有)。

实际上,该关联数组中的每个变量(其键以字符串HTTP_开头)都是由用户代理发送的相应HTTP变量的副本。

那么,为什么它有时包含主机名,有时同时包含主机名和端口号?

事实证明,这两种语法都是合法的和等价的。如果服务器使用非默认端口,则需要端口号,否则是可选的。

在什么情况下,用户代理会发送端口号,即使它是默认的?

RFC 7230第5.4条解释说,Host: header的值是URI的授权组件的精确副本。

如果目标URI包含一个授权组件,那么客户端必须发送与该授权组件相同的主机字段值,不包括任何userinfo子组件及其"@“分隔符。。。

什么是权威的组成部分?

这来自于RFC 3986第3.2节中URI的定义,它解释了它是用户信息(用户名和密码)、主机和端口。它解释说,如果端口是默认端口,则应该省略该端口,但不应该等于必须。(见RFC 2119.)

因此,如果主机:头也出现在URI中,则需要用户代理发送端口号。因此,如果用户代理有URL https://example.com:443/robots.txt,那么它将有一个标头Host: example.com:443。用户代理是如何得到这样一个URL的,没有真正的方法可以判断。它可能是由应用程序发送的,也可能是由用户代理构造的。

RFC 7230第2.7.3节解释了URL规范化,这表明不包含端口号的URL与包含默认端口号的URL是等效的。

TL;DR:您的应用程序必须期望端口号可能出现在这个标头中,并以与使用它的上下文相适应的方式处理它。

您可以考虑使用$_SERVER['SERVER_NAME'],它包含处理请求的Apache 中的ServerName指令的值(或者,对于nginx,是server块中的第一个server_name )。

票数 5
EN
页面原文内容由Server Fault提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://serverfault.com/questions/986761

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档