前言
NGINX 在 2018 正式推出支援 gRPC proxy module,到了今年 2020,還推出了 gRPC 相關的 directives,這些都讓 NGINX 具備 proxy gRPC 的能力。而且還非常實用!
2018–03–20
nginx-1.13.10 mainline version has been released, featuring the gRPC proxy module.2018–04–17
nginx-1.14.0 stable version has been released, incorporating new features and bug fixes from the 1.13.x mainline branch — including the mirror module, HTTP/2 push, the gRPC proxy module, and more.2020–04–21
nginx-1.18.0 stable version has been released, incorporating new features and bug fixes from the 1.17.x mainline branch — including the dry run mode in limit_req and limit_conn, variables support in the limit_rate, limit_rate_after, and grpc_pass directives, the auth_delay directive, and more.
NGINX 跟 gRPC 在 load balancing 的角色
從這圖可以看出,不同 client 來的 gRPC traffic,其實都當 NIGIX 為接口,並 route traffic 到內部的 gRPC server。而這篇就是要介紹如何設定 NGINX config,讓 NGINX 替你導流量。
基本上使用 gRPC 所使用的資料格式,都會是 protobuf,而下面就是我們會使用的 package 範例。
package helloworld;
service Greeter {
rpc SayHello (HelloRequest) returns (HelloReply) {}
}service Dispatcher {
rpc DispatchHello (HelloRequest) returns (HelloReply) {}
}
而 NGINX 其實就是根據你的 request URL 來判斷如何分流,因此你必須先知道 Protobuf 中定義的 service 跟實際發送的 URL 會是什麼樣子
192.168.20.11 - - [01/Mar/2018:13:35:02 +0000] "POST /helloworld.Greeter/SayHello HTTP/2.0" 200 18 "-" "grpc-go/-dev"192.168.20.11 - - [01/Mar/2018:13:35:02 +0000] "POST /helloworld.Dispatcher/DispatchHello HTTP/2.0" 200 18 "-" "grpc-go/dev"
NGINX location
而在 NGINX 的 nginx.conf 裡,你就可以這麼定義分成三個部分。
- 經由
helloworld.Greeter
會導入192.168.20.11:50051
這台 server - 經由
helloworld.Dispatcher
會導入192.168.20.11:50052
這台 server - 而非以上兩種,不管你是忘記還是刻意,他都會進入到 catch-all (
/
),就像是 switch-case 的 default
location /helloworld.Greeter {
grpc_pass grpc://192.168.20.11:50051;
}
location /helloworld.Dispatcher {
grpc_pass grpc://192.168.20.11:50052;
}
location / {
root html;
index index.html index.htm;
}
NGINX upstream
這個方便將多個分類放在一起或命名,你也可以選擇直接透過 grpc_pass 指定就好,不用刻意指出 upstream。
但他還是有非常實用的地方,讓每個 upstream 間可以有各自的設定,例如可以設定裡面 server 的權重讓效能好的機器吃較多的流量,並且也可透過命名快速知道是什麼用途。
NGINX grpc_pass
設定 gRPC server address,這可以有很多方式
domain, IP and port OP
grpc_pass localhost:9000;
UNIX-domain socket path
grpc_pass unix:/tmp/grpc.socket;
grpc 或 grpcs (TLS)
不給也可以,預設會是 grpc://
grpc_pass grpc://127.0.0.1:9000;
grpc_pass grpcs://127.0.0.1:443;