警告-这是第一(快速)草案,需要进一步修订!
2.0及更高版本中的一些更改会影响内部请求处理机制。模块作者需要了解这些更改,以便他们可以利用这些优化和安全性增强功能。
第一个主要变化是子请求和重定向机制。Apache HTTP Server 1.3中有许多不同的代码路径,以尝试优化子请求或重定向行为。在2.0版中引入了补丁程序之后,由于这种重复代码,这些优化(以及服务器行为)很快就被破坏了。所有重复的代码均已折回,ap_process_request_internal()
以防止代码再次不同步。
这意味着现有的许多代码都是“未优化的”。创建HTTP服务器RFC的可靠,正确的实现是Apache HTTP项目的第一个目标。其他目标包括安全性,可伸缩性和优化。寻求了新的方法来优化服务器(超过1.3的性能),而又不引入脆弱或不安全的代码。
所有请求通过ap_process_request_internal()
在server/request.c
包括子请求和重定向。如果某个模块未通过此代码传递生成的请求,则警告作者,该模块可能会因将来对请求处理的更改而被破坏。
为了简化请求,模块作者可以利用提供的钩子来提早退出请求周期,或者绕过无关紧要的核心钩子(在CPU方面成本很高)。
parsed_uri
在内部请求处理开始时,一次且仅一次取消转义请求的路径。
如果设置了proxyreq标志或未设置parsed_uri.path
元素,则绕过此步骤
。该模块无法对此单次转义操作进行进一步的控制,否则,如果无法转义或多次对URL进行转义会导致安全后果。
所有/../
和/./
元素均由ap_getparents()
以及任何尾随
/.
或/..
元素删除。这有助于确保在请求处理继续之前(几乎)绝对路径。(有关更多讨论,请参见RFC 1808第4节。)
无法跳过此步骤。
每个请求都会受到
ap_location_walk()
呼叫的影响。这样可以确保
<Location>
对所有请求都一致地执行各节。如果请求是内部重定向或子请求,则它可以从上一个或父请求的ap_location_walk借用部分或全部处理,因此在处理主请求后,此步骤通常非常有效。
模块可以确定文件名,或在此步骤中更改给定的URI。例如,mod_vhost_alias
将URI的路径转换为已配置的虚拟主机,
mod_alias
将路径转换为别名路径,并且如果请求退回到核心,则该DocumentRoot
前缀将附加到请求资源中。
如果DECLINE
该阶段的所有模块都将向浏览器返回错误500,并自动记录“无法翻译名称”错误。
确定文件或正确的URI之后,将适当的每个目录配置合并在一起。例如,mod_proxy
比较并合并适当的
<Proxy>
部分。如果URI只不过是一个本地(非代理)TRACE
请求,则核心将处理该请求并返回DONE
。如果没有模块用OK
或回答该钩子DONE
,则内核将针对<Directory>
和<Files>
部分运行请求文件名。如果请求“文件名”不是绝对的合法文件名,则会设置注释以供以后终止。
每个请求都会由第二个ap_location_walk()
调用强化
。这样可以确保翻译后的请求仍受配置
<Location>
部分的约束。该请求再次借鉴了之前的请求中的部分或全部处理
location_walk
,因此,除非转换后的URI映射到实质上不同的路径或虚拟主机,否则此步骤几乎总是非常高效。
然后,主请求解析客户端的标头。这将准备其余的请求处理步骤,以更好地服务于客户的请求。
需要文档。代码是:
if ((access_status = ap_run_access_checker(r)) != 0) { return decl_die(access_status, "check access", r); } if ((access_status = ap_run_check_user_id(r)) != 0) { return decl_die(access_status, "check user", r); } if ((access_status = ap_run_auth_checker(r)) != 0) { return decl_die(access_status, "check authorization", r); }
模块有机会针对目标资源测试URI或文件名,并为请求设置mime信息。双方mod_mime
并
mod_mime_magic
使用此阶段进行比较的管理员的配置文件的名称或内容并设置内容类型,语言,字符集和请求处理程序。某些模块此时可能会设置其过滤器或其他请求处理参数。
如果DECLINE
该阶段的所有模块都将向浏览器返回错误500,并自动记录“找不到类型”错误。
在上面的某个阶段,许多模块被“删节了”。模块使用修正阶段来“重新声明”其所有权或将请求的字段强制为适当的值。它并不总是最干净的机制,但有时是唯一的选择。
此阶段不属于中的处理过程
ap_process_request_internal()
。许多模块在创建任何内容之前都会准备一个或多个子请求。在核心或模块调用之后
ap_process_request_internal()
,然后调用
ap_invoke_handler()
以生成请求。
以某种方式转换内容的模块可以插入其值并覆盖现有过滤器,这样,如果用户无序配置了更高级的过滤器,则该模块可以根据需要移动其顺序。没有结果代码,因此最好信任此挂钩中的操作以始终成功。
该模块最终有机会在其处理程序挂钩中处理该请求。请注意,并非每个准备好的请求都发送到处理程序挂钩。许多模块(例如mod_autoindex
)将为给定的URI创建子请求,然后再也不提供该子请求,而只是为用户列出该子请求。切记不要将所需的拆卸操作从上面的挂钩中放到该模块中,而应在请求池中注册池清理,以根据需要释放资源。
可用语言: zh