3、Nginx核心概念:反向代理、正向代理、负载均衡、HTTP/HTTPS、上游服务器、location匹配规则

在部署大模型推理服务时,Nginx 通常扮演流量入口和分发枢纽的角色。理解其核心概念,是正确配置反向代理、保障服务高可用与安全性的前提。本章将围绕六个关键概念展开:反向代理与正向代理的区别、负载均衡策略、HTTP/HTTPS 协议适配、上游服务器(upstream)的配置方法,以及 location 匹配规则的优先级。这些概念并非孤立存在,而是共同构成了一条从客户端请求到后端大模型推理引擎的完整链路。我们先通过一张概念关系图建立整体认知,再逐一深入拆解。

客户端 浏览器 / SDK / curl HTTP/HTTPS 请求 正向代理 代表客户端访问 隐藏客户端身份 场景:翻墙/缓存 Nginx 核心枢纽 反向代理 (proxy_pass) 代表服务器接收请求,转发给上游 负载均衡 (upstream) 轮询 / 最少连接 / IP哈希 location 匹配规则 前缀匹配 / 精确匹配 / 正则 上游服务器组 推理节点 1 10.0.1.11:8000 推理节点 2 10.0.1.12:8000 推理节点 3 10.0.1.13:8000 健康检查 + 权重 max_fails / fail_timeout HTTPS:443 HTTP:8000 转发请求 图例: 客户端 反向代理 负载均衡 location规则 上游服务器 正向代理(可选)

上图展示了 Nginx 在大模型部署中的核心位置。客户端通过 HTTPS 访问 Nginx,Nginx 根据 location 规则匹配请求路径,再通过 upstream 定义的负载均衡策略将请求分发到多个推理节点。正向代理则是一个可选的旁路场景,通常用于开发调试或访问外部受限资源。下面我们逐一解析每个概念。

3.1 反向代理与正向代理:方向决定本质

核心原理

正向代理(Forward Proxy)位于客户端一侧,代表客户端发起请求。客户端将请求发送给代理服务器,由代理服务器转发到目标服务器。目标服务器只知道代理的 IP,不知道真实客户端 IP。典型场景包括:企业内网访问外网、绕过地域限制、缓存加速。

反向代理(Reverse Proxy)位于服务器一侧,代表服务器接收请求。客户端将请求发送给反向代理,反向代理根据规则将请求转发到内部的上游服务器。客户端只知道反向代理的地址,不知道后端真实服务器 IP。典型场景包括:负载均衡、SSL 终结、统一入口、安全防护。

对比维度正向代理反向代理
代理对象客户端(代表用户)服务器(代表后端)
隐藏身份隐藏客户端 IP隐藏服务器 IP
典型配置resolver + proxy_pass(指向外部域名)upstream + proxy_pass(指向内部节点)
部署位置客户端网络边界服务器机房入口
大模型场景调试外部 API(如 OpenAI)统一入口分发到推理集群

判断方法

判断一个代理是正向还是反向,只需问一个问题:代理在替谁工作?如果代理配置在客户端环境,替客户端转发请求,就是正向代理;如果代理配置在服务端入口,替后端服务器接收请求,就是反向代理。在 Nginx 配置中,正向代理通常不配置 upstream,而是直接使用 proxy_pass http://$http_host$request_uri; 配合 resolver;反向代理则必须配置 upstream 或固定的后端地址。

案例拆解:大模型 API 网关的正反向代理混合使用

某 AI 公司内部开发环境需要同时访问外部 GPT-4 API 和内部自研的 Llama-3 推理服务。他们在开发机配置了正向代理(端口 3128)用于访问外部 API,同时在生产环境部署了 Nginx 反向代理(端口 443)用于内部推理集群的负载均衡。开发人员通过 export https_proxy=http://dev-proxy:3128 访问外部 API;生产环境的客户端则直接请求 https://llm-gateway.example.com/v1/completions,由反向代理分发到 3 台推理节点。两种代理解决了不同层面的问题:正向代理解决“出网”问题,反向代理解决“入网”和“分发”问题。

经验提醒:在大模型部署中,反向代理是标配,正向代理仅在特定调试场景使用。不要在生产环境混用两者,否则会导致请求路由混乱。

3.2 负载均衡:让每个推理节点都“忙而不乱”

核心原理

负载均衡(Load Balancing)是将客户端请求按照某种策略分发到多个上游服务器的过程。Nginx 默认支持三种负载均衡算法:轮询(round-robin)、最少连接(least_conn)和IP 哈希(ip_hash)。此外,还可以通过 weight 参数调整权重,通过 max_fails 和 fail_timeout 实现故障转移。

upstream llm_backend {
    least_conn;  # 最少连接策略
    server 10.0.1.11:8000 weight=3 max_fails=3 fail_timeout=30s;
    server 10.0.1.12:8000 weight=2 max_fails=3 fail_timeout=30s;
    server 10.0.1.13:8000 backup;  # 备份节点,平时不参与
}

操作流程

  1. 定义 upstream 块,列出所有推理节点 IP 和端口。
  2. 选择负载均衡算法:默认轮询;如果节点性能差异大,使用 weight;如果请求处理时间差异大,使用 least_conn;如果需要会话保持,使用 ip_hash。
  3. 配置健康检查参数:max_fails 表示允许失败次数,fail_timeout 表示失败后冷却时间。
  4. 在 server 或 location 块中通过 proxy_pass http://llm_backend; 引用 upstream。

案例拆解:推理集群的负载均衡调优

某大模型服务部署了 3 台推理节点,配置为 A100 GPU。初始使用默认轮询策略,但发现节点 1 的 GPU 利用率经常达到 95%,而节点 3 只有 40%。分析日志发现,不同请求的推理长度差异巨大(短文本 0.5 秒,长文本 15 秒),轮询策略无法感知请求耗时。改为 least_conn 策略后,Nginx 会将新请求分配给当前活跃连接数最少的节点,GPU 利用率趋于均衡(75%/70%/68%)。同时,将节点 1 的 weight 从 1 调整为 3(因为其 GPU 型号更新),进一步优化了吞吐量。调优后,P95 延迟从 8.2 秒降至 5.6 秒。

风险提示:ip_hash 策略虽然能保持会话,但如果某个节点宕机,该 IP 的请求会全部转移到其他节点,可能导致瞬时过载。大模型推理通常无状态,建议优先使用 least_conn 或轮询。

3.3 HTTP/HTTPS:加密与性能的平衡

核心原理

HTTP 是明文协议,HTTPS 在 HTTP 之上增加了 TLS/SSL 加密层。Nginx 通常作为 TLS 终结者(TLS Terminator):对外提供 HTTPS 服务,对内使用 HTTP 与上游通信。这样做的优势是:证书管理集中化、后端无需处理加解密、可以利用 Nginx 的 HTTP/2 和 HTTP/3 优化性能。

server {
    listen 443 ssl http2;
    server_name llm-gateway.example.com;
    
    ssl_certificate     /etc/nginx/certs/llm-gateway.crt;
    ssl_certificate_key /etc/nginx/certs/llm-gateway.key;
    ssl_protocols       TLSv1.2 TLSv1.3;
    ssl_ciphers         HIGH:!aNULL:!MD5;
    
    location /v1/ {
        proxy_pass http://llm_backend;
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        proxy_set_header X-Forwarded-Proto $scheme;
    }
}

判断方法

判断是否需要 HTTPS:如果服务暴露在公网,必须启用 HTTPS;如果仅在内网使用,可以权衡性能与安全。大模型 API 通常涉及敏感数据(用户输入、推理结果),建议即使在内网也启用 HTTPS。注意,proxy_set_header X-Forwarded-Proto $scheme; 是必须的,否则后端无法判断原始请求是 HTTP 还是 HTTPS,可能导致生成的回调 URL 协议错误。

常见误区

  • 误区 1:只配置了 443 端口,忘记配置 80 端口跳转。应添加 server { listen 80; return 301 https://$host$request_uri; }。
  • 误区 2:SSL 证书过期未更新,导致客户端握手失败。建议配置 certbot 自动续期。
  • 误区 3:上游也使用 HTTPS,但未配置 proxy_ssl_server_name on;,导致 SNI 校验失败。

3.4 上游服务器:定义后端节点池

核心原理

上游服务器(upstream)是 Nginx 中定义的一组后端服务器。每个服务器可以包含 IP、端口、权重、最大失败次数、备份标记等属性。upstream 块必须定义在 http 上下文内,可以在多个 server 或 location 中复用。

参数默认值说明
weight1权重,值越大分配请求越多
max_fails1允许失败次数,超过后标记为不可用
fail_timeout10s失败后冷却时间,也是标记不可用的持续时间
backup-标记为备份节点,主节点全部不可用时启用
down-手动标记为不可用,不参与请求分发

操作流程

  1. 确定推理节点的 IP 和端口(如 10.0.1.11:8000)。
  2. 评估节点性能差异,设置合理的 weight。
  3. 配置健康检查参数,避免将请求转发到已宕机的节点。
  4. 使用 proxy_next_upstream 指令控制失败重试策略。
proxy_next_upstream error timeout http_502 http_503 http_504;
proxy_next_upstream_tries 2;  # 最多重试 2 次
实战要点:大模型推理请求通常耗时较长(秒级到分钟级),需要将 proxy_read_timeout 设置为 300s 或更长,否则 Nginx 会在默认 60s 后断开连接,导致推理任务中断。

3.5 location 匹配规则:精确控制请求路由

核心原理

location 指令用于匹配请求 URI,并根据匹配结果执行不同的配置块。匹配规则分为三类:前缀匹配(普通字符串)、精确匹配(=)、正则匹配(~ 区分大小写,~* 不区分大小写)。匹配优先级从高到低为:精确匹配(=)→ 前缀匹配(^~,一旦匹配则不再检查正则)→ 正则匹配(按配置顺序)→ 最长前缀匹配(未使用 ^~)。

location = /healthz {
    return 200 "OK\n";  # 精确匹配健康检查
}

location ^~ /v1/ {
    proxy_pass http://llm_backend;  # 前缀匹配,优先于正则
}

location ~* \.(jpg|png|gif)$ {
    expires 30d;  # 正则匹配图片资源
}

location / {
    proxy_pass http://llm_backend;  # 兜底匹配
}

判断方法

判断 location 匹配结果时,按以下顺序检查:

  1. 先检查是否有 = 精确匹配,命中则立即使用。
  2. 再检查最长前缀匹配,如果该前缀使用了 ^~,则直接使用,不再检查正则。
  3. 否则按配置顺序检查正则表达式,第一个匹配的生效。
  4. 如果正则都没有匹配,使用最长前缀匹配的结果。

案例拆解:大模型 API 的多路由配置

某平台需要同时提供聊天补全、模型管理和静态文档服务。配置如下:

server {
    listen 443 ssl;
    server_name llm.example.com;
    
    location = /healthz {
        access_log off;
        return 200 "alive";
    }
    
    location ^~ /v1/chat/completions {
        proxy_pass http://llm_backend;
        proxy_read_timeout 300s;
        proxy_set_header X-Request-ID $request_id;
    }
    
    location ^~ /v1/models {
        proxy_pass http://model_admin;
        proxy_read_timeout 10s;
    }
    
    location ~* \.(html|js|css|png)$ {
        root /data/static;
        expires 7d;
    }
    
    location / {
        return 404;
    }
}

当请求 /healthz 时,精确匹配直接返回;请求 /v1/chat/completions 时,前缀匹配命中并转发到推理集群;请求 /v1/models 时,转发到模型管理服务;请求 /docs/index.html 时,正则匹配到静态文件;其他请求返回 404。这种配置将不同业务路径清晰隔离,避免了规则冲突。

风险提示:location 匹配中,proxy_pass 的路径拼接规则容易出错。如果 location 使用前缀匹配且 proxy_pass 不带 URI(如 http://llm_backend),则原始 URI 会完整传递给上游;如果 proxy_pass 带 URI(如 http://llm_backend/),则匹配部分会被替换。务必通过 curl 测试验证实际转发路径。

3.6 综合配置模板与复盘

将上述概念整合,一个典型的大模型推理网关配置如下:

http {
    upstream llm_backend {
        least_conn;
        server 10.0.1.11:8000 max_fails=3 fail_timeout=30s;
        server 10.0.1.12:8000 max_fails=3 fail_timeout=30s;
        server 10.0.1.13:8000 backup;
    }
    
    server {
        listen 443 ssl http2;
        server_name llm-gateway.example.com;
        
        ssl_certificate     /etc/nginx/certs/fullchain.pem;
        ssl_certificate_key /etc/nginx/certs/privkey.pem;
        
        # 安全头
        add_header X-Content-Type-Options nosniff;
        add_header X-Frame-Options DENY;
        
        location = /healthz {
            access_log off;
            return 200 "OK";
        }
        
        location /v1/ {
            proxy_pass http://llm_backend;
            proxy_http_version 1.1;
            proxy_set_header Connection "";
            proxy_set_header Host $host;
            proxy_set_header X-Real-IP $remote_addr;
            proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
            proxy_set_header X-Forwarded-Proto $scheme;
            proxy_read_timeout 300s;
            proxy_send_timeout 300s;
            proxy_buffering off;  # 流式输出时关闭缓冲
        }
    }
}

复盘要点:第一,反向代理是 Nginx 在大模型部署中的核心角色,务必理解其与正向代理的本质区别;第二,负载均衡策略应根据推理请求的耗时分布选择,least_conn 通常优于轮询;第三,HTTPS 配置中要关注证书管理和超时设置;第四,upstream 的健康检查参数直接影响故障转移效率;第五,location 匹配规则决定了 API 路由的灵活性,建议使用 ^~ 前缀匹配避免正则干扰。在实际部署中,建议先用 nginx -t 校验配置,再用 curl 逐一测试每个 location 的转发行为,最后通过压测工具(如 wrk、ab)验证负载均衡效果。