Open Source Gateway Status:
Currently, there are two Java open source gateways, zuul and SpringCloudGateway. However, these two gateways still need to be expanded according to their own business requirements. So there are many companies on the second development of the company, of course, there are some companies choose from the research gateway. Most of them may be done based on native Netty, but I think it takes time and is difficult to write based on native Netty, so I suggest to do responsive gateway based on Spring WebFlux (based on Netty development).
How to request based on the SpringWebFlux agent:
In fact, the most core point of the gateway is the proxy request, if the proxy to request other functions naturally easy, then how to proxy request based on WebFlux? There are two core apis to extend:
1.AbstractHandlerMapping
2.WebHandler
Here’s how SpringCloudGateway extends these two classes:
1. RoutePredicateHandlerMapping:
This class mainly intercepts the request and passes it to FilteringWebHandler for processing
private final FilteringWebHandler webHandler; private final RouteLocator routeLocator; @Override protected Mono<? > getHandlerInternal(ServerWebExchange exchange) {if(this.managementPortType == DIFFERENT && this.managementPort ! = null && exchange.getRequest().getURI().getPort() == this.managementPort) {return Mono.empty();
}
exchange.getAttributes().put(GATEWAY_HANDLER_MAPPER_ATTR, getSimpleName());
return lookupRoute(exchange)
// .log("route-predicate-handler-mapping", Level.FINER) //name this .flatMap((Function<Route, Mono<? >>) r -> { exchange.getAttributes().remove(GATEWAY_PREDICATE_ROUTE_ATTR);if (logger.isDebugEnabled()) {
logger.debug(
"Mapping [" + getExchangeDesc(exchange) + "] to " + r);
}
exchange.getAttributes().put(GATEWAY_ROUTE_ATTR, r);
returnMono.just(webHandler); }).switchIfEmpty(mono.empty ().then(mono.fromrunnable (()) -> { exchange.getAttributes().remove(GATEWAY_PREDICATE_ROUTE_ATTR);if (logger.isTraceEnabled()) {
logger.trace("No RouteDefinition found for ["
+ getExchangeDesc(exchange) + "]"); }}))); }Copy the code
2. FilteringWebHandler:
This class handles the specific request while executing the entire Filter chain, which is where the Filter is executed using the extended SpringCloudGateway.
@override public Mono<Void> Handle (ServerWebExchange exchange) {// You can implement authentication, traffic limiting, fusing, and greyscale functions exchange.getRequiredAttribute(GATEWAY_ROUTE_ATTR); List<GatewayFilter> gatewayFilters = route.getFilters(); List<GatewayFilter> combined = new ArrayList<>(this.globalFilters); combined.addAll(gatewayFilters); // TODO: needed or cached? AnnotationAwareOrderComparator.sort(combined);if (logger.isDebugEnabled()) {
logger.debug("Sorted gatewayFilterFactories: " + combined);
}
return new DefaultGatewayFilterChain(combined).filter(exchange);
}
Copy the code
The last
If you want to build your own gateway based on SpringWebFlux, you can follow the above implementation. Will it still be difficult for the gateway to support all the registry, Dubbo, HTTP services in SpringCloud?