首先说说我遇到的情况,我是在gateway网关服务中配置了3个路由分别访问到不同的模块,然而第一个配置的路由可以正常访问,之后添加2个路由一直是404报错。
一开始的配置如下:
server:
port: 88
spring:
application:
name: gulimall-gateway
cloud:
nacos:
discovery:
server-addr: 127.0.0.1:8848
gateway:
routes:
- id: test_route
uri: https://www.baidu.com
predicates:
- Query=url,baidu
- id: admin_route
uri: lb://renren-fast
predicates:
- Path=/api/**
filters:
- RewritePath=/api/(?<segment>.*),/renren-fast/$\{segment}
- id: product_route
uri: lb://gulimall-product
predicates:
- Path=/api/product/**
filters:
- RewritePath=/api/(?<segment>.*),/$\{segment}
- id: coupon_route
uri: lb://gulimall-coupon
predicates:
- Path=/api/coupon/**
filters:
- RewritePath=/api/(?<segment>.*),/$\{segment}
在这样的配置下访问id为admin_route路由的请求全都正常,当我尝试访问id为product_route、coupon_route这2个路由对应模块的接口全都报404,反复对这二个路由以及出现404的http请求路径进行检查并未发现任何问题,可他就是神奇的404了,一度崩溃的边缘我似乎突然想到了什么,重点在 predicates 的 path上,当我需要请求product服务的接口,假设路径为localhost:88/api/product/list,看似这个请求是满足了product_route这个路由的断言,实则他也同样满足了admin_route这个路由的断言,由于admin_route这个路由写在了最前面的位置,所以在发送localhost:88/api/product/list这样的请求时被admin_route给拦截到,在admin_route对应的服务上没有相应路径的接口自然就报404这样的错误了。
经过修改后可以正常访问的配置如下:
server:
port: 88
spring:
application:
name: gulimall-gateway
cloud:
nacos:
discovery:
server-addr: 127.0.0.1:8848
gateway:
routes:
- id: test_route
uri: https://www.baidu.com
predicates:
- Query=url,baidu
- id: product_route
uri: lb://gulimall-product
predicates:
- Path=/api/product/**
filters:
- RewritePath=/api/(?<segment>.*),/$\{segment}
- id: coupon_route
uri: lb://gulimall-coupon
predicates:
- Path=/api/coupon/**
filters:
- RewritePath=/api/(?<segment>.*),/$\{segment}
- id: admin_route
uri: lb://renren-fast
predicates:
- Path=/api/**
filters:
- RewritePath=/api/(?<segment>.*),/renren-fast/$\{segment}
因为coupon_route、product_route的断言规则相比admin_route的断言规则多一个层级应当放在前面进行优先匹配。
总结就是写代码时一定要带脑子,一定要带脑子,一定要带脑子,不然总是会犯下一些愚蠢而又想不到的问题。