You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

无法在NGINX中读取gRPC请求头的问题求助

解决OpenResty读取gRPC客户端自定义请求头的问题

问题根源

gRPC的自定义元数据通过HTTP/2传输,OpenResty处理这类请求时,得注意头名的大小写、Lua代码的执行时机,还要确保NGINX没把自定义头过滤掉。

具体解决步骤

1. 选对Lua代码的执行时机

得在grpc_pass转发请求之前的阶段(比如access_by_lua_block)读取请求头,要是等请求已经发往后端了,再读就晚了。

给个NGINX配置的例子:

server {
    listen 443 ssl http2;
    server_name your-domain.com;

    ssl_certificate /path/to/cert;
    ssl_certificate_key /path/to/key;

    location /your.grpc.service {
        # 转发前先执行Lua读头
        access_by_lua_block {
            local headers = ngx.req.get_headers()
            
            # 先遍历所有头,看看有没有收到自定义头
            for k, v in pairs(headers) do
                ngx.log(ngx.ERR, "收到头: ", k, " => ", v)
            end

            # 用完全匹配的小写头名读取(gRPC元数据转HTTP/2后是小写)
            local custom_header = headers["custom-header-name"]
            if custom_header then
                ngx.log(ngx.ERR, "找到自定义头: ", custom_header)
            else
                ngx.log(ngx.ERR, "没找到自定义头")
            end
        }

        grpc_pass grpc://your-grpc-backend:50051;
        # 如果要把自定义头传给后端服务,加这句
        grpc_pass_header custom-header-name;
    }
}

2. 严格匹配gRPC元数据的HTTP/2映射规则

gRPC的文本元数据要求头名必须是小写字母开头,只能包含小写字母、数字、连字符,你的custom-header-name是符合要求的。传输时头名会原样保留,所以Lua里必须用custom-header-name这个完全一致的key读取,别换成下划线版本。

3. 确认OpenResty版本支持gRPC

得用OpenResty 1.13.6.1及以上的版本,Docker镜像直接用官方的openresty/openresty稳定版就行,别用太老的版本。

4. 验证客户端确实发了元数据

在Go客户端加个日志,确认元数据已经正确附在请求上下文里:

md, ok := metadata.FromOutgoingContext(ctx)
if ok {
    log.Printf("发送的元数据: %v", md)
}

额外提醒

  • 要是想在Lua里改或者加gRPC元数据,用ngx.req.set_header()就行,但头名得符合gRPC的规则。
  • grpc_pass_header是控制哪些头传给后端gRPC服务的,要是只是NGINX自己读头,不用配这个。

内容的提问来源于stack exchange,提问作者Ben Zini

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.21 18:45:55