Spring Cloud Gateway 请求执行流程源码分析

1. 官网流程图

Spring Cloud Gateway Diagram

2. 代码时序图示

  • 请求首先进入 DispatcherHandler的handler方法
  • DispatcherHandler的handler方法中循环遍历所有的 HandlerMapping 并找到合适的 Handler(可能有多个,这里是FilteringWebHandler)
  • 然后遍历所有的适配器 handlerAdapters,找到能够支持执行上面找到的Handler的适配器
  • 通过找到的适配器 Adapter 去执行 Handler
  • handler中会根据Exchange中路由获取自定义Filter集合(gatewayFilters),同时与全局globalFilters组装为新的全量Filter集合
  • 之后根据全量Filter集合构造FilterChain,并依次链式执行Filter的filter方法

请添加图片描述

3. 关键代码分析

3.1 DispatcherHandler#handler

	@Override
	public Mono<Void> handle(ServerWebExchange exchange) {
		if (this.handlerMappings == null) {
			return createNotFoundError();
		}
		if (CorsUtils.isPreFlightRequest(exchange.getRequest())) {
			return handlePreFlight(exchange);
		}
		// 遍历handlerMappings并依次调用getHandler方法,获取适配的handler
		return Flux.fromIterable(this.handlerMappings)
				// 这里会执行到AbstractHandlerMapping#getHandler,最终返回的是FilteringWebHandler
				.concatMap(mapping -> mapping.getHandler(exchange))
				.next()
				.switchIfEmpty(createNotFoundError())
				// 此方法会遍历所有的适配器 handlerAdapters,找到能够支持执行上面找到的Handler的适配器
				.flatMap(handler -> invokeHandler(exchange, handler))
				.flatMap(result -> handleResult(exchange, result));
	}
	
	
	private Mono<HandlerResult> invokeHandler(ServerWebExchange exchange, Object handler) {
		if (ObjectUtils.nullSafeEquals(exchange.getResponse().getStatusCode(), HttpStatus.FORBIDDEN)) {
			return Mono.empty();  // CORS rejection
		}
		if (this.handlerAdapters != null) {
			for (HandlerAdapter handlerAdapter : this.handlerAdapters) {
				if (handlerAdapter.supports(handler)) {
					// 通过找到的适配器 Adapter 去执行 Handler,最终进入到SimpleHandlerAdapter.handler方法
					return handlerAdapter.handle(exchange, handler);
				}
			}
		}
		return Mono.error(new IllegalStateException("No HandlerAdapter: " + handler));
	}

3.2 AbstractHandlerMapping#getHandler

	@Override
	public Mono<Object> getHandler(ServerWebExchange exchange) {
		// 这里首先会执行RoutePredicateHandlerMapping#getHandlerInternal方法获取匹配的路由route
		return getHandlerInternal(exchange).map(handler -> {
			if (logger.isDebugEnabled()) {
				logger.debug(exchange.getLogPrefix() + "Mapped to " + handler);
			}
			ServerHttpRequest request = exchange.getRequest();
			if (hasCorsConfigurationSource(handler) || CorsUtils.isPreFlightRequest(request)) {
				CorsConfiguration config = (this.corsConfigurationSource != null ?
						this.corsConfigurationSource.getCorsConfiguration(exchange) : null);
				CorsConfiguration handlerConfig = getCorsConfiguration(handler, exchange);
				config = (config != null ? config.combine(handlerConfig) : handlerConfig);
				if (config != null) {
					config.validateAllowCredentials();
				}
				if (!this.corsProcessor.process(config, exchange) || CorsUtils.isPreFlightRequest(request)) {
					return NO_OP_HANDLER;
				}
			}
			return handler;
		});
	}

3.3 RoutePredicateHandlerMapping#getHandlerInternal

    // 该方法最终会返回FilteringWebHandler
    @Override
	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());
		// 此处会遍历路由集合进行匹配,获取匹配到的route,其中包含了设置的自定义Filter集合
		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) + "]");
					}
				})));
	}
	
	
	
	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);
				})
						// instead of immediately stopping main flux due to error, log and
						// swallow it
						.doOnError(e -> logger.error("Error applying predicate for route: " + route.getId(), e))
						.onErrorResume(e -> Mono.empty()))
				// .defaultIfEmpty() put a static Route not found
				// or .switchIfEmpty()
				// .switchIfEmpty(Mono.<Route>empty().log("noroute"))
				.next()
				// TODO: error handling
				.map(route -> {
					if (logger.isDebugEnabled()) {
						logger.debug("Route matched: " + route.getId());
					}
					validateRoute(route, exchange);
					return route;
				});

		/*
		 * TODO: trace logging if (logger.isTraceEnabled()) {
		 * logger.trace("RouteDefinition did not match: " + routeDefinition.getId()); }
		 */
	}

3.4 SimpleHandlerAdapter#handle

	@Override
	public Mono<HandlerResult> handle(ServerWebExchange exchange, Object handler) {
		WebHandler webHandler = (WebHandler) handler;
		// 此处最终还是执行了handler的handle方法,实际执行的是FilteringWebHandler.handler方法
		Mono<Void> mono = webHandler.handle(exchange);
		return mono.then(Mono.empty());
	}

3.5 FilteringWebHandler#handle

	@Override
	public Mono<Void> handle(ServerWebExchange exchange) {
		Route route = exchange.getRequiredAttribute(GATEWAY_ROUTE_ATTR);
		// 获取路由route中的gatewayFilters集合
		List<GatewayFilter> gatewayFilters = route.getFilters();

		// 获取全局的filter集合globalFilters
		List<GatewayFilter> combined = new ArrayList<>(this.globalFilters);
		// 将自定义filter集合放在全局globalFilters的后面,此处可知,先执行的是GlobalFilter,然后是gatewayFilter
		combined.addAll(gatewayFilters);
		// TODO: needed or cached?
		
		// 此处根据order进行排序,order值越小越先执行,order相同的则按照文件名排序
		AnnotationAwareOrderComparator.sort(combined);

		if (logger.isDebugEnabled()) {
			logger.debug("Sorted gatewayFilterFactories: " + combined);
		}
		// 最终构造filter链执行器
		return new DefaultGatewayFilterChain(combined).filter(exchange);
	}

3.6 DefaultGatewayFilterChain#filter

		@Override
		public Mono<Void> filter(ServerWebExchange exchange) {
			return Mono.defer(() -> {
				if (this.index < filters.size()) {
					GatewayFilter filter = filters.get(this.index);
					// 此处构造了一种链式结构,依次链式执行各个filter的filter方法
					DefaultGatewayFilterChain chain = new DefaultGatewayFilterChain(this, this.index + 1);
					return filter.filter(exchange, chain);
				}
				else {
					return Mono.empty(); // complete
				}
			});
		}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值