在spring cloud gateway的源码中,我们看到会调用 RibbonLoadBalancerClient.choose(String serviceId)的方法。这个方法调用了getServer(serviceId),choose方法就是通过Ribbon获取到服务的ip。
public ServiceInstance choose(String serviceId) {
Server server = getServer(serviceId);
if (server ==null) {
return null;
}
return new RibbonServer(serviceId, server, isSecure(server, serviceId),
serverIntrospector(serviceId).getMetadata(server));
}
1.getServer(serviceId)方法 这个方法调用了getLoadBalancer(serviceId),getLoadBalancer(serviceId)这个方法就是通过工厂来获取LoadBanlancer。
protected Server getServer(String serviceId) {
return getServer(getLoadBalancer(serviceId));
}
protected Server getServer(ILoadBalancer loadBalancer) {
if (loadBalancer ==null) {
return null;
}
return loadBalancer.chooseServer("default");// TODO: better handling of key
}
protected ILoadBalancer getLoadBalancer(String serviceId) {
return this.clientFactory.getLoadBalancer(serviceId);
}
获取到服务的ip后,gateway获取到url,并且组装成调用下游的绝对路径,进行调用
URI uri = exchange.getRequest().getURI();
// if the `lb:` mechanism was used, use `` as the default,
// if the loadbalancer doesn't provide one.
String overrideScheme =null;
if (schemePrefix !=null) {
overrideScheme = url.getScheme();
}
URI requestUrl =loadBalancer.reconstructURI(new DelegatingServiceInstance(instance, overrideScheme), uri);
最后将具体的uri放到exchange上下文的GATEWAY_REQUEST_URL_ATTR中
为最后的NettyRoutingFilter的httpclient调用做准备