Consul + zuul:api网关,提供路由转发功能之服务路由的默认配置

it2023-07-11  69

实现功能:

每次往Consul注册新的服务,我们无需更改zuul的网关配置,就可以通过zuul服务的ip实现路由转发功能。

serviceservice-id(instance-id)ip:porturi通过路由的访问方式test-configtest-config10.9.100.100:8801

/api/getCountNum

/api/hand/sites

/health

localhost:8804/test-config/api/getCountNum

localhost:8804/test-config/api/hand/sites

localhost:8804/test-config/health

test-config-service00test-config-service0010.9.100.100:8802

/api/getCountNum

/api/hand/sites

/health

localhost:8804/test-config-service00/api/getCountNum

localhost:8804/test-config-service00/api/hand/sites

localhost:8804/test-config-service00/health

test-config-service01test-config-service0110.9.100.100:8803

/api/getCountNum

/api/hand/sites

/health

localhost:8804/test-config-service01/api/getCountNum

localhost:8804/test-config-service01/api/hand/sites

localhost:8804/test-config-service01/health

路由服务

zuul-gateway-service

(在这里是

test-config-service02)

zuul-gateway-servicelocalhost:8804/health 

请求方式:

${ZuulServerIP}:${server.port}:/${新注册的Server}/[新服务的请求uri]

案例:

Consul上的三个服务:

Zuul-gateway服务:

注:应为是本地启动的zuul-gateway服务,名字为test-config-service02,端口号为8804 。另,Consul服务上有个红×的原因是因为我是本地电脑注册到Consul的,健康检测时获取的是我电脑PC的主机名,该主机名在Consul服务器上没有映射,故无法健康检测。但是服务不受影响。

test-config-service02服务的

pom.xml

<?xml version="1.0" encoding="UTF-8"?> <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> <parent> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-parent</artifactId> <version>2.3.2.RELEASE</version> <relativePath/> <!-- lookup parent from repository --> </parent> <modelVersion>4.0.0</modelVersion> <groupId>com.example</groupId> <artifactId>zuul-gateway</artifactId> <version>1.0</version> <packaging>jar</packaging> <name>springboot</name> <properties> <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding> <maven.compiler.source>1.8</maven.compiler.source> <maven.compiler.target>1.8</maven.compiler.target> <java.version>1.8</java.version> <spring-cloud.version>Greenwich.RELEASE</spring-cloud.version> </properties> <dependencies> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-web</artifactId> <exclusions><!-- 去掉springboot默认配置 --> <exclusion> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-logging</artifactId> </exclusion> <exclusion> <artifactId>snakeyaml</artifactId> <groupId>org.yaml</groupId> </exclusion> </exclusions> </dependency> <dependency> <!-- 引入log4j2依赖 --> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-log4j2</artifactId> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-test</artifactId> <scope>test</scope> <exclusions> <exclusion> <groupId>org.junit.vintage</groupId> <artifactId>junit-vintage-engine</artifactId> </exclusion> </exclusions> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-devtools</artifactId> <scope>runtime</scope> </dependency> <dependency> <groupId>org.projectlombok</groupId> <artifactId>lombok</artifactId> <optional>true</optional> </dependency> <dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-consul-discovery</artifactId> </dependency> <dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-consul-config</artifactId> </dependency> <dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-netflix-zuul</artifactId> <exclusions> <exclusion> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-actuator</artifactId> </exclusion> </exclusions> </dependency> </dependencies> <dependencyManagement> <dependencies> <dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-dependencies</artifactId> <version>${spring-cloud.version}</version> <type>pom</type> <scope>import</scope> </dependency> </dependencies> </dependencyManagement> <build> <plugins> <plugin> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-maven-plugin</artifactId> </plugin> </plugins> </build> </project>

application.yml

spring: cloud: consul: host: hdp04 # consul 服务器主机名 port: 8500 # consul 服务器端口 discovery: # healthCheckPath: ${management.contextPath}/health # actuator 健康检查的 url 路径 healthCheckPath: /health # 自定义健康检查的 url(适合于不适用 actuator 的场景) healthCheckInterval: 15s # 健康检查的频率, 默认 15 秒 # 直接指定服务的 consul service id(即 instance id). # 默认情况下为 spring.application.name + server.port, 如果在多个服务器上同一个服务, 因为应用名和端口都一致, #会导致service id 会重复, 所以一般情况都需要引入一个随机数避免重复 . # ${spring.application.name}:${spring.cloud.client.ip-address}:${server.port} 应用名称+服务器IP+端口 instance-id: test-config-service02 #${spring.application.name}:${vcap.application.instance_id:${spring.application.instance_id:${random.value}}} # prefer-ip-address: true # 在注册时使用 consul IP, 而不是 hostname # ip-address: hdp04 # 使用 consul 服务器 IP, 而不是 hostname, 需要搭配 prefer-ip-address 属性 # acl-token: 4efb1523-76a3-f476-e6d8-452220593089 #设定 consul acl token 值 enabled: true #是否启用服务发现 # 维护 tags #$ 下面示例的 tag map 是: foo->bar 和 baz->baz tags: version=1.0,author=xx enabled: true # ribbon: # enabled: false application: name: test-config-service02 ##负载均衡 test-config的服务会转发到 hdp01:8801上执行 #test-config: # ribbon: # listOfServers: hdp01:8801 ##负载均衡 test-config-service00的服务会转发到 hdp01:8802上执行 #test-config-service00: # ribbon: # listOfServers: hdp01:8802 ##负载均衡 test-config-service01的服务会转发到 hdp01:8803上执行 #test-config-service01: # ribbon: # listOfServers: hdp01:8803 ##负载均衡 test-config-service02的服务会转发到 hdp01:8803,localhost:8804上执行 #test-config-service02: # ribbon: # listOfServers: hdp01:8803,localhost:8804 server: port: 8804 #zuul属性配置 zuul.routes路由转发配置 #Zuul来代理请求转发到内部的服务上去,统一为外部提供服务 动态的路由转发功能 #zuul: # routes: # test-config: # #静态路径配置 所有的以/api 开始的请求,全部转发到test-config服务去执行 # path: /api/** #consul-provider-payment是自定义的微服务名称,当访问consul-provider-payment/**开始的地址时,就会跳转到上。 匹配规则三种:/? /* /** # url: hdp01:8801 # #url: #本地跳转 # # forward: /test-config #本地跳转 # #service-id: consul-provider-payment # #consul-provider-payment-part: #功能拆分, 将原属于 api-a 服务的某些功能拆分到另一个全新的服务 api-a-part 中, 而这些拆分的外部调用 URL 路径希望能够符合规则 /api-a/part/** # # path: /consul-provider-payment/service-another/** # test-config-service00: # path: /test-config-service00/** # url: hdp01:8802 # test-config-service01: # path: /test-config-service01/** # url: hdp01:8803 # test-config-service02: # path: /test-config-service02/** # url: localhost:8804 # host: # connect-timeout-millis: 3000 # socket-timeout-millis: 60000 # 添加ribbon的超时时间设置 ribbon: ReadTimeout: 3000 ConnectTimeout: 10000 #hystrix: # command: # default: # execution: # isolation: # thread: # timeoutInMilliseconds: 6000

Application.java

import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.SpringBootApplication; import org.springframework.cloud.client.discovery.EnableDiscoveryClient; import org.springframework.cloud.netflix.zuul.EnableZuulProxy; /** * @author : lihai * @date : 2020/9/3 9:24 AM * springboot启动类 */ @SpringBootApplication //@EnableDiscoveryClient @EnableZuulProxy /**EnableZuulProxy包含了EnableDiscoveryClient*/ public class Application { public static void main(String[] args) { SpringApplication.run(Application.class, args); } }

 测试:

服务test-config测试: 

 

17:43:46.536 [http-nio-8804-exec-5] INFO com.netflix.config.ChainedDynamicProperty - Flipping property: test-config.ribbon.ActiveConnectionsLimit to use NEXT property: niws.loadbalancer.availabilityFilteringRule.activeConnectionsLimit = 2147483647 17:43:46.537 [http-nio-8804-exec-5] INFO com.netflix.util.concurrent.ShutdownEnabledTimer - Shutdown hook installed for: NFLoadBalancer-PingTimer-test-config 17:43:46.538 [http-nio-8804-exec-5] INFO com.netflix.loadbalancer.BaseLoadBalancer - Client: test-config instantiated a LoadBalancer: DynamicServerListLoadBalancer:{NFLoadBalancer:name=test-config,current list of Servers=[],Load balancer stats=Zone stats: {},Server stats: []}ServerList:null 17:43:46.539 [http-nio-8804-exec-5] INFO com.netflix.loadbalancer.DynamicServerListLoadBalancer - Using serverListUpdater PollingServerListUpdater 17:43:46.547 [http-nio-8804-exec-5] INFO com.netflix.config.ChainedDynamicProperty - Flipping property: test-config.ribbon.ActiveConnectionsLimit to use NEXT property: niws.loadbalancer.availabilityFilteringRule.activeConnectionsLimit = 2147483647 17:43:46.547 [http-nio-8804-exec-5] INFO com.netflix.loadbalancer.DynamicServerListLoadBalancer - DynamicServerListLoadBalancer for client test-config initialized: DynamicServerListLoadBalancer:{NFLoadBalancer:name=test-config,current list of Servers=[hdp01:8801],Load balancer stats=Zone stats: {unknown=[Zone:unknown; Instance count:1; Active connections count: 0; Circuit breaker tripped count: 0; Active connections per server: 0.0;] },Server stats: [[Server:hdp01:8801; Zone:UNKNOWN; Total Requests:0; Successive connection failure:0; Total blackout seconds:0; Last connection made:Thu Jan 01 08:00:00 CST 1970; First connection made: Thu Jan 01 08:00:00 CST 1970; Active Connections:0; total failure count in last (1000) msecs:0; average resp time:0.0; 90 percentile resp time:0.0; 95 percentile resp time:0.0; min resp time:0.0; max resp time:0.0; stddev resp time:0.0] ]}ServerList:ConsulServerList{serviceId='test-config', tag=null} 17:43:47.565 [PollingServerListUpdater-0] INFO com.netflix.config.ChainedDynamicProperty - Flipping property: test-config.ribbon.ActiveConnectionsLimit to use NEXT property: niws.loadbalancer.availabilityFilteringRule.activeConnectionsLimit = 2147483647

服务 test-config-service00测试: 

 

18:49:12.282 [http-nio-8804-exec-1] INFO com.netflix.config.ChainedDynamicProperty - Flipping property: test-config-service00.ribbon.ActiveConnectionsLimit to use NEXT property: niws.loadbalancer.availabilityFilteringRule.activeConnectionsLimit = 2147483647 18:49:12.300 [http-nio-8804-exec-1] INFO com.netflix.util.concurrent.ShutdownEnabledTimer - Shutdown hook installed for: NFLoadBalancer-PingTimer-test-config-service00 18:49:12.300 [http-nio-8804-exec-1] INFO com.netflix.loadbalancer.BaseLoadBalancer - Client: test-config-service00 instantiated a LoadBalancer: DynamicServerListLoadBalancer:{NFLoadBalancer:name=test-config-service00,current list of Servers=[],Load balancer stats=Zone stats: {},Server stats: []}ServerList:null 18:49:12.306 [http-nio-8804-exec-1] INFO com.netflix.loadbalancer.DynamicServerListLoadBalancer - Using serverListUpdater PollingServerListUpdater 18:49:12.329 [http-nio-8804-exec-1] INFO com.netflix.config.ChainedDynamicProperty - Flipping property: test-config-service00.ribbon.ActiveConnectionsLimit to use NEXT property: niws.loadbalancer.availabilityFilteringRule.activeConnectionsLimit = 2147483647 18:49:12.330 [http-nio-8804-exec-1] INFO com.netflix.loadbalancer.DynamicServerListLoadBalancer - DynamicServerListLoadBalancer for client test-config-service00 initialized: DynamicServerListLoadBalancer:{NFLoadBalancer:name=test-config-service00,current list of Servers=[hdp01:8802],Load balancer stats=Zone stats: {unknown=[Zone:unknown; Instance count:1; Active connections count: 0; Circuit breaker tripped count: 0; Active connections per server: 0.0;] },Server stats: [[Server:hdp01:8802; Zone:UNKNOWN; Total Requests:0; Successive connection failure:0; Total blackout seconds:0; Last connection made:Thu Jan 01 08:00:00 CST 1970; First connection made: Thu Jan 01 08:00:00 CST 1970; Active Connections:0; total failure count in last (1000) msecs:0; average resp time:0.0; 90 percentile resp time:0.0; 95 percentile resp time:0.0; min resp time:0.0; max resp time:0.0; stddev resp time:0.0] ]}ServerList:ConsulServerList{serviceId='test-config-service00', tag=null} 18:49:13.355 [PollingServerListUpdater-0] INFO com.netflix.config.ChainedDynamicProperty - Flipping property: test-config-service00.ribbon.ActiveConnectionsLimit to use NEXT property: niws.loadbalancer.availabilityFilteringRule.activeConnectionsLimit = 2147483647

 

 

中途遇到的一个错误:

该错误出现的环境:Consul上的服务都正常,本地的zuul-gateway服务也正常。在请求后端接口的时候,INFO  com.netflix.loadbalancer.DynamicServerListLoadBalancer - DynamicServerListLoadBalancer for client test-config-service00 initialized: DynamicServerListLoadBalancer:也正常,能看到请求体包括访问的服务、ip、端口、数据都正常,但是结果获取结果的时候报错。

com.netflix.zuul.exception.ZuulException: at org.springframework.cloud.netflix.zuul.filters.post.SendErrorFilter.findZuulException(SendErrorFilter.java:118) ~[spring-cloud-netflix-zuul-2.1.2.RELEASE.jar:2.1.2.RELEASE] at org.springframework.cloud.netflix.zuul.filters.post.SendErrorFilter.run(SendErrorFilter.java:78) ~[spring-cloud-netflix-zuul-2.1.2.RELEASE.jar:2.1.2.RELEASE] at com.netflix.zuul.ZuulFilter.runFilter(ZuulFilter.java:117) [zuul-core-1.3.1.jar:1.3.1] at com.netflix.zuul.FilterProcessor.processZuulFilter(FilterProcessor.java:193) [zuul-core-1.3.1.jar:1.3.1] at com.netflix.zuul.FilterProcessor.runFilters(FilterProcessor.java:157) [zuul-core-1.3.1.jar:1.3.1] at com.netflix.zuul.FilterProcessor.error(FilterProcessor.java:105) [zuul-core-1.3.1.jar:1.3.1] at com.netflix.zuul.ZuulRunner.error(ZuulRunner.java:112) [zuul-core-1.3.1.jar:1.3.1] at com.netflix.zuul.http.ZuulServlet.error(ZuulServlet.java:145) [zuul-core-1.3.1.jar:1.3.1] at com.netflix.zuul.http.ZuulServlet.service(ZuulServlet.java:83) [zuul-core-1.3.1.jar:1.3.1] at org.springframework.web.servlet.mvc.ServletWrappingController.handleRequestInternal(ServletWrappingController.java:165) [spring-webmvc-5.1.9.RELEASE.jar:5.1.9.RELEASE] at org.springframework.cloud.netflix.zuul.web.ZuulController.handleRequest(ZuulController.java:45) [spring-cloud-netflix-zuul-2.1.2.RELEASE.jar:2.1.2.RELEASE] at org.springframework.web.servlet.mvc.SimpleControllerHandlerAdapter.handle(SimpleControllerHandlerAdapter.java:52) [spring-webmvc-5.1.9.RELEASE.jar:5.1.9.RELEASE] at org.springframework.web.servlet.DispatcherServlet.doDispatch(DispatcherServlet.java:1039) [spring-webmvc-5.1.9.RELEASE.jar:5.1.9.RELEASE] at org.springframework.web.servlet.DispatcherServlet.doService(DispatcherServlet.java:942) [spring-webmvc-5.1.9.RELEASE.jar:5.1.9.RELEASE] at org.springframework.web.servlet.FrameworkServlet.processRequest(FrameworkServlet.java:1005) [spring-webmvc-5.1.9.RELEASE.jar:5.1.9.RELEASE] at org.springframework.web.servlet.FrameworkServlet.doGet(FrameworkServlet.java:897) [spring-webmvc-5.1.9.RELEASE.jar:5.1.9.RELEASE] at javax.servlet.http.HttpServlet.service(HttpServlet.java:634) [tomcat-embed-core-9.0.22.jar:9.0.22] at org.springframework.web.servlet.FrameworkServlet.service(FrameworkServlet.java:882) [spring-webmvc-5.1.9.RELEASE.jar:5.1.9.RELEASE] at javax.servlet.http.HttpServlet.service(HttpServlet.java:741) [tomcat-embed-core-9.0.22.jar:9.0.22] at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:231) [tomcat-embed-core-9.0.22.jar:9.0.22] at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166) [tomcat-embed-core-9.0.22.jar:9.0.22] at org.apache.tomcat.websocket.server.WsFilter.doFilter(WsFilter.java:53) [tomcat-embed-websocket-9.0.22.jar:9.0.22] at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:193) [tomcat-embed-core-9.0.22.jar:9.0.22] at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166) [tomcat-embed-core-9.0.22.jar:9.0.22] at org.springframework.boot.actuate.web.trace.servlet.HttpTraceFilter.doFilterInternal(HttpTraceFilter.java:88) [spring-boot-actuator-2.1.7.RELEASE.jar:2.1.7.RELEASE] at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:118) [spring-web-5.1.9.RELEASE.jar:5.1.9.RELEASE] at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:193) [tomcat-embed-core-9.0.22.jar:9.0.22] at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166) [tomcat-embed-core-9.0.22.jar:9.0.22] at org.springframework.web.filter.RequestContextFilter.doFilterInternal(RequestContextFilter.java:99) [spring-web-5.1.9.RELEASE.jar:5.1.9.RELEASE] at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:118) [spring-web-5.1.9.RELEASE.jar:5.1.9.RELEASE] at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:193) [tomcat-embed-core-9.0.22.jar:9.0.22] at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.ja

解决方式:

 

# 添加ribbon的超时时间设置 ribbon: ReadTimeout: 3000 ConnectTimeout: 10000

 

最新回复(0)