RoutePredicateHandlerMapping#getHandlerInternal

The WebFlux entry point is the DispatcherHandler, which calls the getHandler method of HandlerMapping. AbstracThandlerMapping implements the HandlerMapping interface. It has an abstract method called GetHandlerInternal that requires a subclass implementation. RoutePredicateHandlerMapping inherited AbstractHandlerMapping, so our focus is his getHandlerInternal method. This Route is used to determine whether there is a corresponding Route. This method, in fact, mainly calls the lookuProute method.

protected Mono<? > getHandlerInternal(ServerWebExchange exchange) { // don't handle requests on management port if set and different than  server port 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); return Mono.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) + "]"); }}))); }

RoutePredicateHandlerMapping#lookupRoute

You can see that it has code like r.getpredicate ().apply. This apply will eventually call each test method on the Predicate, returning false or true.

protected Mono<Route> lookupRoute(ServerWebExchange exchange) { return this.routeLocator.getRoutes() // individually filter routes so that filterWhen error delaying is not a // problem .concatMap(route -> Mono.just(route).filterWhen(r ->  { // add the current route we are testing exchange.getAttributes().put(GATEWAY_PREDICATE_ROUTE_ATTR, r.getId()); return r.getPredicate().apply(exchange); }) // Other short}

DefaultAsyncPredicate#apply

In this case, you call the test method of each Predicate.

public Publisher<Boolean> apply(T t) {
    return Mono.just(delegate.test(t));
}

FilteringWebHandler#handle

We’ve got a Route from the above method (we won’t continue without it), so let’s call the Filter. After calling Handlermappings, the DispatcherHandler will call his InvokeHandler method.

private Mono<HandlerResult> invokeHandler(ServerWebExchange exchange, Object handler) { if (this.handlerAdapters ! = null) { for (HandlerAdapter handlerAdapter : this.handlerAdapters) { if (handlerAdapter.supports(handler)) { return handlerAdapter.handle(exchange, handler); } } } return Mono.error(new IllegalStateException("No HandlerAdapter: " + handler)); }

The WebHandler.handle method is then called.

public Mono<HandlerResult> handle(ServerWebExchange exchange, Object handler) {
    WebHandler webHandler = (WebHandler) handler;
    Mono<Void> mono = webHandler.handle(exchange);
    return mono.then(Mono.empty());
}

Our FilteringWebHandler is a WebHandler, and let’s look at its handle method. It fetches the corresponding Route’s Filters, merges the order with the generic Filters, and finally starts the call chain for the Filters.

Public Mono<Void> handle(ServerWebExchange exchange) {// get Route Route Route = exchange.getRequiredAttribute(GATEWAY_ROUTE_ATTR); // Filters < gatewayFilter > gatewayFilters = route.getFilters(); // Filters < gatewayFilter > combined = new ArrayList<>(this.globalfilters); combined.addAll(gatewayFilters); // TODO: needed or cached? / / sorting AnnotationAwareOrderComparator. Sort (combined); if (logger.isDebugEnabled()) { logger.debug("Sorted gatewayFilterFactories: " + combined); } / / invocation chain return new DefaultGatewayFilterChain (combined) filter (exchange); }

The whole process

The DispatcherHandler part is ignored here