如何设置路由规则

    安装完成后,可以看到集群中增加了下面两个 NS,这两个 NS 中分别安装了基于 MetaProtocol 实现的 Dubbo 和 Thrift 协议的示例程序。 你可以选用任何一个程序进行测试。

    Istio 会使用 TCP proxy 来代理非 HTTP 协议的客户端请求,同一个客户端 TCP 连接上发出的所有请求都会被发送到一个服务器实例。这导致了一个问题:当客户端使用长连接时,多个服务器实例收到的请求不够均衡,当服务端压力过大时,即使及时扩容也不能将已有服务端的压力分担出去。

    Aeraki 支持对基于 MetaProtocol 开发的任何协议进行七层(请求级别)负载均衡,因此在不进行任何配置的情况下,客户端的代理会将请求均匀发送到两个不同版本的服务器端。 下面我们用 aerakictl 命令来查看客户端的应用日志,可以看到同一个客户端连接上的多个请求被依次发送到了 v1 和 v2 两个服务器端。

    1. Hello Aeraki, response from dubbo-sample-provider-v2-7546478cbf-l2l74/172.16.0.37
    2. Hello Aeraki, response from dubbo-sample-provider-v1-6b7cc9b6f8-j9dvl/172.16.0.89
    3. Hello Aeraki, response from dubbo-sample-provider-v2-7546478cbf-l2l74/172.16.0.37
    4. Hello Aeraki, response from dubbo-sample-provider-v1-6b7cc9b6f8-j9dvl/172.16.0.89
    5. Hello Aeraki, response from dubbo-sample-provider-v2-7546478cbf-l2l74/172.16.0.37
    6. Hello Aeraki, response from dubbo-sample-provider-v1-6b7cc9b6f8-j9dvl/172.16.0.89

    MetaProtocol 支持了非常灵活的路由匹配条件,任何可以从协议数据包中解析出来的属性都能用于路由匹配条件。

    创建一条 MetaRouter 路由规则,将请求路由到 v1:

    1. kubectl apply -f- <<EOF
    2. apiVersion: metaprotocol.aeraki.io/v1alpha1
    3. kind: MetaRouter
    4. metadata:
    5. name: test-metaprotocol-dubbo-route
    6. namespace: meta-dubbo
    7. spec:
    8. hosts:
    9. - org.apache.dubbo.samples.basic.api.demoservice
    10. routes:
    11. - name: v1
    12. match:
    13. attributes:
    14. interface:
    15. exact: org.apache.dubbo.samples.basic.api.DemoService
    16. method:
    17. exact: sayHello
    18. foo:
    19. exact: bar
    20. route:
    21. - destination:
    22. host: org.apache.dubbo.samples.basic.api.demoservice
    23. subset: v1
    24. EOF

    使用 aerakictl 命令来查看客户端的应用日志,可以看到客户端的所有请求都被路由到了 v1 版本:

    使用 MetaRouter 路由规则将客户端的流量按照指定比例发送到不同版本的服务。

    1. kubectl apply -f- <<EOF
    2. apiVersion: metaprotocol.aeraki.io/v1alpha1
    3. kind: MetaRouter
    4. metadata:
    5. name: test-metaprotocol-dubbo-route
    6. namespace: meta-dubbo
    7. spec:
    8. hosts:
    9. - org.apache.dubbo.samples.basic.api.demoservice
    10. routes:
    11. - name: traffic-split
    12. match:
    13. attributes:
    14. interface:
    15. exact: org.apache.dubbo.samples.basic.api.DemoService
    16. method:
    17. foo:
    18. exact: bar
    19. route:
    20. host: org.apache.dubbo.samples.basic.api.demoservice
    21. subset: v1
    22. weight: 20
    23. - destination:
    24. host: org.apache.dubbo.samples.basic.api.demoservice
    25. subset: v2
    26. weight: 80
    27. EOF

    使用 aerakictl 命令来查看客户端的应用日志,可以看到客户端的请求按照 MetaRouter 中设置的指定比例发送到了 v1 和 v2:

    1. ~ aerakictl_app_log consumer meta-dubbo -f --tail 10
    2. Hello Aeraki, response from dubbo-sample-provider-v1-6b7cc9b6f8-j9dvl/172.16.0.89
    3. Hello Aeraki, response from dubbo-sample-provider-v1-6b7cc9b6f8-j9dvl/172.16.0.89
    4. Hello Aeraki, response from dubbo-sample-provider-v1-6b7cc9b6f8-j9dvl/172.16.0.89
    5. Hello Aeraki, response from dubbo-sample-provider-v1-6b7cc9b6f8-j9dvl/172.16.0.89
    6. Hello Aeraki, response from dubbo-sample-provider-v1-6b7cc9b6f8-j9dvl/172.16.0.89
    7. Hello Aeraki, response from dubbo-sample-provider-v1-6b7cc9b6f8-j9dvl/172.16.0.89
    8. Hello Aeraki, response from dubbo-sample-provider-v1-6b7cc9b6f8-j9dvl/172.16.0.89
    9. Hello Aeraki, response from dubbo-sample-provider-v2-7546478cbf-l2l74/172.16.0.37
    10. Hello Aeraki, response from dubbo-sample-provider-v2-7546478cbf-l2l74/172.16.0.37
    11. Hello Aeraki, response from dubbo-sample-provider-v1-6b7cc9b6f8-j9dvl/172.16.0.89

    Aeraki 会将 MetaRouter 中配置的路由规则翻译为 MetaProtocol Proxy 的路由规则,通过 Aeraki 内置的 RDS 服务器下发给 MetaProtocol Proxy。

    可以通过下面的命令查看 sidecar proxy 的配置:

    其中 Dubbo 服务的 Outbound Listener 中的 MetaProtocol Proxy 配置如下所示:

    1. {
    2. "name":"envoy.filters.network.meta_protocol_proxy",
    3. "typed_config":{
    4. "@type":"type.googleapis.com/udpa.type.v1.TypedStruct",
    5. "type_url":"type.googleapis.com/aeraki.meta_protocol_proxy.v1alpha.MetaProtocolProxy",
    6. "value":{
    7. "stat_prefix":"outbound|20880||org.apache.dubbo.samples.basic.api.demoservice",
    8. "application_protocol":"dubbo",
    9. "rds":{
    10. "config_source":{
    11. "api_config_source":{
    12. "api_type":"GRPC",
    13. "grpc_services":[
    14. {
    15. "envoy_grpc":{
    16. "cluster_name":"aeraki-xds"
    17. }
    18. }
    19. ],
    20. "transport_api_version":"V3"
    21. },
    22. "resource_api_version":"V3"
    23. },
    24. "route_config_name":"org.apache.dubbo.samples.basic.api.demoservice_20880"
    25. },
    26. "codec":{
    27. "name":"aeraki.meta_protocol.codec.dubbo"
    28. },
    29. "meta_protocol_filters":[
    30. "name":"aeraki.meta_protocol.filters.router"
    31. ]
    32. }
    33. }
    34. }

    在导出的文件中还可以查看到目前 Proxy 中生效的 RDS 路由信息,如下所示:

    1. {
    2. "@type":"type.googleapis.com/aeraki.meta_protocol_proxy.admin.v1alpha.RoutesConfigDump",
    3. "dynamic_route_configs":[
    4. {
    5. "version_info":"1650265656",
    6. "route_config":{
    7. "@type":"type.googleapis.com/aeraki.meta_protocol_proxy.config.route.v1alpha.RouteConfiguration",
    8. "name":"org.apache.dubbo.samples.basic.api.demoservice_20880",
    9. "routes":[
    10. {
    11. "name":"traffic-split",
    12. "match":{
    13. "metadata":[
    14. {
    15. "name":"interface",
    16. "exact_match":"org.apache.dubbo.samples.basic.api.DemoService"
    17. },
    18. {
    19. "name":"method",
    20. "exact_match":"sayHello"
    21. },
    22. {
    23. "name":"foo",
    24. "exact_match":"bar"
    25. }
    26. ]
    27. },
    28. "route":{
    29. "weighted_clusters":{
    30. "clusters":[
    31. {
    32. "name":"outbound|20880|v1|org.apache.dubbo.samples.basic.api.demoservice",
    33. "weight":20
    34. },
    35. {
    36. "name":"outbound|20880|v2|org.apache.dubbo.samples.basic.api.demoservice",
    37. "weight":80
    38. }
    39. ],
    40. "total_weight":100
    41. }
    42. }
    43. }
    44. ]
    45. },
    46. "last_updated":"2022-04-18T07:07:36.165Z"