内部重定向由nginx worker进程在单次请求生命周期内同步完成,通过修改请求对象的uri和args并重新匹配location实现,不返回3xx响应、不新建连接、不增加并发压力。

Worker Process 本身不直接“处理”内部重定向,而是由 Nginx 的事件驱动机制和请求处理流程协同完成——内部重定向(如 try_files 触发的 fallback)是模块级行为,发生在单个 worker 进程内的一次请求生命周期中,无需跨进程或重新调度。
内部重定向不是 HTTP 跳转,而是请求路径重解析
所谓“内部重定向”,本质是 Nginx 在当前 worker 进程内,对同一请求对象(ngx_http_request_t)修改其 r->uri 和 r->args,然后重新匹配 location 块,不返回 3xx 响应,客户端无感知。整个过程在一次事件循环中完成,不涉及新连接、不触发新的 accept 或 upstream 转发(除非后续 location 配置了 proxy_pass)。
worker 进程内如何执行 try_files fallback
当配置 try_files $uri $uri/ /index.html; 时:
- worker 接收请求后,先按
root或alias拼出物理路径,检查$uri对应文件是否存在; - 若不存在,再检查
$uri/是否为有效目录; - 两者都失败,则将
r->uri改为/index.html,并清空r->args(除非显式保留); - 接着调用
ngx_http_core_find_location重新查找匹配的 location 块; - 若新 URI 匹配到静态文件 location,直接读取并响应;若匹配到
location ~ \.php$,则交由 fastcgi 模块处理。
rewrite 指令中的内部重定向也由 worker 同步完成
例如:rewrite ^/old/(.*)$ /new/$1 last;
-
last标志表示内部重定向:修改r->uri后重新进行 location 查找; - 该操作在当前 worker 的 handler 函数中同步执行,不阻塞事件循环;
- 若使用
break,则只改 URI 不重匹配 location;若用redirect或permanent,才返回 302/301,属于外部重定向。
注意:内部重定向不会增加 worker 并发压力
因为不产生新请求、不新建 socket、不触发 epoll wait 新事件:
- 它复用原始请求结构体,仅重走路由与 handler 链;
- 耗时取决于文件系统 I/O(如
stat()检查)和后续模块处理逻辑(如 PHP 解析),而非 worker 数量; - 高并发下,合理使用
try_files反而比频繁 rewrite + external redirect 更高效,避免客户端二次请求。











