在httpd的反向代理中,ProxyPass 的主要作用就是修改Content-Location和Location的内容。对这两个首部的含义做一些说明。
内容协商(content negotiation)
为了说明Content-Location的含义,必须先明白http的内容协商机制。
考虑支持多语言的服务器端:一个相同的URL可以返回不同语言版本的文档, 其实服务器端就是利用内容协商来识别客户端的,具体可以参见《http权威指南》第17章。 在请求的头信息中,包含有Accept开头的内容协商首部,服务器端可以根据这些内容协商首部来判断出客户端的需求。 除此之外,服务器端还可以根据诸如User-Agent这种首部信息进行推测,例如老版本的浏览器可能不支持JavaScript,如果User-Agent代表老版本的浏览器,那么服务器可以向其响应不包含JavaScript的文档。
在上面的请求头部中,我们看到了多个内容协商首部。 在Accept-Languoge中我们还发现了q值,这叫做质量值。 考虑这种情况,假如服务器端仅仅拥有中文和英文两个版本,并没有日文,但是客户端却最希望能请求到日文内容,这样服务器端就无法提供合适的文档给它了。 而q值的意义就是让客户端可以提供多个候选方案,q值(0.0-1.0)越大表明优先级越高,例如上图中表明:优先选择日文,如果没有日文优先选择en-US,没有en-US,那就选择en。
上面这种内容协商机制叫做服务器端协商。 为了减轻服务器端的压力,我们可以使用中间代理来代替服务器端来与客户端协商,这叫做透明协商。 中间代理如果可以代替服务器,那么代理必须有能力可以完全像服务器那样处理协商逻辑。对于每一种不同的请求服务器端响应的不同版本的文档,我们可以称作是一个 变体。 代理需要有能力根据每一个请求的信息,从缓存的副本中选择 或者 向服务器请求(当副本中没有对应的时候),得到准确的变体。 从上面服务器端协商的讨论中我们知道除了内容协商首部外,服务器能够根据其他首部(例如user-agent)来识别客户端,从而响应不同的变体。 为了让代理具有完全相同的处理协商逻辑的能力,服务器在响应代理的时候,必须告诉代理除了内容协商首部外还根据什么信息处理协商逻辑了,这个首部叫做vary,例如vary:User-Agent。
Content-Location和Content
Content-Location首部表明返回数据的另一种位置。主要的使用场景是用来表明作为内容协商结果响应的资源的URL。
Location和Content-Location是不同的:Location表明重定向的目标(302),而Content-Location表明无需进行进一步的内容协商就可以直接访问的资源的URL,例如英文环境客户端发送 url_file_a 可以得到文件fileA,那么假设响应中Content-Location中内容为 url_file_a_en ,则这个url可以直接访问到对应的那个英文文件,此时其实就不存在内容协商了。 Location是一个与响应相关的头信息,而Content-Location是与返回的内容主体相关的头信息。
参考:
《http权威zhinan》 第17章
https://developer.mozilla.org/zh-CN/docs/Web/HTTP/Headers/Content-Location